feat(evidence): build semantic fragments from typed units
This commit is contained in:
@@ -2,6 +2,7 @@ from datetime import UTC, datetime, timedelta
|
||||
|
||||
import pytest
|
||||
|
||||
from tht.evidence.canonical import CuratedEvidence, dump_curated_markdown
|
||||
from tht.evidence.contracts import AcquiredDocument, SourceObject
|
||||
from tht.evidence.corpus.chunk import ChunkPolicy
|
||||
from tht.evidence.corpus.models import CanonicalChunk, CanonicalDocument, CorpusManifest
|
||||
@@ -116,6 +117,131 @@ def pipeline(tmp_path, source, *, embedder=None, vectors=None, model="model-a",
|
||||
)
|
||||
|
||||
|
||||
def test_pipeline_embeds_validated_curated_evidence_as_semantic_fragments(tmp_path):
|
||||
evidence = CuratedEvidence.model_validate(
|
||||
{
|
||||
"schema_version": 1,
|
||||
"id": "evidence:fascia-pediatrica",
|
||||
"title": "Fascia pediatrica",
|
||||
"kind": "formula",
|
||||
"purposes": ["sql_generation"],
|
||||
"applies_to": {"columns": ["clinical.patient.birth_date"]},
|
||||
"language": "it",
|
||||
"provenance": {
|
||||
"source_file": "source/paziente.md",
|
||||
"source_sha256": "sha256:" + "a" * 64,
|
||||
"supporting_excerpts": ["Pazienti con età inferiore a 18 anni."],
|
||||
},
|
||||
"review_items": [],
|
||||
"payload": {
|
||||
"concept": "fascia pediatrica",
|
||||
"columns": ["clinical.patient.birth_date"],
|
||||
"sql": "CASE WHEN age < 18 THEN 'pediatric' END",
|
||||
},
|
||||
}
|
||||
)
|
||||
source_item = SourceObject(
|
||||
source_id="fs:curated-formula",
|
||||
uri="file:///safe/curated/formula/fascia-pediatrica.md",
|
||||
fingerprint="sha256:" + "b" * 64,
|
||||
metadata={"relative_path": "curated/formula/fascia-pediatrica.md"},
|
||||
)
|
||||
embedder = Embedder()
|
||||
vectors = Vectors()
|
||||
|
||||
result = pipeline(
|
||||
tmp_path,
|
||||
Source([(source_item, dump_curated_markdown(evidence))]),
|
||||
embedder=embedder,
|
||||
vectors=vectors,
|
||||
policy=ChunkPolicy(version="chunk-v1", max_chars=4000),
|
||||
).run()
|
||||
|
||||
assert result.status == "succeeded"
|
||||
assert len(result.manifest.chunks) == 1
|
||||
assert "Formula: Fascia pediatrica" in embedder.calls[0]
|
||||
assert vectors.records[0].record.metadata["evidence_id"] == evidence.id
|
||||
assert vectors.records[0].record.metadata["provenance"]["source_file"] == "source/paziente.md"
|
||||
|
||||
|
||||
def test_pipeline_exposes_atomic_content_review_code_when_candidate_is_blocked(tmp_path):
|
||||
evidence = CuratedEvidence.model_validate(
|
||||
{
|
||||
"schema_version": 1,
|
||||
"id": "evidence:formula-lunga",
|
||||
"title": "Formula lunga",
|
||||
"kind": "formula",
|
||||
"purposes": ["sql_generation"],
|
||||
"language": "it",
|
||||
"provenance": {
|
||||
"source_file": "source/paziente.md",
|
||||
"source_sha256": "sha256:" + "a" * 64,
|
||||
"supporting_excerpts": ["Una formula molto lunga."],
|
||||
},
|
||||
"review_items": [],
|
||||
"payload": {"concept": "formula lunga", "columns": [], "sql": "x" * 200},
|
||||
}
|
||||
)
|
||||
source_item = SourceObject(
|
||||
source_id="fs:formula-lunga",
|
||||
uri="file:///safe/curated/formula/formula-lunga.md",
|
||||
fingerprint="sha256:" + "b" * 64,
|
||||
metadata={"relative_path": "curated/formula/formula-lunga.md"},
|
||||
)
|
||||
|
||||
result = pipeline(
|
||||
tmp_path,
|
||||
Source([(source_item, dump_curated_markdown(evidence))]),
|
||||
policy=ChunkPolicy(version="chunk-v1", max_chars=120),
|
||||
).run()
|
||||
|
||||
assert result.status == "blocked"
|
||||
assert result.published is False
|
||||
assert [item.code for item in result.review_items] == ["atomic_content_too_large"]
|
||||
assert result.review_items[0].field == "formula.sql"
|
||||
|
||||
|
||||
def test_job_pipeline_persists_atomic_content_review_item_when_candidate_is_blocked(tmp_path):
|
||||
evidence = CuratedEvidence.model_validate(
|
||||
{
|
||||
"schema_version": 1,
|
||||
"id": "evidence:formula-lunga-job",
|
||||
"title": "Formula lunga",
|
||||
"kind": "formula",
|
||||
"purposes": ["sql_generation"],
|
||||
"language": "it",
|
||||
"provenance": {
|
||||
"source_file": "source/paziente.md",
|
||||
"source_sha256": "sha256:" + "a" * 64,
|
||||
"supporting_excerpts": ["Una formula molto lunga."],
|
||||
},
|
||||
"review_items": [],
|
||||
"payload": {"concept": "formula lunga", "columns": [], "sql": "x" * 200},
|
||||
}
|
||||
)
|
||||
source_item = SourceObject(
|
||||
source_id="fs:formula-lunga-job",
|
||||
uri="file:///safe/curated/formula/formula-lunga-job.md",
|
||||
fingerprint="sha256:" + "b" * 64,
|
||||
metadata={"relative_path": "curated/formula/formula-lunga-job.md"},
|
||||
)
|
||||
|
||||
result = pipeline(
|
||||
tmp_path,
|
||||
Source([(source_item, dump_curated_markdown(evidence))]),
|
||||
policy=ChunkPolicy(version="chunk-v1", max_chars=120),
|
||||
).run_as_job(
|
||||
workspace_id="demo",
|
||||
workspace_root=tmp_path,
|
||||
config_fingerprint="sha256:" + "1" * 64,
|
||||
input_fingerprint="sha256:" + "2" * 64,
|
||||
)
|
||||
|
||||
assert result.status == "blocked"
|
||||
assert result.published is False
|
||||
assert [item.code for item in result.review_items] == ["atomic_content_too_large"]
|
||||
|
||||
|
||||
def test_pipeline_routes_source_io_through_evidence_facade(tmp_path, monkeypatch):
|
||||
import tht.evidence.acquisition as evidence_acquisition
|
||||
|
||||
|
||||
Reference in New Issue
Block a user