feat(organizations): migrate source storage to polymorphic records
This commit is contained in:
143
tests/apps/organizations/test_source_ingestion.py
Normal file
143
tests/apps/organizations/test_source_ingestion.py
Normal file
@@ -0,0 +1,143 @@
|
||||
"""Tests for direct parser ingestion into organization source storage."""
|
||||
|
||||
from decimal import Decimal
|
||||
|
||||
from apps.parsers.models import FinancialReport, GenericParserRecord, ParserLoadLog
|
||||
from django.test import TestCase
|
||||
from organizations.models import (
|
||||
DefenseSupplierExtension,
|
||||
FinancialIndicatorsExtension,
|
||||
Organization,
|
||||
OrganizationSourceFinancialLine,
|
||||
OrganizationSourceRecord,
|
||||
SourceGroup,
|
||||
)
|
||||
from organizations.source_ingestion import (
|
||||
OrganizationSourceIngestionService,
|
||||
SourceFinancialLineInput,
|
||||
SourceRecordInput,
|
||||
)
|
||||
|
||||
|
||||
class OrganizationSourceIngestionServiceTest(TestCase):
|
||||
"""Checks runtime parser writes bypass legacy parser record tables."""
|
||||
|
||||
def test_save_generic_records_writes_source_records_without_legacy_rows(self):
|
||||
result = OrganizationSourceIngestionService.save_records(
|
||||
source=ParserLoadLog.Source.UNFAIR_SUPPLIERS,
|
||||
load_batch=42,
|
||||
records=[
|
||||
SourceRecordInput(
|
||||
external_id="unfair-42",
|
||||
title="Недобросовестный поставщик",
|
||||
organization_name='ООО "ГОЗ"',
|
||||
inn="7707083803",
|
||||
ogrn="",
|
||||
record_date="2026-05-18",
|
||||
amount=Decimal("100.50"),
|
||||
status="active",
|
||||
url="https://example.test/unfair-42",
|
||||
payload={"reason": "contract breach"},
|
||||
)
|
||||
],
|
||||
)
|
||||
|
||||
self.assertEqual(result.scanned, 1)
|
||||
self.assertEqual(result.created_records, 1)
|
||||
self.assertEqual(result.updated_records, 0)
|
||||
self.assertEqual(result.created_extensions, 1)
|
||||
self.assertEqual(result.unresolved, 0)
|
||||
self.assertEqual(GenericParserRecord.objects.count(), 0)
|
||||
|
||||
organization = Organization.objects.get(inn="7707083803")
|
||||
extension = DefenseSupplierExtension.objects.get(organization=organization)
|
||||
self.assertEqual(extension.source_group, SourceGroup.DEFENSE_SUPPLIERS)
|
||||
self.assertEqual(extension.records_count, 1)
|
||||
|
||||
record = OrganizationSourceRecord.objects.get(extension=extension)
|
||||
self.assertEqual(record.source, ParserLoadLog.Source.UNFAIR_SUPPLIERS)
|
||||
self.assertEqual(record.record_type, "unfair_supplier")
|
||||
self.assertEqual(record.external_id, "unfair-42")
|
||||
self.assertEqual(record.amount, Decimal("100.50"))
|
||||
self.assertEqual(record.payload["reason"], "contract breach")
|
||||
self.assertEqual(record.legacy_model, "")
|
||||
self.assertEqual(record.legacy_pk, "")
|
||||
|
||||
def test_save_records_is_idempotent_by_source_external_id(self):
|
||||
first = SourceRecordInput(
|
||||
external_id="unfair-idempotent",
|
||||
title="Old title",
|
||||
organization_name='ООО "Идемпотентность"',
|
||||
inn="7707083810",
|
||||
status="old",
|
||||
payload={"version": 1},
|
||||
)
|
||||
second = SourceRecordInput(
|
||||
external_id="unfair-idempotent",
|
||||
title="New title",
|
||||
organization_name='ООО "Идемпотентность"',
|
||||
inn="7707083810",
|
||||
status="new",
|
||||
payload={"version": 2},
|
||||
)
|
||||
|
||||
OrganizationSourceIngestionService.save_records(
|
||||
source=ParserLoadLog.Source.UNFAIR_SUPPLIERS,
|
||||
load_batch=43,
|
||||
records=[first],
|
||||
)
|
||||
result = OrganizationSourceIngestionService.save_records(
|
||||
source=ParserLoadLog.Source.UNFAIR_SUPPLIERS,
|
||||
load_batch=44,
|
||||
records=[second],
|
||||
)
|
||||
|
||||
self.assertEqual(result.created_records, 0)
|
||||
self.assertEqual(result.updated_records, 1)
|
||||
self.assertEqual(OrganizationSourceRecord.objects.count(), 1)
|
||||
record = OrganizationSourceRecord.objects.get()
|
||||
self.assertEqual(record.title, "New title")
|
||||
self.assertEqual(record.status, "new")
|
||||
self.assertEqual(record.payload["version"], 2)
|
||||
self.assertEqual(record.load_batch, 44)
|
||||
|
||||
def test_save_financial_report_writes_financial_lines_without_legacy_report(self):
|
||||
result = OrganizationSourceIngestionService.save_records(
|
||||
source=ParserLoadLog.Source.FNS_REPORTS,
|
||||
load_batch=88,
|
||||
records=[
|
||||
SourceRecordInput(
|
||||
external_id="fns-report-1",
|
||||
title="fin_001_1027700132002.xlsx",
|
||||
organization_name="",
|
||||
ogrn="1027700132002",
|
||||
status="success",
|
||||
payload={
|
||||
"file_name": "fin_001_1027700132002.xlsx",
|
||||
"file_hash": "a" * 64,
|
||||
},
|
||||
financial_lines=[
|
||||
SourceFinancialLineInput(
|
||||
form_code="1",
|
||||
line_code="1100",
|
||||
line_name="Нематериальные активы",
|
||||
year=2025,
|
||||
period_start=100,
|
||||
period_end=200,
|
||||
)
|
||||
],
|
||||
)
|
||||
],
|
||||
)
|
||||
|
||||
self.assertEqual(result.created_records, 1)
|
||||
self.assertEqual(result.created_financial_lines, 1)
|
||||
self.assertEqual(FinancialReport.objects.count(), 0)
|
||||
|
||||
organization = Organization.objects.get(ogrn="1027700132002")
|
||||
extension = FinancialIndicatorsExtension.objects.get(organization=organization)
|
||||
record = OrganizationSourceRecord.objects.get(extension=extension)
|
||||
self.assertEqual(record.source, ParserLoadLog.Source.FNS_REPORTS)
|
||||
line = OrganizationSourceFinancialLine.objects.get(source_record=record)
|
||||
self.assertEqual(line.line_code, "1100")
|
||||
self.assertEqual(line.period_end, 200)
|
||||
Reference in New Issue
Block a user