"""Иерархия строк на реальных ОСВ из ../fixtures (ruling R-2, R-13; spec «Иерархия строк — каскад стратегий»). Свойства без таблицы файлов: дерево непротиворечиво, «Итого» — уровень 0; у файла со строками данных — `outline` (у всех фикстур есть группировки Excel), у пустой ОСВ (только «Итого») — `trivial`. Разбор файла укладывается в 5 с. """ from pathlib import Path import pytest from real_osv import parse_real from src.parser.hierarchy import TRIVIAL_STRATEGY, is_consistent MAX_SECONDS_PER_FILE = 5 RB_66_FY = Path("osv/rb/2024-FY/ОСВ_66 за 2024.xls") YUG_FINANS = "Юг-Финанс / ПЕКАРНЯ СЧАСТЛИВОЧНАЯ" COUNTERPARTY_LEVEL = 2 # счёт (0) → субсчёт (1) → контрагент (2) @pytest.mark.fixtures def test_real_osv_hierarchy(osv_file: Path) -> None: parsed = parse_real(osv_file) assert is_consistent(parsed.body, parsed.levels.by_row, parsed.total_row) assert parsed.total_row is not None assert parsed.levels.by_row[parsed.total_row] == 0 assert parsed.levels.parent[parsed.total_row] is None expected = "outline" if parsed.data_rows else TRIVIAL_STRATEGY assert parsed.levels.strategy == expected assert parsed.seconds < MAX_SECONDS_PER_FILE @pytest.mark.fixtures def test_rb_66_fy_outline_tree(fixtures_dir: Path) -> None: """Spec «Outline level (реальные файлы)»: 66 (0) → 66.01 (1) → контрагент (2); «Юг-Финанс» — под 66.03.""" parsed = parse_real(fixtures_dir / RB_66_FY) assert parsed.levels.strategy == "outline" account, subaccount, counterparty = parsed.rows[:3] assert [(account.body.text, account.level), (subaccount.body.text, subaccount.level)] == [("66", 0), ("66.01", 1)] assert (counterparty.level, counterparty.parent) == (COUNTERPARTY_LEVEL, subaccount.body.row) first = parsed.by_text(YUG_FINANS)[0] assert first.parent is not None assert parsed.row(first.parent).body.text == "66.03"