"""Инварианты форм на всех `../fixtures/statements-xlsx/**` по манифесту (spec «Словари форм, координаты, golden»).""" import time from pathlib import Path from typing import cast import pytest from fixtures_helpers import statement_files from result_contract import assert_valid_result from statement_helpers import load_manifest, relative_key from src.contract import FileType, ResultStatus, StatementDocument from src.parser import get_parser pytestmark = pytest.mark.fixtures EXPECTED_FILES = 18 MAX_PARSE_SECONDS = 5 def test_manifest_covers_every_file(fixtures_dir: Path) -> None: files = statement_files(fixtures_dir) assert len(files) == EXPECTED_FILES assert {relative_key(fixtures_dir, path) for path in files} == set(load_manifest()) def test_statement_file_matches_manifest(fixtures_dir: Path, statement_file: Path) -> None: expectation = load_manifest()[relative_key(fixtures_dir, statement_file)] started = time.monotonic() file_type = cast(FileType, statement_file.suffix.lstrip(".").upper()) outcome = get_parser().parse(statement_file.read_bytes(), file_type) assert time.monotonic() - started < MAX_PARSE_SECONDS assert outcome.error is None, outcome.error documents = [document for document in outcome.documents if isinstance(document, StatementDocument)] assert [document.document_type for document in documents] == [item.type for item in expectation.documents] all_done = all(item.status == "done" for item in expectation.documents) assert outcome.status is (ResultStatus.DONE if all_done else ResultStatus.NEEDS_CHECK) for document, item in zip(documents, expectation.documents, strict=True): codes = [line.line_code for line in document.lines] assert len(codes) == len(set(codes)), "коды уникальны" assert all(value.column_index < len(document.columns) for line in document.lines for value in line.values) if item.sheets: assert document.locator.count(",") == item.sheets - 1 if item.complete: assert document.checks is not None assert document.checks.relations_failed == [], document.checks assert document.columns assert all(column.period_date is not None for column in document.columns) if expectation.organization and document.header.organization_name is not None: assert document.header.organization_name == expectation.organization if expectation.inn and document.document_type not in expectation.inn_optional_for and document.header.inn: assert document.header.inn == expectation.inn assert_valid_result(outcome)