#!/usr/bin/env python3
"""Corrections PII FORT (audit Qwon 2026-06-17, 13 lacunes FORT validées Dom).

Batch A — extensions additives de regex déjà câblées dans le pipeline
``_mask_line_by_regex`` (+ ``RE_FINESS``). Fichier de test DÉDIÉ pour ne pas
entrer en collision avec la WIP hotfix sur les tests P0.

Toutes les valeurs sont FICTIVES. Chaque correction a un cas positif ET un
contrôle anti-faux-positif (ne pas sur-masquer du texte clinique générique).

#9 (FAX) et #11/#12 (NIR avec label / multiline) nécessitent un nouveau
placeholder / hook de masquage : marqués xfail (RED documenté) en attendant
le batch A-2.
"""
from __future__ import annotations

from anonymizer_core_refactored_onnx import (
    PLACEHOLDERS,
    RE_FINESS,
    _mask_line_by_regex,
    load_dictionaries,
)

CFG = load_dictionaries(None)


def _mask(line: str):
    audit: list = []
    out = _mask_line_by_regex(line, audit, 0, CFG)
    return out, audit


# --- #1 NOMS : Mlle / Mademoiselle dans le contexte personne -----------------

def test_mlle_masks_following_name():
    out, _ = _mask("Mlle DUPONT convoquée")
    assert "DUPONT" not in out


def test_mademoiselle_masks_following_name():
    out, _ = _mask("Mademoiselle Lefevre présente")
    assert "Lefevre" not in out


def test_mlle_anti_fp_generic_sentence():
    line = "La consultation est programmée demain"
    out, _ = _mask(line)
    assert out == line  # aucun titre → aucun masque


# --- #2 NOMS : "Fait par" comme contexte personne ----------------------------

def test_fait_par_masks_name():
    out, _ = _mask("Fait par MARTIN")
    assert "MARTIN" not in out


def test_fait_par_colon_masks_name():
    out, _ = _mask("Fait par : DURAND")
    assert "DURAND" not in out


# --- #3 DDN : mois abrégés ----------------------------------------------------

def test_ddn_abbreviated_month_sept():
    out, _ = _mask("Né le 19 sept. 1972")
    assert PLACEHOLDERS["DATE_NAISSANCE"] in out
    assert "1972" not in out


def test_ddn_abbreviated_month_janv():
    out, _ = _mask("Née le 3 janv. 1980")
    assert PLACEHOLDERS["DATE_NAISSANCE"] in out


def test_ddn_full_month_still_works():
    out, _ = _mask("Né le 19 septembre 1972")
    assert PLACEHOLDERS["DATE_NAISSANCE"] in out


# --- #4 DDN : labels enrichis (Naissance / DN / Nées le) ---------------------

def test_ddn_label_naissance_standalone():
    out, _ = _mask("Naissance : 19/09/1972")
    assert PLACEHOLDERS["DATE_NAISSANCE"] in out


def test_ddn_label_dn():
    out, _ = _mask("DN : 19/09/1972")
    assert PLACEHOLDERS["DATE_NAISSANCE"] in out


def test_ddn_label_nees_le():
    out, _ = _mask("Nées le 19/09/1972")
    assert PLACEHOLDERS["DATE_NAISSANCE"] in out


def test_ddn_label_date_de_naissance_still_works():
    out, _ = _mask("Date de naissance : 19/09/1972")
    assert PLACEHOLDERS["DATE_NAISSANCE"] in out


def test_ddn_anti_fp_clinical_date_preserved():
    # date clinique hors contexte naissance : NE DOIT PAS être masquée DDN
    out, _ = _mask("Intervention réalisée le 19/09/1972")
    assert PLACEHOLDERS["DATE_NAISSANCE"] not in out
    assert "19/09/1972" in out


def test_ddn_anti_fp_lieu_de_naissance_textuel():
    # "Lieu de naissance : Bordeaux" — pas une date → pas de masque DATE_NAISSANCE
    out, _ = _mask("Lieu de naissance : Bordeaux")
    assert PLACEHOLDERS["DATE_NAISSANCE"] not in out


# --- #5 FINESS Corse 2A/2B ----------------------------------------------------

def test_finess_corse_2a():
    assert RE_FINESS.search("FINESS : 2A0000001") is not None


def test_finess_corse_2b():
    assert RE_FINESS.search("N° FINESS 2B0123456") is not None


def test_finess_standard_still_matches():
    assert RE_FINESS.search("FINESS : 330056123") is not None


def test_finess_anti_fp_unlabelled_number():
    # 9 chiffres sans label FINESS ne doivent pas matcher
    assert RE_FINESS.search("Total facture 123456789 euros") is None


# --- #7 ADRESSES : types de voie supplémentaires -----------------------------

def test_adresse_villa():
    out, _ = _mask("15 villa des Nympheas")
    assert PLACEHOLDERS["ADRESSE"] in out


def test_adresse_faubourg():
    out, _ = _mask("12 faubourg Saint-Honore")
    assert PLACEHOLDERS["ADRESSE"] in out


def test_adresse_existing_rue_still_works():
    out, _ = _mask("35 rue Claude Boucher")
    assert PLACEHOLDERS["ADRESSE"] in out


# --- #10 + #13 MUTUELLE / AMC / CSS → [ADHERENT] -----------------------------

def test_adherent_mutuelle_number():
    out, _ = _mask("Mutuelle : 123456")
    assert "123456" not in out


def test_adherent_amc_number():
    out, _ = _mask("AMC : 1234567")
    assert "1234567" not in out


def test_adherent_existing_label_still_works():
    out, _ = _mask("N° adhérent : 123456789")
    assert "123456789" not in out


def test_adherent_anti_fp_short_mutuelle_name():
    # "MGEN" (4 chars) n'est pas un numéro → ne doit pas être capté comme [ADHERENT]
    out, _ = _mask("Mutuelle : MGEN")
    assert "MGEN" in out


# --- #11/#12 NIR : 13 chiffres avec label + multiline (batch A-2, RED) --------

def test_nir_13_digits_with_label():
    # implémenté en batch A-2 (RE_NIR_NO_KEY, label-ancré)
    out, _ = _mask("NIR : 2840556123456")
    assert "2840556123456" not in out


def test_nir_anti_fp_bare_13_digits_not_masked():
    # 13 chiffres SANS label NIR ne doivent jamais être masqués (anti-FP fort)
    line = "Référence dossier 2840556123456"
    out, _ = _mask(line)
    assert "2840556123456" in out


# --- #9 FAX : placeholder [FAX] (batch A-2, RED) -----------------------------

def test_fax_label_masked():
    # implémenté en batch A-2 (RE_FAX + placeholder [FAX], appliqué avant RE_TEL)
    out, _ = _mask("Fax : 05 56 00 00 00")
    assert PLACEHOLDERS["FAX"] in out
    assert "05 56 00 00 00" not in out
