- Couche depot_etat juste apres le socle (serveur_backup, serveur_backup_site) : l'AC, les bases et la supervision trouvent un depot qui repond quand elles naissent. - site-deployer-tout amorce d'abord la machine du cache, seule (socle, serveur_artefacts, serveur_cache_site) : aucune couche ne peut exprimer cet ordre par machine. - verifier_flux_site.py refuse le deploiement si une machine active n'a pas ses regles nftables generees ; test_verifier_flux_site.py l'eprouve. Simulation complete contre le site de TechnoLibre : aucun echec sur les neuf machines. 95 preuves (make verifier), make test passe. CHANGELOG 147. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
42 lines
1.7 KiB
Python
42 lines
1.7 KiB
Python
#!/usr/bin/env python3
|
|
"""Le deploiement du site refuse une machine sans regles nftables generees.
|
|
|
|
POURQUOI (2026-10-13). Sans `flux-genere/<machine>.nft`, `nftables_baseline` pose en silence
|
|
son gabarit generique. Le premier site construit depuis zero n'avait jamais eu `make flux`.
|
|
Sur un inventaire SYNTHETIQUE (aucun site requis) :
|
|
- toutes les machines ont leur fichier : accepte ;
|
|
- une machine sans fichier : refuse, et la nomme (temoin) ;
|
|
- une machine qui n'arme pas son pare-feu n'est pas exigee.
|
|
"""
|
|
from __future__ import annotations
|
|
|
|
import sys
|
|
import tempfile
|
|
from pathlib import Path
|
|
|
|
sys.path.insert(0, str(Path(__file__).resolve().parents[1]))
|
|
import verifier_flux_site as V # noqa: E402
|
|
|
|
|
|
def main() -> int:
|
|
with tempfile.TemporaryDirectory() as d:
|
|
a = Path(d) / "a.nft"
|
|
a.write_text("table inet filter {}\n")
|
|
inv = {"hotes_actifs": {"hosts": ["a", "b", "c"]},
|
|
"_meta": {"hostvars": {
|
|
"a": {"nftables_baseline_enabled": True, "nftables_baseline_ruleset_genere": str(a)},
|
|
"b": {"nftables_baseline_enabled": True, "nftables_baseline_ruleset_genere": str(Path(d) / "b.nft")},
|
|
"c": {"nftables_baseline_enabled": False}}}}
|
|
cas = [("une machine sans fichier", inv, ["b"]),
|
|
("toutes ont leur fichier", {**inv, "hotes_actifs": {"hosts": ["a", "c"]}}, [])]
|
|
echecs = 0
|
|
for nom, i, attendu in cas:
|
|
vu = [x.split(" :")[0] for x in V.manquants(i)]
|
|
ok = vu == attendu
|
|
echecs += not ok
|
|
print(f"{'OK ' if ok else 'ECHEC '} {nom} : {vu or 'rien a signaler'}")
|
|
return 1 if echecs else 0
|
|
|
|
|
|
if __name__ == "__main__":
|
|
sys.exit(main())
|