"""Build data/ergo-knowledge-base.json from the raw datasource dumps. Run: uv run python scripts/build_knowledge_base.py """ from __future__ import annotations import json from pathlib import Path ROOT = Path(__file__).resolve().parents[1] PARAMS_FILE = ROOT / "docs" / "datasources" / "common-assessment-parameters.json" ISSUES_FILE = ROOT / "docs" / "datasources" / "issue-based-outcomes.json" OUT_FILE = ROOT / "data" / "ergo-knowledge-base.json" def _none_if_empty(value): if value is None: return None if isinstance(value, str) and value.strip() == "": return None return value def main() -> None: raw_params = json.loads(PARAMS_FILE.read_text()) raw_issues = json.loads(ISSUES_FILE.read_text()) issues_by_outcome = {row["outcome"]: row for row in raw_issues} parameters = [] for p in raw_params: options = [] for o in p["options"]: key = o["option"] risk_title = _none_if_empty(o.get("riskTitle")) overall_risk = _none_if_empty(o.get("overallRisk")) is_good_habit = risk_title is None and overall_risk is None issue = issues_by_outcome.get(key) if issue is None: raise SystemExit( f"Missing issue-based-outcomes entry for option key: {key}" ) posture_score = issue["postureScore"] # Parameter file is the authoritative visual rubric — if it says # good habit, force risk_level to null. Otherwise take the issue # file's risk_level. if is_good_habit: risk_level = None else: risk_level = _none_if_empty(issue.get("riskLevel")) if risk_level is None: raise SystemExit( f"{key}: risky in parameter file but issue riskLevel is null" ) options.append( { "key": key, "label": o["optionText"], "reference_image": o["optionImage"], "is_good_habit": is_good_habit, "risk_level": risk_level, "posture_score": posture_score, "risk_title": risk_title, "overall_risk": overall_risk, } ) selection_mode = "multi" if p.get("has_multi_select") else "single" parameters.append( { "id": p["id"], "group": p["group"], "order": p["order"], "selection_mode": selection_mode, "parameter_text": p["parameterText"], "question_text": p["question_text"], "options": options, } ) payload = {"version": "1.0", "parameters": parameters} OUT_FILE.parent.mkdir(parents=True, exist_ok=True) OUT_FILE.write_text(json.dumps(payload, indent=2) + "\n") print(f"Wrote {OUT_FILE} ({len(parameters)} parameters, " f"{sum(len(p['options']) for p in parameters)} options)") if __name__ == "__main__": main()