Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@
)

ContractText = Annotated[str, Field(min_length=1, max_length=255)]
ObservabilityId = Annotated[str, Field(min_length=1, max_length=36)]
# ``evaluation_id`` is the already-deployed physical database and wire field
# for the temporary comparison-run identifier. Stage 14 owns its removal.
Sha256Digest = Annotated[str, Field(pattern=r"^[0-9a-f]{64}$")]
Expand Down Expand Up @@ -525,6 +526,7 @@ class ComparisonReportRecord(StrictContractModel):
environment: ContractText
calculation_flow: ContractText
originating_request_id: ContractText
observability_id: ObservabilityId | None = None
production_identity: ContractText
incumbent_execution_id: ContractText | None = None
worker_version: ContractText
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -92,6 +92,7 @@
Column("environment", String(255), nullable=False),
Column("calculation_flow", String(255), nullable=False),
Column("originating_request_id", String(255), nullable=False),
Column("observability_id", String(36)),
Column("production_identity", String(255), nullable=False),
Column("incumbent_execution_id", String(255)),
Column("worker_version", String(255), nullable=False),
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -229,6 +229,7 @@ def _exercise_runtime_dml(connection: Connection, *, environment: str) -> None:
"environment": environment,
"calculation_flow": "infrastructure_validation",
"originating_request_id": f"validation-{evaluation_id}",
"observability_id": None,
"production_identity": f"validation-{evaluation_id}",
"incumbent_execution_id": None,
"worker_version": "validation",
Expand Down
10 changes: 10 additions & 0 deletions libs/policyengine-stage12-persistence/tests/test_store.py
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,7 @@ def _report() -> ComparisonReportRecord:
environment="staging",
calculation_flow="economy",
originating_request_id="request-1",
observability_id="00000000-0000-0000-0000-000000000003",
production_identity="job-1",
incumbent_execution_id="job-1",
worker_version="5.2.0",
Expand Down Expand Up @@ -125,6 +126,15 @@ def test_create_and_read_report_use_sqlalchemy_statements_only() -> None:
assert result.created is True
assert result.record == report
assert len(engine.connection.statements) == 1
assert "observability_id" in str(engine.connection.statements[0])


def test_report_observability_identifier_is_limited_to_36_characters() -> None:
values = _report().model_dump(mode="python")
values["observability_id"] = "x" * 37

with pytest.raises(ValueError, match="at most 36 characters"):
ComparisonReportRecord.model_validate(values)


def test_report_identity_conflict_resolves_existing_row() -> None:
Expand Down
16 changes: 11 additions & 5 deletions libs/policyengine-stage12-persistence/tests/test_tables.py
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@
comparison_simulations,
metadata,
)
from sqlalchemy import ForeignKeyConstraint, UniqueConstraint
from sqlalchemy import ForeignKeyConstraint, String, UniqueConstraint


def test_mappings_cover_every_cross_service_record_field() -> None:
Expand All @@ -25,6 +25,14 @@ def test_mappings_cover_every_cross_service_record_field() -> None:
assert comparison_simulations.schema == "public"


def test_report_observability_identifier_matches_api_owned_schema() -> None:
column = comparison_reports.c.observability_id

assert column.nullable is True
assert isinstance(column.type, String)
assert column.type.length == 36


def test_mappings_retain_identity_and_parent_constraints() -> None:
report_unique = next(
constraint
Expand Down Expand Up @@ -60,13 +68,11 @@ def test_mappings_retain_identity_and_parent_constraints() -> None:
)
assert parent_key.ondelete == "CASCADE"
assert parent_key.name == (
"fk_stage12_evaluation_simulations_evaluation_id_"
"stage12_evaluation_reports"
"fk_stage12_evaluation_simulations_evaluation_id_stage12_evaluation_reports"
)
assert comparison_reports.primary_key.name == "pk_stage12_evaluation_reports"
assert (
comparison_simulations.primary_key.name
== "pk_stage12_evaluation_simulations"
comparison_simulations.primary_key.name == "pk_stage12_evaluation_simulations"
)


Expand Down
Loading