Spaces:
Sleeping
Sleeping
File size: 6,212 Bytes
86c402d |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 |
"""
Модуль с абстрактным классом парсера.
"""
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
@abstractmethod
def parse(self, file: BinaryIO, file_type: FileType | None = None) -> ParsedDocument:
"""
Парсит документ из объекта файла и возвращает его структурное представление.
Args:
file (BinaryIO): Объект файла для парсинга.
file_type (FileType | None): Тип файла, если известен.
Returns:
ParsedDocument: Структурное представление документа.
"""
pass
@abstractmethod
def parse_by_path(self, file_path: str) -> ParsedDocument:
"""
Парсит документ по пути к файлу и возвращает его структурное представление.
Args:
file_path (str): Путь к файлу для парсинга.
Returns:
ParsedDocument: Структурное представление документа.
"""
pass |