Skip to content

test(dimred): audit XGBoostBridge inference and provenance contracts (M2.6) - #91

Merged
PhD-Brown merged 15 commits into
mainfrom
audit/43-dimred-xgboost-bridge
Nov 9, 2026
Merged

PhD-Brown merged 15 commits into
mainfrom
audit/43-dimred-xgboost-bridge

Conversation

@PhD-Brown

@PhD-Brown PhD-Brown commented Nov 9, 2026 •

Copy link
Copy Markdown
Owner

Refs #43 — dernière correction ciblée après la seconde revue Claude. Périmètre R1/R3/R5 et note R6 uniquement. Tests/oracles et documentation ; production inchangée, défauts #88/#89/#90 suivis séparément.

Branche audit/43-dimred-xgboost-bridge, tête 5581bb5. Checkpoint tests/runner aaa3213, puis 5581bb5 ajoute seulement matrice et deux résultats. Deux pushes avec SHA distant vérifié ; worktree propre. Base/source 18302e6, blob bridge eab849e4bb80be03a50ebc9128d2737530262358 (352 lignes).

Dernières corrections

Point Changement et contrôle
R1 Quatre tests filtrés acceptent un refus d’identité pertinent ou un succès avec features/prédictions/Z/labels/clusters exacts. Populations inchangées toujours positives. G1 exact : 102 PASS verts, 4 PASS R1/shared. Longueurs seules : 2 FAIL/2 PASS, S1/S2 toujours rejetés. G1 sur16 preuves : 9 FAIL/7 PASS, #89/#90 exposés.
R3 Domaine et cause indépendants de l’ordre des mots. Les quatre diagnostics signalés sont acceptés ; l’erreur interne d’index/insertion est rejetée, même enveloppée de mots de schéma. 24 cas isolés, exception et refus structuré ; aucun nouveau type d’exception. A06 passe102cas.
R5 Tolérance plafonnée indépendamment du résultat à8·eps(float32), float64 plus strict. Dtype seul non rejeté : float16 exact passe. Float32/64 : 102 PASS chacun. Float16 avec perte, permutations et perturbation1e-6 : 3 FAIL numériques/2 PASS dans les intégrations réelles. β/γ incorrects restent rouges.
R6 Règle écrite : une erreur interne sans rapport avec données/schéma/validité des prédictions ne doit pas être présentée comme refus scientifique pertinent. Propagation ou résultat structuré restent une décision humaine.

Matrice datée · contrôles ciblés : patches, sélections, assertions et hashes · validation locale.

Vérifications réellement exécutées

Windows/Python3.11.9, NumPy2.4.6, pandas3.1.1, sklearn1.9.1, XGBoost3.2.0, pytest8.4.2, pytest-socket0.7.0, Black24.4.2, Ruff0.5.0.

  • M2.6 python -m pytest -q tests/test_dimred_xgboost_bridge.py tests/test_dimred_xgboost_bridge_real.py -W error : 102 PASS (71 conservés +24 diagnostics isolés +7 précision).
  • Suite rapide normale et --import-mode=importlib : 518 PASS/62 exclus/7 avertissements Gaia existants chacune.
  • Phase final --proofs-ref fe25d1a... :25 exécutions ciblées avec baselines, toutes conformes, collecte identique, sites exécutés, FAIL par assertions, aucun ERROR/SKIP. Ancienne campagne complète non relancée.
  • R3 : baseline et trois faux correctifs 6 FAIL/1 PASS chacun, gardes pertinentes 7 PASS. Supplément complet : production 13 FAIL/3 PASS, contrôle combiné 16 PASS.
  • Black39fichiers, Ruff, pip check, diff check : PASS. Production/config/notebooks inchangés. Empreintes des entrées testées identiques à la tête finale ;21 JSON historiques inchangés.

CI42712064469 completed/success à 5581bb5, journal du job129483905352 lu : Linux/Python3.11.18, 515 PASS/3 SKIP Windows/62 exclus/7 warnings, cinq intégrations XGBoost PASS ; pip check, Black37 et Ruff PASS. Merge de contrôle1d9e6de, sans fusion de la PR.

Preuves durables et décisions ouvertes

Archives 0da7581, 7b32abb, fe25d1a intactes et ancêtres. Supplément16cas reconstruit explicitement depuis son ref pour les contrôles avec le helper courant. Aucune nouvelle archive nécessaire, aucun xfail/skip masquant un défaut ; FAIL ne compte pas les bugs.

Restent humains : confidence=max(proba) ou P(classe affichée), propagation ou refus structuré, politique NaN et transport des identifiants. Permutation extérieure invisible à l’API, doublons #50, façade sans Torch #21 et autres limites de provenance/entraînement/persistance inchangés. Aucune validation astrophysique, de calibration, de catalogue historique, GPU/W&B ou couverture générale.

PR Draft, non fusionnée ; R1/R3/R5 laissés ouverts. Prochaine étape : vérification courte par Claude limitée à R1, R3, R5 et la note R6, puis décision humaine. Pas de nouvelle première/seconde revue complète ni M2.7.

@PhD-Brown PhD-Brown left a comment

Copy link
Copy Markdown
Owner Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Première revue scientifique indépendante — M2.6 XGBoostBridge (Claude)

Verdict scientifique : MODIFICATIONS REQUISES. La review est enregistrée en COMMENTED parce que le compte GitHub est partagé ; ce n'est pas un événement APPROVED ni CHANGES_REQUESTED formel. La PR reste en Draft ; aucun commit, push, merge ni travail M2.7.

Références revérifiées. Tête 1d6b257f923b02e7800bd1f5dcb747ef512e8b3d (locale = distante), base 18302e68, blob du bridge eab849e4 inchangé (352 lignes), entrées de validation 68b86aa, archives 0da7581 et 7b32abb accessibles et ancêtres de la tête. Diff : 11 fichiers, uniquement audit/ et tests/, aucun changement de production, de configuration ou de notebook.

Exécuté (Linux · Python 3.11.18 · NumPy 2.4.6 · pandas 3.1.1 · sklearn 1.9.1 · XGBoost 3.2.0 · pytest 8.4.2 (venv uv installé depuis requirements/ci.txt)) :

  • M2.6 -W error : 64 PASS ; même résultat en ordre inversé, avec sys.path et sys.modules restaurés.
  • pytest -q et --import-mode=importlib : 477 PASS / 3 SKIP / 62 deselected / 7 warnings chacun.
  • Black (38 fichiers), Ruff, pip check, git diff --check : PASS.
  • CI 42625517366 : journal relu, merge ece92e8 de 1d6b257, 477/3/62, les 4 tests XGBoost réels inclus (marqueur integration non exclu par addopts).
  • Archives rejouées sous Linux : 19 FAIL / 19 PASS et 1 FAIL, identiques aux résultats de Codex.

Ce qui est solide.

  • Oracles par valeurs et IDs asymétriques, recalculés à la main : décodage G/M/F, maxima .7/.55/.8/.8/.55, masque F/G, frontières SNR et NaN.
  • Mes mutants d'identité, de schéma, de décodage et de lignes de probabilités sont tous tués.
  • Preuve #89 confirmée au niveau de la matrice reçue par le booster (R2).
  • GaussianNB réel confirmé.
  • Qualification honnête « 20 FAIL ≠ 20 bugs » ; distinction entre injections et backend réel.

Fils publiés :

  • R1 — bloquant : le bridge re-dérive une population différente de celle du vrai DimRedDataLoader. À longueur égale, 4/9 (options par défaut) et 5/9 (appel réel du NB01) prédictions sont associées au mauvais objet, sans erreur. Ce n'est pas une précondition de l'appelant. Le remède partiel « refus si les longueurs diffèrent » passe les 7 preuves #88.
  • R2 — bloquant : le test de caractérisation à 0.0 rejette le remède complet « NaN vers l'imputeur appris » admis par #89 (3 FAIL). S'y ajoutent la coïncidence médiane = moyenne de la fixture, une dépendance au lot (question ouverte) et le survivant « médiane du lot ».
  • R3 — bloquant : des correctifs interdits par #88/#90 rendent vertes 4 preuves rouges (Gaussian par confiance inventée, cardinalité de taille 7 par troncature, tenseur aplati).
  • R4 — non bloquant : chaque mutant Codex n'a été exécuté que contre un seul test. fillna(7) survit bien aux 64 cas (vérifié). Ma campagne : 12 mutants, dont 4 survivants à déclarer.
  • R5 — non bloquant : oracles de dtype trop stricts. Les conversions float64/float32 donnent 34 FAIL côté spies alors que le XGBoost réel est identique.
  • R6 — question ouverte : sémantique de confidence (maximum de ligne ou probabilité de la classe prédite) ; propagation ou refus structuré après chargement.
  • R7 — non bloquant : les intégrations réelles ne détectent pas la permutation de deux lignes de même classe.

Remarque mineure. La matrice mentionne un bridge de « 354 lignes » (l.26, _empty_result333–354) ; le blob en compte 352.

Fiabilité de la matrice. Elle est fiable pour les contrats unitaires locaux du wrapper et pour la parité technique. Elle ne l'est pas encore pour la qualification de l'identité des observations (R1) ni pour les critères de vérification des correctifs #88/#89/#90 (R2, R3).

Prochaine action. Codex corrige, sur la même branche et la même PR, les tests, preuves archivées supplémentaires, la matrice et les commentaires de #88/#89/#90 pour R1–R3, et si possible R4, R5 et R7. Ensuite, seconde revue Claude. R6 et les politiques ouvertes reviennent au responsable scientifique. Aucun remède de production n'est imposé.


Generated by Claude Code

Comment thread audit/M26_XGBOOST_BRIDGE.md Resolved
Comment thread tests/test_dimred_xgboost_bridge.py Resolved
Comment thread audit/M26_XGBOOST_BRIDGE.md Resolved
Comment thread audit/check_m26_mutations.py Resolved
Comment thread tests/test_dimred_xgboost_bridge.py Resolved
Comment thread tests/test_dimred_xgboost_bridge.py Resolved
Comment thread tests/conftest.py Resolved

@PhD-Brown PhD-Brown left a comment

Copy link
Copy Markdown
Owner Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Seconde revue scientifique indépendante — M2.6 XGBoostBridge (Claude)

Verdict scientifique : MODIFICATIONS REQUISES. La review est enregistrée en COMMENTED parce que le compte est partagé ; ce n'est pas un APPROVED ni un CHANGES_REQUESTED formel. Il reste un seul point bloquant, petit et limité aux tests (R1). La PR reste en Draft ; aucun commit, push, merge ni travail M2.7.

SHA audité.

  • Tête b3988ebd8adf6711d074d9e8b9e3ff9c2955c2c7 (locale = distante), base 18302e68, blob du bridge eab849e4 (352 lignes, inchangé).
  • Entrées testées par Codex : 15f5cc5.
  • Diff cumulé depuis main limité à audit/ et tests/ : aucune modification de production, de notebook ni de configuration.
  • Archives 0da7581, 7b32abb et fe25d1a ancêtres de la tête ; les deux anciennes ne sont touchées par aucun commit depuis 1d6b257. Aucun proofs_*.py dans la tête. Le conftest de fe25d1a est identique à celui de la tête.

Exécuté (Linux · Python 3.11.18 · NumPy 2.4.6 · pandas 3.1.1 · sklearn 1.9.1 · XGBoost 3.2.0 · pytest 8.4.2 (venv uv installé depuis requirements/ci.txt)) :

  • M2.6 -W error : 71 PASS, dont 5 XGBoost CPU réels ; même résultat en ordre inversé, avec sys.path et sys.modules restaurés.
  • pytest -q et --import-mode=importlib : 484 PASS / 3 SKIP / 62 deselected / 7 warnings chacun.
  • Black (46 fichiers), Ruff, pip check, git diff --check : PASS.
  • CI 42684088961 : journal relu, merge 6c06b89 de b3988eb, Python 3.11.18, 484/3/62, les 5 tests réels passent.
  • Archive fe25d1a rejouée : 13 FAIL / 3 PASS, conforme au manifeste.

Calculs et mutations propres à Claude.

  • β/γ recalculés en rationnels exacts (4 valeurs confirmées).
  • Populations S1/S2/S3 recalculées à la main.
  • Faux correctifs exacts de la première revue rejoués sur fe25d1a : M04, M08, M09, M11, fillna(7), moyenne d'entraînement, refus sur longueur seule, has_proba toujours faux.
  • 12 variantes sur les 71 cas verts : permutations, colonnes renommées, perturbation de 10⁻⁶, M10, float16/32/64, A03, A05, A06, G1, NaN complets, refus des lignes incomplètes.
  • Sondes du helper de refus.

Synthèse R1–R7

Fil Statut Point clé
R1 PARTIELLEMENT RÉSOLU — bloquant résiduel Preuves au vrai chargeur valides : le refus sur longueur seule ne passe plus (S1/S2 rouges). Mais 4 tests verts rejettent le refus « provenance invérifiable après filtrage interne », seul refus implémentable sans IDs, que la matrice et #88 déclarent admissible.
R2 RÉSOLU Oracle exact sur la matrice reçue par le booster ; moyenne, zéro, médiane du lot et 7 rejetés numériquement ; NaN complets et refus : 71 PASS.
R3 PARTIELLEMENT RÉSOLU (non bloquant) Les trois faux correctifs restent rouges ; contrôles positifs corrects. Le helper de refus dépend de l'ordre des mots (refus pertinents rejetés) et reste perméable aux mots-clés (bug interne accepté).
R4 RÉSOLU Portées qualifiées, JSON historiques intacts, M10 détecté, survivants vert/rouge correctement séparés.
R5 PARTIELLEMENT RÉSOLU (non bloquant) float32/64 et refus de chaînes admis ; mais la tolérance dérivée du dtype observé admet le float16 dans les oracles réels et R2.
R6 RÉSOLU (doc/neutralité) — politique OUVERTE Les deux sémantiques de confiance et les deux politiques d'erreur sont admises. Les tests du helper imposent implicitement la propagation des erreurs sans rapport : à écrire explicitement.
R7 RÉSOLU Observateur passif, oracle externe, permutation de même classe détectée numériquement (3 FAIL réels).

Limites scientifiques restantes.

  • Transport d'IDs/population ou refus : ouvert.
  • Politique NaN et colonnes absentes, avec la dépendance au lot : ouverte.
  • Sémantique de confidence et politique d'erreur : ouvertes.
  • Permutation extérieure à longueur égale invisible à l'API ; doublons de fusion (#50).
  • Aucune validation astrophysique, de calibration ou de provenance réelle ; façade #21.

Prochaine action. Codex, sur la même branche et la même PR :

  1. R1 (requis) : faire passer les 4 tests verts cités par bridge_review_contracts.invoke(c, "identity").
  2. Recommandé dans la même passe : rendre le helper insensible à l'ordre des mots (R3) ; plafonner la tolérance à float32 (R5) ; nommer la règle de propagation des erreurs sans rapport (R6).

Ensuite, une vérification ciblée par Claude, courte : il suffit de rejouer G1 et les sondes du helper ; aucune nouvelle campagne n'est nécessaire. Puis décision humaine.


Generated by Claude Code

@PhD-Brown PhD-Brown left a comment

Copy link
Copy Markdown
Owner Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Vérification scientifique finale — M2.6 XGBoostBridge (Claude)

Verdict scientifique : APPROUVER — prête pour décision humaine de fusion. La review est enregistrée en COMMENTED parce que le compte est partagé ; ce n'est pas un événement APPROVED formel. Ce verdict n'autorise aucune fusion de ma part. La PR reste en Draft ; M2.6 reste 🟡 jusqu'à une fusion réellement effectuée.

SHA audité.

  • Tête 5581bb59f1dd85bc6138bea993c069f50b887eb7 (locale = distante), base 18302e68, blob du bridge eab849e4 (352 lignes, inchangé).
  • Tests et runner à aaa3213.
  • Diff b3988eb..5581bb5 : 6 fichiers, uniquement tests/ et audit/. Aucune modification de production, de configuration, de dépendances ni de notebook depuis main.
  • Archives 0da7581, 7b32abb et fe25d1a accessibles sur GitHub et ancêtres de la tête ; ledgers historiques inchangés ; aucun fichier de preuve dans la suite verte.

Exécuté (Linux · Python 3.11.18 · NumPy 2.4.6 · pandas 3.1.1 · sklearn 1.9.1 · XGBoost 3.2.0 · pytest 8.4.2) :

  • M2.6 -W error : 102 PASS, aussi en ordre inversé, avec sys.path et sys.modules restaurés.
  • pytest -q et importlib : 515 PASS / 3 SKIP / 62 deselected / 7 warnings chacun.
  • Black (46 fichiers), Ruff, pip check, git diff --check : PASS.
  • CI 42712064469 : completed/success sur 5581bb5 (merge 1d9e6de), Python 3.11.18, 515/3/62, 5 tests réels passés.

Contrôles ciblés (copies jetables ; preuves de fe25d1a superposées au helper corrigé, ce qui est distinct du rejeu historique intégral) :

  • G1 : 102 PASS vert, 4 PASS R1/shared, 9 FAIL / 7 PASS sur les 16 preuves.
  • Refus sur longueur seule : 2 FAIL / 2 PASS (S1/S2 rouges).
  • Succès mal associé (M01) : les 4 tests R1 échouent. Refus systématique : 55 FAIL.
  • Faux correctifs nan_to_num, troncature et tenseur : 13 FAIL / 3 PASS chacun.
  • 28 sondes directes du helper conformes ; défauts internes H1/H2 rejetés.
  • float32/64 acceptés ; float16 avec perte : 3 FAIL numériques réels et 3 FAIL sur les preuves R2.
Fil Statut final
R1 RÉSOLU : refus d'identité admis, succès strictement associé, refus global rejeté, remède partiel toujours rouge
R2 RÉSOLU (seconde revue ; pas de régression : suite verte complète à 102 PASS)
R3 RÉSOLU : domaine et cause indépendants de l'ordre des mots ; heuristique bornée documentée
R4 RÉSOLU (seconde revue)
R5 RÉSOLU : tolérance plafonnée à float32, la perte float16 est détectée numériquement
R6 RÉSOLU pour la documentation et la neutralité ; la règle sur les erreurs internes est écrite ; politiques ouvertes
R7 RÉSOLU (seconde revue ; permutation de même classe toujours 3 FAIL réels)

Limites scientifiques restantes (non bloquantes, documentées).

  • Le helper de refus reste une heuristique de message : un défaut interne formulé avec un domaine et une cause peut passer.
  • Une permutation extérieure à longueur égale reste invisible pour l'API ; doublons de fusion (#50) ; façade #21.
  • Tolérances valables pour les jeux synthétiques seulement.
  • Aucune validation astrophysique, de calibration ou de provenance réelle.
  • Défauts de production #88/#89/#90 confirmés et non corrigés par cette PR, qui est une PR d'audit.

Décisions humaines ouvertes : sémantique de confidence ; propagation ou refus structuré ; politique NaN et colonnes absentes ; transport des IDs/population ou refus.

Prochaine action : décision humaine de fusion de la PR #91.


Generated by Claude Code

@PhD-Brown
PhD-Brown marked this pull request as ready for review November 9, 2026 23:46
@PhD-Brown
PhD-Brown merged commit 1e22663 into main Nov 9, 2026
1 check passed
@PhD-Brown
PhD-Brown deleted the audit/43-dimred-xgboost-bridge branch November 9, 2026 23:46
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant