Spaces:
Sleeping
Sleeping
""" | |
Модуль с абстрактным классом парсера. | |
""" | |
import os | |
from abc import ABC, abstractmethod | |
from typing import BinaryIO | |
from ..data_classes import ParsedDocument | |
from .file_types import FileType | |
class AbstractParser(ABC): | |
""" | |
Абстрактный класс парсера документов. | |
Все конкретные парсеры должны наследоваться от этого класса | |
и реализовывать метод parse. | |
""" | |
def __init__(self, file_types: FileType | list[FileType] | str | list[str] | None = None): | |
""" | |
Инициализирует парсер. | |
Args: | |
file_types: Поддерживаемые типы файлов. Может быть одним из: | |
- FileType - объект перечисления | |
- list[FileType] - список объектов перечисления | |
- str - строка с расширением файла (с точкой, например ".xml") | |
- list[str] - список строк с расширениями | |
- None - если не указан, парсер не ограничен типами | |
""" | |
self.file_types = [] | |
if file_types is None: | |
return | |
# Преобразуем одиночный FileType в список | |
if isinstance(file_types, FileType): | |
self.file_types = [file_types] | |
# Преобразуем список FileType в список | |
elif isinstance(file_types, list) and all(isinstance(ft, FileType) for ft in file_types): | |
self.file_types = file_types | |
# Преобразуем строку расширения в FileType | |
elif isinstance(file_types, str): | |
try: | |
self.file_types = [FileType.from_extension(file_types)] | |
except ValueError: | |
# Если не удалось найти подходящий FileType, создаем пустой список | |
self.file_types = [] | |
# Преобразуем список строк расширений в список FileType | |
elif isinstance(file_types, list) and all(isinstance(ft, str) for ft in file_types): | |
self.file_types = [] | |
for ext in file_types: | |
try: | |
self.file_types.append(FileType.from_extension(ext)) | |
except ValueError: | |
pass | |
def _supported_extension(self, ext: str) -> bool: | |
""" | |
Проверяет, поддерживается ли расширение файла. | |
Этот метод должен быть переопределен в наследниках | |
для указания поддерживаемых расширений. | |
Args: | |
ext (str): Расширение файла с точкой (.pdf, .docx и т.д.). | |
Returns: | |
bool: True, если расширение поддерживается, иначе False. | |
""" | |
if not self.file_types: | |
try: | |
FileType.from_extension(ext) | |
return True | |
except ValueError: | |
return False | |
ext = ext.lower() | |
for file_type in self.file_types: | |
for supported_ext in file_type.value: | |
if ext == supported_ext.lower(): | |
return True | |
return False | |
def supports_file(self, file: str | BinaryIO | FileType) -> bool: | |
""" | |
Проверяет, может ли парсер обработать файл. | |
Args: | |
file: Может быть одним из: | |
- str: Путь к файлу | |
- BinaryIO: Объект файла | |
- FileType: Конкретный тип файла | |
Returns: | |
bool: True, если парсер поддерживает файл, иначе False. | |
""" | |
# Если передан FileType, проверяем его наличие в списке поддерживаемых | |
if isinstance(file, FileType): | |
return file in self.file_types | |
# Если переданы пустые file_types и не строка, не можем определить тип | |
if not self.file_types and not isinstance(file, str): | |
return False | |
# Если передан путь к файлу, проверяем расширение | |
if isinstance(file, str): | |
_, ext = os.path.splitext(file) | |
return self._supported_extension(ext) | |
# Если передан бинарный объект, считаем что подходит | |
# (конкретный тип будет проверен при вызове parse) | |
return True | |
def parse(self, file: BinaryIO, file_type: FileType | None = None) -> ParsedDocument: | |
""" | |
Парсит документ из объекта файла и возвращает его структурное представление. | |
Args: | |
file (BinaryIO): Объект файла для парсинга. | |
file_type (FileType | None): Тип файла, если известен. | |
Returns: | |
ParsedDocument: Структурное представление документа. | |
""" | |
pass | |
def parse_by_path(self, file_path: str) -> ParsedDocument: | |
""" | |
Парсит документ по пути к файлу и возвращает его структурное представление. | |
Args: | |
file_path (str): Путь к файлу для парсинга. | |
Returns: | |
ParsedDocument: Структурное представление документа. | |
""" | |
pass |