"""C-1 후속 — facets 집계 + version_status decorate 순수 로직 테스트. version_status 의 실제 legal_meta 조회는 GPU 라이브(법령 검색)로 검증 — 여기선 facets 분포 계약 + decorate 의 law 무결과 skip 경로(DB 미접촉)만. """ import asyncio import sys from pathlib import Path sys.path.insert(0, str(Path(__file__).parent.parent / "app")) from services.search.result_decorate import ( # noqa: E402 compute_facets, decorate_version_status, ) class _R: """SearchResult 흉내 — 분류 축 속성만.""" def __init__(self, material_type=None, jurisdiction=None, version_status=None, id=1): self.material_type = material_type self.jurisdiction = jurisdiction self.version_status = version_status self.id = id def test_compute_facets_distribution(): results = [ _R("law", "KR", "current"), _R("law", "KR", "superseded"), _R("incident", "KR", None), _R("paper", None, None), ] f = compute_facets(results) assert f["material_type"] == {"law": 2, "incident": 1, "paper": 1} assert f["jurisdiction"] == {"KR": 3} # paper jurisdiction None 제외 assert f["version_status"] == {"current": 1, "superseded": 1} # None 제외 def test_compute_facets_empty_and_all_none(): assert compute_facets([]) == {} assert compute_facets([_R(), _R()]) == {} # 모든 축 None → 빈 축 미포함 def test_compute_facets_excludes_empty_axes(): f = compute_facets([_R(jurisdiction="US"), _R(jurisdiction="EU")]) assert f == {"jurisdiction": {"US": 1, "EU": 1}} assert "material_type" not in f def test_decorate_version_status_skips_without_law(): # law 결과 없으면 legal_meta 조회 skip → session 미사용(None 으로도 무오류) results = [_R("incident", "KR"), _R("paper")] asyncio.run(decorate_version_status(None, results)) assert all(r.version_status is None for r in results)