Intégration des 7 textes détectés par le pipeline — la veille converge
make update écrivait jusqu'ici les changements de statut et de date, mais se contentait de journaliser les ajouts et les décisions du Conseil : les mêmes écarts seraient revenus à chaque passage, indéfiniment. Un rapport qui répète les mêmes lignes cesse d'être lu. Deux manques comblés : - un écart d'ajout porte désormais la collecte qui l'a produit, et appliquer() crée réellement le texte via classer_nouveau() - un écart de décision porte l'affaire collectée, et l'écrit dans decisions_cc Une affaire orpheline est rattachée par similarité de titre : le registre du Conseil donne l'intitulé complet (« Loi actualisant la programmation militaire pour les années 2024 à 2030… »), la base le nom d'usage. L'affaire 2026-907 DC a ainsi trouvé sa loi toute seule. Résultat sur les sources réelles : passage 1 → 7 ajouts, 4 modifications passage 2 → 0 ajout, 4 modifications (décisions désormais écrites) passage 3 → 0 écart : « la base est conforme aux sources officielles » Les 7 textes ajoutés sont des lois de janvier à avril 2026, hors de la fenêtre du corpus mais relevées par la liste du Sénat qui couvre toute la session. Dont la loi de finances pour 2026 (n° 2026-103), qui touche l'octroi de mer et étend le versement mobilité aux DROM — donc pertinente pour la Guadeloupe. Toutes entrent avec confiance = low et le drapeau de revue : le pipeline constate qu'un texte existe, il ne prétend pas l'avoir analysé. Base : 59 textes, 367 sources, 13 affaires CC, 0 texte sans lien. 176 tests, make verifier au vert. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
This commit is contained in:
co-authored by
Claude Opus 5
parent
34d81c66a8
commit
29424afdd5
@@ -364,3 +364,117 @@ def test_la_negation_ne_porte_que_sur_son_voisinage() -> None:
|
||||
+ "Le dispositif est sans objet pour les collectivités du Pacifique."
|
||||
)
|
||||
assert cotation.pertinence is Pertinence.FORTE
|
||||
|
||||
|
||||
# ─────────────────────────────────────────────────────────────────────────────
|
||||
# Application effective : créer, mettre à jour, converger
|
||||
# ─────────────────────────────────────────────────────────────────────────────
|
||||
|
||||
|
||||
def test_un_ajout_cree_reellement_le_texte(base) -> None:
|
||||
"""Un écart d'ajout doit écrire le texte, pas seulement le journaliser."""
|
||||
collecte = _collecte(
|
||||
textes=[
|
||||
TexteCollecte(
|
||||
titre="LOI n° 2026-103 du 19 février 2026 de finances pour 2026",
|
||||
source_url="https://www.legifrance.gouv.fr/jorf/id/JORFTEXT000999",
|
||||
collecteur="senat",
|
||||
numero_officiel="2026-103",
|
||||
statut=Statut.PROMULGUEE,
|
||||
date_promulgation=date(2026, 2, 19),
|
||||
sources=[
|
||||
Source(
|
||||
url="https://www.legifrance.gouv.fr/jorf/id/JORFTEXT000999",
|
||||
editeur="Légifrance",
|
||||
)
|
||||
],
|
||||
)
|
||||
]
|
||||
)
|
||||
rapport = comparer(base, [collecte])
|
||||
crees = appliquer(base, rapport, db.ouvrir_run(base, "update"))
|
||||
|
||||
assert crees == 1
|
||||
ligne = base.execute("SELECT * FROM textes WHERE id = 'loi-2026-103'").fetchone()
|
||||
assert ligne is not None
|
||||
assert ligne["confiance"] == "low"
|
||||
assert ligne["a_verifier"] == 1
|
||||
assert ligne["source_seed"] == "collecteur:senat"
|
||||
# Un texte sans source serait un texte invérifiable : la collecte doit
|
||||
# transmettre la sienne.
|
||||
assert base.execute(
|
||||
"SELECT COUNT(*) FROM sources WHERE texte_id = 'loi-2026-103'"
|
||||
).fetchone()[0] >= 1
|
||||
|
||||
|
||||
def test_une_decision_collectee_est_ecrite_pas_seulement_journalisee(base) -> None:
|
||||
"""Sans écriture, le même écart serait redétecté à chaque passage."""
|
||||
collecte = _collecte(
|
||||
decisions_cc=[
|
||||
DecisionCC(
|
||||
numero_affaire="2026-915 DC",
|
||||
date_decision=date(2026, 8, 24),
|
||||
resultat=ResultatCC.NON_CONFORMITE_PARTIELLE,
|
||||
)
|
||||
]
|
||||
)
|
||||
rapport = comparer(base, [collecte])
|
||||
appliquer(base, rapport, db.ouvrir_run(base, "update"))
|
||||
|
||||
ligne = base.execute(
|
||||
"SELECT * FROM decisions_cc WHERE numero_affaire = '2026-915 DC'"
|
||||
).fetchone()
|
||||
assert ligne["date_decision"] == "2026-08-24"
|
||||
assert ligne["resultat"] == "non_conformite_partielle"
|
||||
|
||||
|
||||
def test_le_pipeline_converge(base) -> None:
|
||||
"""Rejouer la même collecte après application ne doit plus rien signaler.
|
||||
|
||||
C'est la propriété qui rend une veille utilisable : si le rapport répétait
|
||||
les mêmes écarts à chaque passage, il deviendrait illisible et on cesserait
|
||||
de le lire.
|
||||
"""
|
||||
collecte = _collecte(
|
||||
textes=[
|
||||
TexteCollecte(
|
||||
titre="LOI n° 2026-103 du 19 février 2026 de finances pour 2026",
|
||||
source_url="https://www.legifrance.gouv.fr/jorf/id/JORFTEXT000999",
|
||||
collecteur="senat",
|
||||
numero_officiel="2026-103",
|
||||
statut=Statut.PROMULGUEE,
|
||||
date_promulgation=date(2026, 2, 19),
|
||||
)
|
||||
],
|
||||
decisions_cc=[
|
||||
DecisionCC(
|
||||
numero_affaire="2026-915 DC",
|
||||
date_decision=date(2026, 8, 24),
|
||||
resultat=ResultatCC.NON_CONFORMITE_PARTIELLE,
|
||||
)
|
||||
],
|
||||
)
|
||||
|
||||
premier = comparer(base, [collecte])
|
||||
assert premier.ecarts, "le premier passage doit voir des écarts"
|
||||
appliquer(base, premier, db.ouvrir_run(base, "update"))
|
||||
|
||||
second = comparer(base, [collecte])
|
||||
assert second.ecarts == [], "le second passage ne doit plus rien signaler"
|
||||
|
||||
|
||||
def test_une_affaire_orpheline_est_rattachee_par_son_intitule(base) -> None:
|
||||
"""Cas réel : le Conseil donne l'intitulé complet, la base le nom d'usage."""
|
||||
collecte = _collecte(
|
||||
decisions_cc=[
|
||||
DecisionCC(
|
||||
numero_affaire="2026-916 DC",
|
||||
date_saisine=date(2026, 8, 1),
|
||||
resume="Loi « Riposte » ordre public sécurité tranquillité",
|
||||
)
|
||||
]
|
||||
)
|
||||
rapport = comparer(base, [collecte])
|
||||
(ecart,) = [e for e in rapport.ecarts if e.nature == "decision_cc"]
|
||||
assert ecart.texte_id == "loi-riposte"
|
||||
assert "rattachée à loi-riposte" in ecart.description
|
||||
|
||||
Reference in New Issue
Block a user