Coverage for src/lumen/fhir/binding_validator.py: 96%

24 statements  

« prev     ^ index     » next       coverage.py v7.16.0, created at 2026-08-31 18:46 +0000

1""" 

2This file validates required value-set bindings for primitive code elements. 

3It matches code values against the HL7 binding table to enforce conformance on writes. 

4""" 

5 

6from __future__ import annotations 

7 

8import json 

9from functools import lru_cache 

10from pathlib import Path 

11 

12from .path import evaluate_path 

13 

14_TABLE_PATH = Path(__file__).parent / "data" / "r4b" / "r4b-code-bindings.json" 

15 

16 

17@lru_cache(maxsize=1) 

18def _bindings_by_type() -> dict[str, list[tuple[str, frozenset[str]]]]: 

19 table: dict[str, list[str]] = json.loads(_TABLE_PATH.read_text()) 

20 index: dict[str, list[tuple[str, frozenset[str]]]] = {} 

21 for path, codes in table.items(): 

22 resource_type = path.split(".", 1)[0] 

23 index.setdefault(resource_type, []).append((path, frozenset(codes))) 

24 return index 

25 

26 

27def validate_code_bindings(resource: dict[str, object]) -> list[str]: 

28 """Return messages for code values violating a required binding (empty if valid).""" 

29 resource_type = resource.get("resourceType") 

30 if not isinstance(resource_type, str): 

31 return [] 

32 

33 errors: list[str] = [] 

34 for path, allowed in _bindings_by_type().get(resource_type, []): 

35 for value in evaluate_path(path, resource): 

36 if isinstance(value, str) and value not in allowed: 

37 errors.append( 

38 f"{path}: {value!r} is not in the required value set " 

39 f"({', '.join(sorted(allowed))})" 

40 ) 

41 return errors