"""Tests feature Questionnaires : PHQ-9 fourni, authoring QCM, scoring, assignation, résultats chiffrés dans le dossier patient.""" import nacl.pwhash from kazeia_central.core.store import Store from kazeia_central.features.medical.questionnaires import service as svc _OPS = nacl.pwhash.argon2id.OPSLIMIT_MIN _MEM = nacl.pwhash.argon2id.MEMLIMIT_MIN NOW = 1_700_000_000_000 def _store(tmp_path): s = Store(tmp_path / "c.db", kdf_ops=_OPS, kdf_mem=_MEM) s.unlock("pw") return s def test_phq9_seeded_and_undeletable(tmp_path): s = _store(tmp_path) ids = {q["id"] for q in svc.list_questionnaires(s)} assert "phq9" in ids q = svc.get_questionnaire(s, "phq9") assert q["builtin"] is True and len(q["definition"]["questions"]) == 9 assert svc.delete_questionnaire(s, "phq9", now=NOW)["deleted"] is False # fourni → protégé def test_phq9_scoring_bands(tmp_path): s = _store(tmp_path) defn = svc.get_questionnaire(s, "phq9")["definition"] assert svc.score(defn, [0] * 9) == {"total_score": 0, "interpretation": defn["scoring"]["ranges"][0]["label"]} top = svc.score(defn, [3] * 9) assert top["total_score"] == 27 and "sévère" in top["interpretation"].lower() def test_authoring_custom_qcm(tmp_path): s = _store(tmp_path) defn = { "type": "qcm", "questions": [{"text": "Sommeil ?", "choices": [{"label": "Bon", "score": 0}, {"label": "Mauvais", "score": 2}]}], "scoring": {"method": "sum", "ranges": [{"min": 0, "max": 1, "label": "ok"}, {"min": 2, "max": 2, "label": "alerte"}]}, } svc.save_questionnaire(s, "sommeil", "Suivi sommeil", defn, now=NOW, actor="dr") assert svc.score(defn, [1])["interpretation"] == "alerte" assert svc.delete_questionnaire(s, "sommeil", now=NOW)["deleted"] is True def test_assign_list_deactivate(tmp_path): s = _store(tmp_path) r = svc.assign(s, "phq9", "SER1", "p_1", {"mode": "recurring", "every_days": 7}, now=NOW, actor="dr") aid = r["assignment_id"] ags = svc.assignments(s, serial="SER1") assert len(ags) == 1 and ags[0]["frequency"]["every_days"] == 7 and ags[0]["active"] == 1 svc.deactivate(s, aid, now=NOW, actor="dr") assert svc.assignments(s, serial="SER1") == [] # active_only → filtré def test_result_into_patient_dossier_encrypted(tmp_path): s = _store(tmp_path) out = svc.record_result(s, "phq9", "SER1", "p_1", [2, 2, 1, 1, 0, 0, 0, 0, 0], now=NOW, actor="dr") assert out["total_score"] == 6 and out["interpretation"] res = svc.patient_results(s, "SER1", "p_1") assert len(res) == 1 and res[0]["result"]["total_score"] == 6 assert res[0]["result"]["answers"][0] == 2 # PII chiffrée au repos : le blob brut ne contient pas l'interprétation en clair raw = s._db.execute("SELECT result_enc FROM questionnaire_results").fetchone()["result_enc"] assert isinstance(raw, (bytes, memoryview)) and b"interpretation" not in bytes(raw)