Andrey Epifancev 3fc8fa7871 test(osv): синтетика s17–s19 (ИНН в названии, строкой выше, ИНН/КПП) и golden: ИНН из текста названия
Новые: s17_inn_in_name, s18_inn_row_above, s19_inn_kpp_cell + снимки. Изменены 9 снимков (rb 60 ×5, schastl 76 ×4):
counterparty_name без ИНН и разделителя, counterparty_inn — извлечённый ИНН; остальное без изменений.
Парный PR: RSHB/arm-tabular-parser (feat/9-inn-in-text), issue #9.

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
Claude-Session: cedd7915-2efe-41e5-988c-a9117033598b
2026-10-06 13:13:42 +04:00

60 lines
9.5 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

# osv/synthetic — синтетические ОСВ
Синтетика для форматов шапки, иерархии и колонок, которых нет в реальных файлах `osv/{rb,schastl}/`. Данных реальных
организаций здесь нет: организация «ООО "Тестовая организация"», контрагенты «ООО Альфа», «ООО Бета» и т. п., ИНН
вымышленные. Файлы — **вход** парсера ОСВ (`tabular-parser`), а не эталон: ожидания по каждому файлу выведены из спеки
(`openspec/changes/slice-2a-osv-parser/specs/osv-parsing/spec.md`) и лежат в тесте
`tabular-parser/api/tests/synthetic/test_synthetic_files.py`.
Суммы согласованы арифметически (сальдо на конец = начало + обороты, родитель = сумма детей по колонкам), поэтому все
файлы, кроме `s10`, сходятся по контрольным суммам §1.4 и дают статус `done`.
## Генерация
Файлы собирает детерминированный генератор (openpyxl + минимальный писатель BIFF12 для xlsb); повторный запуск даёт
те же байты (метки времени книги и zip зафиксированы):
```
cd tabular-parser/api
.venv/bin/python -m tests.synthetic.generate ../../fixtures/osv/synthetic
```
Правка набора — в `tabular-parser/api/tests/synthetic/generate.py`, затем перегенерация и коммит файлов здесь.
## Набор
| Файл | Что проверяет | Ожидание |
|---|---|---|
| `s01_variant2_header.xlsx` | шапка варианта 2: «Период: …», «Детализация по субсчетам, субконто: Контрагенты, Договоры», заголовок «Субконто»; данные «Сумма» | `header_variant=2`, `group_schema=[ACCOUNT, COUNTERPARTY, CONTRACT]`, `Q1`/2026, `data_type=SUM`, `hierarchy=outline` |
| `s02_no_outline_indent.xlsx` | уровни только отступами ячеек (без outline level); `Валюта БУ, НУ: руб.`; период «2 квартал 2025 г.» | `hierarchy=indent`, дерево 0/1/2 |
| `s03_no_outline_no_indent.xlsx` | ни outline, ни отступов: уровни по кодам счетов и жирности; период «I кв. 2025 г.» (римский квартал) | `hierarchy=account_pattern`, дерево как у `s02` |
| `s04_currency_quantity_rows.xlsx` | под контрагентом строки «USD», «Кол.» (и «Вал.» у другого) | `data_type` `CURRENCY`/`QUANTITY`, в проверку суммы детей не входят, `done` |
| `s05_text_numbers.xlsx` | суммы текстом: «1 234 567,89», «(1 234,00)», «—»; неразрывные и узкие пробелы, прочерки «–», «-»; период «полугодие 2025 г.» | `1234567.89`, `-1234.00`, `null` |
| `s06_two_osv_and_other_sheet.xlsx` | листы «ОСВ 60», «Справка», «ОСВ 62» | два документа в порядке листов, предупреждение о пропуске «Справка» |
| `s07_no_opening_collapsed_closing.xlsx` | нет группы «Сальдо на начало»; сальдо на конец — одна колонка со знаком; период «9 месяцев 2025 г.» | `opening_* = null`, отрицательное сальдо — в `closing_credit`, предупреждение о свёрнутом сальдо |
| `s08_extra_kpp_column.xlsx` | колонка «КПП» между «ИНН» и суммами; период «с 01.01.2025 по 31.03.2025» | `extra["КПП"]` у контрагентов, суммы не сдвинуты |
| `s09_subaccount_names.xlsx` | «60.01, Расчеты с поставщиками и подрядчиками», буквенный субсчёт «60.АВ, …» | `ACCOUNT`, `account_code_raw` без названия, `row_value` — исходный текст |
| `s10_broken_sum.xlsx` | у «ООО Бета» `closing_debit` увеличен на 1 | `needs_check`, нарушение тождества — строка контрагента, суммы родителя — строка «60.01» |
| `s11_header_repeat.xlsx` | заголовок таблицы повторяется внутри данных (печать по страницам); период «12 месяцев 2025 г.» | строки заголовка пропущены, дерево и суммы не нарушены |
| `s12_statement_and_osv.xlsx` | лист ББ («Бухгалтерский баланс», 0710001) и лист «ОСВ 60»; данные «НУ», период «январь - сентябрь 2025 г.» | один документ, предупреждение «skipped: statement» |
| `s13_no_outline_indent.xlsb` | та же ведомость, что `s02`, в формате xlsb; отступ — ведущими пробелами текста | результат равен `s02` кроме предупреждения «xlsb: outline level недоступен» |
| `s14_statement_forms.xlsx` | три листа форм, каждый опознаётся одним признаком: «Форма по ОКУД 0710001», «Отчет о финансовых результатах», «Форма по ОКУД 0710002»; лист «ОСВ 60» | один документ, три предупреждения «skipped: statement» |
| `s15_group_title_synonyms.xlsx` | названия групп сумм: лист «ОСВ 60» — «Входящее сальдо»/«Конечное сальдо», лист «ОСВ 62» — «Начальное сальдо»/«Исходящее сальдо» | два документа, все шесть колонок сумм найдены, `done` |
| `s16_header_synonyms.xlsx` | лист «ОСВ 60»: нет названия организации, период «2024», валюта «RUB (код 643)», «Счет» и «Контрагенты» отдельными строками под «Дебет/Кредит»; лист «ОСВ 62» (вариант 2): «Детализация по субсчетам: Номенклатура, Статьи затрат, Нематериальные активы, Валюта» | `organization_name=""` + предупреждение, `Q4`/2024, `currency=RUB`, схема листа 62 — `ACCOUNT` + четыре `OTHER` |
| `s17_inn_in_name.xlsx` | колонки ИНН нет, ИНН записан в текст названия контрагента: «ООО Альфа, 7701234567», «ООО Бета (ИНН 7707654321)», «ООО Гамма ИНН: 5001234567», «ИП Сидоров 500100732259» (OQ-100) | `counterparty_inn` — цифры, `counterparty_name` — без ИНН и разделителя, `row_value` не меняется; физлицо без ИНН — `null`; `done` |
| `s18_inn_row_above.xlsx` | у «ООО Альфа» и «ООО Гамма» ИНН стоит отдельной строкой над названием (без сумм, тот же уровень), колонки ИНН нет (OQ-130) | строка с ИНН в `rows` не попадает и не уходит в `OTHER`; ИНН — у контрагента, предупреждение «ИНН … над строкой … отнесён к ней»; `done` |
| `s19_inn_kpp_cell.xlsx` | колонка «ИНН/КПП»: в ячейках склеенное «7701234567/770101001» (OQ-100) | `counterparty_inn` — только ИНН; колонка распознана как колонка ИНН; `done` |
`s17`–`s19` — регрессия извлечения ИНН из текста (issue #9). `s14`–`s16` добавлены тестом покрытия словарей `tabular-parser` (`rules/*.yaml`, решение R-22): каждая запись словаря
должна сработать на реальных или синтетических файлах; эти файлы закрывают записи, которых нет в реальных ОСВ.
## О файле xlsb
`s13_no_outline_indent.xlsb` собран **не Excel и не LibreOffice** (их на машине разработки нет), а минимальным
писателем BIFF12 `tabular-parser/api/tests/synthetic/xlsb_writer.py`: он пишет только то, что читает `pyxlsb`
(workbook, таблица общих строк, лист; без стилей и объединений). Файл читается `pyxlsb` и парсером, но совместимость с
Excel не проверялась и этот файл не доказывает чтение xlsb, сохранённого Excel (другая раскладка записей, стили,
`BrtCellSt` и т. д.). Когда появится возможность — заменить `s13` настоящим: открыть `s02_no_outline_indent.xlsx` в
Excel или LibreOffice, «Сохранить как» → Книга Excel двоичная (`.xlsb`), имя `s13_no_outline_indent.xlsb`; в xlsb нет
outline level и форматирования ячеек, отступ нужно продублировать ведущими пробелами в колонке текста до сохранения.