reachy_mini_minder / tests /test_pii_guard.py
Boopster's picture
initial commit
af9cde9
"""Tests for the PIIGuard PII protection module."""
import pytest
from reachy_mini_conversation_app.pii_guard import PIIGuard, DEFAULT_MEDICATION_MAPPINGS
class TestPIIGuard:
"""Test PIIGuard redaction and hydration."""
def test_medication_redaction(self):
"""Test that medication names are redacted to symptom categories."""
guard = PIIGuard()
text = "I took my Topiramate this morning"
redacted, mapping = guard.redact(text)
assert "Topiramate" not in redacted
assert "migraine prevention medication" in redacted
assert mapping["migraine prevention medication"] == "Topiramate"
def test_multiple_medications(self):
"""Test redaction of multiple different medications."""
guard = PIIGuard()
text = "I take Topiramate for migraines and Aspirin for stroke prevention"
redacted, mapping = guard.redact(text)
assert "Topiramate" not in redacted
assert "Aspirin" not in redacted
assert "migraine prevention medication" in redacted
assert "blood thinner medication" in redacted
def test_name_redaction(self):
"""Test that patient/caregiver names are redacted to roles."""
guard = PIIGuard()
guard.set_patient_context(
patient_name="Elena", caregiver_name="Maya", doctor_name="Dr. Patel"
)
text = "Elena needs her medication. Maya will call Dr. Patel."
redacted, mapping = guard.redact(text)
assert "Elena" not in redacted
assert "Maya" not in redacted
assert "Dr. Patel" not in redacted
assert "the patient" in redacted
assert "the caregiver" in redacted
assert "the neurologist" in redacted
def test_hydration_restores_values(self):
"""Test that hydration restores original values."""
guard = PIIGuard()
guard.set_patient_context(patient_name="Elena", caregiver_name="Maya")
original = "Elena should take her Topiramate at 8am"
redacted, mapping = guard.redact(original)
# Simulate cloud AI response using redacted terms
ai_response = (
"the patient should take the migraine prevention medication with water"
)
hydrated = guard.hydrate(ai_response, mapping)
assert "Elena" in hydrated
assert "Topiramate" in hydrated
def test_case_insensitive_redaction(self):
"""Test that redaction works regardless of case."""
guard = PIIGuard()
text = "I took TOPIRAMATE and topiramate"
redacted, mapping = guard.redact(text)
assert "TOPIRAMATE" not in redacted
assert "topiramate" not in redacted
def test_empty_text(self):
"""Test handling of empty text."""
guard = PIIGuard()
redacted, mapping = guard.redact("")
assert redacted == ""
assert mapping == {}
hydrated = guard.hydrate("", {})
assert hydrated == ""
def test_no_pii_text(self):
"""Test text with no PII returns unchanged."""
guard = PIIGuard()
text = "Today is a beautiful day"
redacted, mapping = guard.redact(text)
assert redacted == text
assert mapping == {}
def test_register_custom_medication(self):
"""Test registering custom medication mappings."""
guard = PIIGuard()
guard.register_medication("Gabapentin", "nerve_pain", "nerve pain medication")
text = "I take Gabapentin daily"
redacted, mapping = guard.redact(text)
assert "Gabapentin" not in redacted
assert "nerve pain medication" in redacted
def test_default_mappings_loaded(self):
"""Test that default medication mappings are available."""
guard = PIIGuard()
# Check some common CADASIL medications
text = "Topiramate, Aspirin, Paracetamol, and Clopidogrel"
redacted, mapping = guard.redact(text)
# Aspirin & Clopidogrel share "blood thinner medication" key, so 3 unique labels
assert len(mapping) >= 3
class TestPIIGuardWithDatabase:
"""Test PIIGuard with database persistence."""
def test_database_mappings_loaded(self, tmp_path):
"""Test that mappings from database are loaded."""
from reachy_mini_conversation_app.database import MiniMinderDB
db_path = tmp_path / "test.db"
db = MiniMinderDB(db_path)
# Register a custom mapping in the database
db.register_medication_redaction(
"CustomMed", "custom", "custom category medication"
)
# Create PIIGuard with database
guard = PIIGuard(database=db)
text = "I take CustomMed daily"
redacted, mapping = guard.redact(text)
assert "CustomMed" not in redacted.lower()
assert "custom category medication" in redacted
db.close()