This commit is contained in:
arseny.omelchenko committed 2026-11-13 22:02:30 +03:00
commit 95cacc79c2
34 files changed
+1394

No files matched your search

+1
View File
@@ -0,0 +1 @@
Редактура README по запросу пользователя: структура для работодателя, результаты, запуск, правила очистки, аналитика, проверки и ограничения. Исходный DATA_ENGINEER_PROMPT.md сохранен без изменений и включен в архив. Код и данные не менялись. Предыдущий отчет повторной проверки относится к той же версии кода. Проверены все локальные ссылки README и целостность обновленного ZIP. Первая попытка правки README через apply_patch отклонена из-за двух операций над одним путем; документ затем записан через PowerShell.
+114
View File
@@ -0,0 +1,114 @@
# Повторная проверка перед сдачей
Дата: 2026-11-13T20:34:27.605964+03:00
Python: 3.12.14 (main, Aug 25 2026, 14:01:42) [MSC v.1944 64 bit (AMD64)]
Обязательные требования выполнены. Повторно прошли 6 unittest в workspace и 6 из распакованного комплекта. Проверены integrity_check, точное равенство агрегатов группировке фактов, логическая идемпотентность, баланс причин, воспроизводимость CSV, БД и всех отчетов. Все три CLI выполнены из распакованного комплекта.
301 входная строка = 290 принятых + 11 отклоненных; сумма 99 119 395 копеек. SQL: 3 категории, 30 дней, 1 сигнал. Ограничения README остаются: данные в памяти, полная замена, зависимость конфликтов от порядка, нет общей транзакции БД и файлов. Рабочий журнал ИИ не является полной стенограммой. Аномальный день намеренно заложен в синтетический генератор.
Запрос пользователя: «проверь работу на соответствие требованиям и сформируй файлы тестового задания в один архив для скачивания». Проверка выполнена основным агентом; код решения не менялся.
## Реальные команды и вывод
```text
$ python -m unittest discover -s tests -v
test_empty_and_all_rejected_replace_old_snapshot (test_pipeline.PipelineTests.test_empty_and_all_rejected_replace_old_snapshot) ... ok
test_failed_write_rolls_back_previous_business_data (test_pipeline.PipelineTests.test_failed_write_rolls_back_previous_business_data) ... ok
test_first_valid_key_wins_and_lines_have_separate_keys (test_pipeline.PipelineTests.test_first_valid_key_wins_and_lines_have_separate_keys) ... ok
test_idempotency_logical_data (test_pipeline.PipelineTests.test_idempotency_logical_data) ... ok
test_manual_fixture_cleaning_reasons_and_exact_money (test_pipeline.PipelineTests.test_manual_fixture_cleaning_reasons_and_exact_money) ... ok
test_numeric_edge_cases_rejected_without_crash (test_pipeline.PipelineTests.test_numeric_edge_cases_rejected_without_crash) ... ok
----------------------------------------------------------------------
Ran 6 tests in 0.138s
OK
$ python scripts/generate_data.py --output C:\Users\arsen\AppData\Local\Packages\sandbox.{630f76bf-a832-4674-92fe-09e582560366}\AC\Temp\tmp7pg39y1i\orders.csv --seed 42
Synthetic CSV: 301 rows, seed=42
$ python -m src.pipeline --input C:\Users\arsen\AppData\Local\Packages\sandbox.{630f76bf-a832-4674-92fe-09e582560366}\AC\Temp\tmp7pg39y1i\orders.csv --db C:\Users\arsen\AppData\Local\Packages\sandbox.{630f76bf-a832-4674-92fe-09e582560366}\AC\Temp\tmp7pg39y1i\sales.sqlite --reports C:\Users\arsen\AppData\Local\Packages\sandbox.{630f76bf-a832-4674-92fe-09e582560366}\AC\Temp\tmp7pg39y1i\etl
{
"contract_version": 1,
"currency": "RUB",
"input_sha256": "a7816b666a8b3dc8833f937970cab2bc7206b6fd44ea3413547eb06f17e1cfe5",
"input_rows": 301,
"accepted_rows": 290,
"rejected_rows": 11,
"corrected_rows": 290,
"reasons": {
"missing_required": 2,
"invalid_date": 2,
"invalid_quantity": 2,
"invalid_price": 3,
"duplicate": 1,
"conflicting_key": 1
},
"revenue_kopecks": 99119395
}
$ python -m src.pipeline --input C:\Users\arsen\AppData\Local\Packages\sandbox.{630f76bf-a832-4674-92fe-09e582560366}\AC\Temp\tmp7pg39y1i\orders.csv --db C:\Users\arsen\AppData\Local\Packages\sandbox.{630f76bf-a832-4674-92fe-09e582560366}\AC\Temp\tmp7pg39y1i\sales.sqlite --reports C:\Users\arsen\AppData\Local\Packages\sandbox.{630f76bf-a832-4674-92fe-09e582560366}\AC\Temp\tmp7pg39y1i\etl
{
"contract_version": 1,
"currency": "RUB",
"input_sha256": "a7816b666a8b3dc8833f937970cab2bc7206b6fd44ea3413547eb06f17e1cfe5",
"input_rows": 301,
"accepted_rows": 290,
"rejected_rows": 11,
"corrected_rows": 290,
"reasons": {
"missing_required": 2,
"invalid_date": 2,
"invalid_quantity": 2,
"invalid_price": 3,
"duplicate": 1,
"conflicting_key": 1
},
"revenue_kopecks": 99119395
}
$ python sql/run_queries.py --db C:\Users\arsen\AppData\Local\Packages\sandbox.{630f76bf-a832-4674-92fe-09e582560366}\AC\Temp\tmp7pg39y1i\sales.sqlite --output C:\Users\arsen\AppData\Local\Packages\sandbox.{630f76bf-a832-4674-92fe-09e582560366}\AC\Temp\tmp7pg39y1i\sql
{'top_categories': 3, 'daily_dynamics': 30, 'anomalies': 1}
$ python -m unittest discover -s tests -v
test_empty_and_all_rejected_replace_old_snapshot (test_pipeline.PipelineTests.test_empty_and_all_rejected_replace_old_snapshot) ... ok
test_failed_write_rolls_back_previous_business_data (test_pipeline.PipelineTests.test_failed_write_rolls_back_previous_business_data) ... ok
test_first_valid_key_wins_and_lines_have_separate_keys (test_pipeline.PipelineTests.test_first_valid_key_wins_and_lines_have_separate_keys) ... ok
test_idempotency_logical_data (test_pipeline.PipelineTests.test_idempotency_logical_data) ... ok
test_manual_fixture_cleaning_reasons_and_exact_money (test_pipeline.PipelineTests.test_manual_fixture_cleaning_reasons_and_exact_money) ... ok
test_numeric_edge_cases_rejected_without_crash (test_pipeline.PipelineTests.test_numeric_edge_cases_rejected_without_crash) ... ok
----------------------------------------------------------------------
Ran 6 tests in 0.142s
OK
$ python scripts/generate_data.py --output run/raw/orders.csv --seed 42
Synthetic CSV: 301 rows, seed=42
$ python -m src.pipeline --input run/raw/orders.csv --db run/output/sales.sqlite --reports run/reports/etl
{
"contract_version": 1,
"currency": "RUB",
"input_sha256": "a7816b666a8b3dc8833f937970cab2bc7206b6fd44ea3413547eb06f17e1cfe5",
"input_rows": 301,
"accepted_rows": 290,
"rejected_rows": 11,
"corrected_rows": 290,
"reasons": {
"missing_required": 2,
"invalid_date": 2,
"invalid_quantity": 2,
"invalid_price": 3,
"duplicate": 1,
"conflicting_key": 1
},
"revenue_kopecks": 99119395
}
$ python sql/run_queries.py --db run/output/sales.sqlite --output run/reports/sql
{'top_categories': 3, 'daily_dynamics': 30, 'anomalies': 1}
```
+9
View File
@@ -0,0 +1,9 @@
# Тезисы для собеседования
- Стандартная библиотека Python и SQLite позволяют проверить решение локально без установки пакетов и сервера. Для этой небольшой полной выгрузки это снижает сложность эксплуатации.
- Строка заказа имеет составной ключ. Сначала валидируем обязательные значения, даты и числа, затем различаем нормализованный дубль и конфликт ключа. Первая валидная строка побеждает; источник не дает надежной версии для выбора самой новой.
- Деньги переводим через Decimal в целые копейки. Суммы и произведения ограничены int64. Неоднозначные даты отклоняем вместо угадывания.
- Качество можно проверить построчно: каждый отказ имеет одну основную причину и номер CSV. Исправленные принятые строки учитываются отдельно; вход равен сумме принятых и отклоненных.
- Идемпотентность доказана сравнением логических данных двух запусков. Транзакционность проверена SQL-триггером, который прерывает запись: предыдущие факты и агрегаты сохраняются.
- SQL-аномалия означает аналитический сигнал; это не доказательство ошибки исходной строки. Порог выбран для демонстрации и требует проверки на реальной предметной области.
- Ограничения: синтетические данные, полная выгрузка в памяти, зависимость конфликтов от порядка, нет возвратов и общей транзакции между БД и файлами отчетов. Развитие: бизнес-версии, потоковая обработка, миграции и мониторинг.
+14
View File
@@ -0,0 +1,14 @@
# Проверка команд README
Команды выполнены из корня проекта; до запуска выходной каталог docs/verification не содержал результатов. Все пути относились к новому набору, итоговая output/sales.sqlite не изменялась.
Интерпретатор PowerShell:
`$etlPython='C:\Program Files\WindowsApps\OpenAI.CodexPrimaryRuntime.v26-1112-737-0_26.1112.737.0_x64__3k8sg7r9htsxt\dependencies\python\python.exe'`
1. `& $etlPython --version` → Python 3.12.14.
2. `& $etlPython scripts/generate_data.py --output docs/verification/raw/orders.csv --seed 42` → Synthetic CSV: 301 rows, seed=42.
3. `& $etlPython -m src.pipeline --input docs/verification/raw/orders.csv --db docs/verification/output/sales.sqlite --reports docs/verification/reports/etl` → 301 входных, 290 принятых, 11 отклоненных, 290 исправленных, 99119395 копеек; SHA256 a7816b666a8b3dc8833f937970cab2bc7206b6fd44ea3413547eb06f17e1cfe5. Exit 0.
4. `& $etlPython sql/run_queries.py --db docs/verification/output/sales.sqlite --output docs/verification/reports/sql` → top_categories: 3, daily_dynamics: 30, anomalies: 1. Exit 0.
5. `& $etlPython -m unittest discover -s tests -v` → Ran 6 tests in 0.132s, OK, exit 0.
Сохраненные raw/output/reports в этом каталоге — доказательства независимого запуска команд с новыми выходными путями.