Files
sasedev-knowledge/deltas/0.0.2/alpha.3.fix.1.md

10 KiB

Delta 0.0.2-alpha.3.fix.1 — conformité alpha.3 et REPLAN d'autonomie Knowledge

Base requise

Partir de 0.0.2-alpha.3 après application de son history réel FAIL, commit et push :

deltas/0.0.2/alpha.3.md    présent et historique
history/0.0.2/alpha.3.md   FAIL

Les deltas, histories et prompts antérieurs ne doivent pas être réécrits.

La version devient :

0.0.2-alpha.3.fix.1

Causes du fix

La gate opérateur d'alpha.3 a confirmé le comportement Git réel mais a relevé trois défauts bloquants :

  1. docs/validation/001-VALIDATION_MATRIX.md possède une ligne vide terminale rejetée par git diff --check ;
  2. crates/knowledge-git-api/unit_tests/lib.rs n'est pas au format exact attendu par rustfmt ;
  3. crates/knowledge-git-lib/tests/git_read_path.rs ne possède pas de documentation de crate et échoue sous -D missing-docs lors de Clippy.

La revue a aussi déclenché un REPLAN explicite : avant d'ajouter l'orchestration Changed / Unchanged, Knowledge doit terminer son autonomie normative après l'adoption PGR et auditer l'organisation interne de ses crates.

Scope technique du fix

Le correctif technique est volontairement minimal :

  • retirer la ligne vide terminale fautive de la matrice ;
  • appliquer le formatage rustfmt attendu au test de knowledge-git-api ;
  • ajouter une documentation de crate au test d'intégration git_read_path ;
  • conserver inchangés le backend Git, ses erreurs, son API publique et les deux scénarios d'intégration réels.

Le comportement prouvé en alpha.3 reste donc : mirror -> refresh -> résolution -> snapshot/worktree détaché -> validation/réutilisation.

REPLAN de 0.0.2

Le plan docs/plans/002-V0_0_2_GIT_SYNC_PLAN.md passe en version documentaire 7 et adopte la trajectoire suivante :

alpha.3      refresh / resolve / snapshot          FAIL initial -> fix.1
alpha.4      autonomie normative + structure crates
alpha.5      cas d'usage Changed / Unchanged
beta.1       réconciliation + revue d'horizon
rc.1         candidate stable
rel.1        fermeture stable

L'ancienne tranche alpha.4 de synchronisation devient alpha.5 sans changement de mission fonctionnelle.

Autonomie PGR enregistrée

RULES.md et le profil projet distinguent désormais explicitement :

PGR v0.1.3 = provenance de l'adoption engagée pendant 0.0.2
Knowledge   = baseline normative locale après matérialisation

Les règles sont :

  • ne pas charger/rechercher automatiquement PGR au début de chaque version, session ou tranche ;
  • ne pas faire dépendre un futur prompt de démarrage Knowledge d'une « stable PGR courante » ;
  • consulter une nouvelle version PGR uniquement lorsqu'une réévaluation/adoption PGR est explicitement inscrite au scope ;
  • lors d'une telle réévaluation, comparer la baseline locale puis classifier ADOPT / KEEP-LOCAL / OVERRIDE / DEFER ;
  • matérialiser/adopter localement uniquement les règles, templates/configurations et audits réellement nécessaires ;
  • ne pas recopier mécaniquement l'arborescence PGR lorsqu'un owner Knowledge plus adapté suffit.

Le prompt prompts/002-V0_0_2_START_PROMPT.md reste historique et inchangé : sa consultation de PGR appartenait précisément à l'adoption explicitement engagée au démarrage de 0.0.2.

Scope futur alpha.4

alpha.4 doit :

  • inventorier les owners/contrats PGR v0.1.3 réellement retenus par Knowledge ;
  • produire le mapping durable de leurs décisions et owners locaux ;
  • vérifier que gouvernance, workflow, documentation, validation, Rust/Cargo et Web nécessaires sont compréhensibles depuis Knowledge seul ;
  • adapter/matérialiser les règles, templates/configurations et audits manquants ;
  • supprimer toute dépendance documentaire obligatoire vers PGR pour le développement courant ;
  • auditer toutes les crates pour garder lib.rs comme façade/documentation/réexports et déplacer les définitions dans des modules possédant une responsabilité claire lorsque cela est justifié ;
  • examiner en priorité knowledge-git-api et knowledge-sync-api ;
  • ne pas imposer un générique api.rs si des modules reference, revision, snapshot, repository, signal, etc. expriment mieux l'ownership ;
  • ne pas découper artificiellement une petite crate sans bénéfice réel.

Cette tranche sera livrée séparément après PASS du présent fix.

Hors scope du fix

alpha.3.fix.1 ne doit pas :

  • créer docs/rules/ ou copier des owners PGR détaillés ;
  • refactorer maintenant knowledge-git-api ou knowledge-sync-api en modules supplémentaires ;
  • modifier crates/knowledge-git-api/src/, crates/knowledge-git-lib/src/ ou crates/knowledge-sync-api/ ;
  • modifier le comportement Git d'alpha.3 ;
  • introduire knowledge-app-lib, scheduler, PostgreSQL ou adapter de forge ;
  • modifier Web/ ;
  • préparer alpha.4 avant PASS opérateur du fix.

Gate opérateur

Exécuter depuis la racine du workspace après application du delta :

test "$(cat VERSION)" = '0.0.2-alpha.3.fix.1'
grep -F 'version = "0.0.2-alpha.3.fix.1"' Cargo.toml
grep -A2 '^## Statut$' history/0.0.2/alpha.3.md | grep -Fx 'FAIL'

git diff --check

python3 - <<'PY'
from pathlib import Path
import re
import tomllib

root = tomllib.loads(Path("Cargo.toml").read_text(encoding="utf-8"))
assert len(root["workspace"]["members"]) == 8

plan_path = Path("docs/plans/002-V0_0_2_GIT_SYNC_PLAN.md")
plan = plan_path.read_text(encoding="utf-8")
plan_lines = plan.splitlines()
assert plan_lines[1] == "<!-- version: 7 -->"

trajectory_start = plan_lines.index("## Trajectoire prévisionnelle")
replan_start = plan_lines.index("## Déclencheurs de REPLAN")
trajectory = plan_lines[trajectory_start + 1:replan_start]

for heading in (
    "### alpha.3 — refresh, résolution et snapshot réel",
    "### alpha.4 — autonomie normative et structure interne des crates",
    "### alpha.5 — cas d'usage de synchronisation",
    "### beta.1 — réconciliation et revue d'horizon",
    "### rc.1 — candidate stable",
    "### rel.1 — fermeture stable",
):
    assert heading in trajectory, heading

for phrase in (
    "Statut opérateur initial : **FAIL**.",
    "`v0.1.3` constitue une provenance d'adoption",
    "une réévaluation PGR explicitement engagée",
    "aucune consultation PGR automatique",
):
    assert phrase in plan, phrase

assert "une nouvelle stable PGR modifie un owner" not in plan

rules = Path("RULES.md").read_text(encoding="utf-8")
for phrase in (
    "## Provenance PGR et autonomie normative",
    "source d'adoption",
    "n'est pas une dépendance normative vivante",
    "ni un référentiel à charger automatiquement",
    "Une future version de PGR n'a aucun effet automatique sur Knowledge",
):
    assert phrase in rules, phrase
assert "baseline PGR courante" not in rules

profile = Path("docs/architecture/001-PROJECT_PROFILE.md").read_text(encoding="utf-8")
assert "source d'adoption" in profile
assert "provenance d'adoption figée" in profile
assert "ne consulte pas automatiquement le PGR courant" in profile

git_api_test = Path("crates/knowledge-git-api/unit_tests/lib.rs").read_text(encoding="utf-8")
assert 'assert_eq!(snapshot_result, Ok(crate::GitSnapshot::new(revision, std::path::PathBuf::from("/controlled/snapshot"))));' in git_api_test

integration = Path("crates/knowledge-git-lib/tests/git_read_path.rs").read_text(encoding="utf-8")
assert "//! Integration tests for the real generic Git read path using local temporary repositories." in integration
for phrase in (
    "real_local_repository_refreshes_resolves_and_materializes_revision_snapshots",
    "invalid_reference_and_dirty_existing_snapshot_are_rejected",
):
    assert phrase in integration, phrase

for path in Path(".").rglob("*.md"):
    if any(part in {".git", "node_modules", "target", "builds"} for part in path.parts):
        continue
    lines = path.read_text(encoding="utf-8").splitlines()
    assert lines[0] == f"<!-- file: {path.as_posix()} -->", path
    assert re.fullmatch(r"<!-- version: [1-9][0-9]* -->", lines[1]), path

print("Knowledge 0.0.2-alpha.3.fix.1 structural/replan audit: clean")
PY

python3 -B scripts/audit_rust_test_layout.py crates
python3 -B scripts/audit_rust_blank_lines.py crates
python3 -B scripts/audit_rust_item_spacing.py crates
python3 -B scripts/audit_rust_module_order.py crates
python3 -B scripts/audit_rust_trait_import_blocks.py crates
python3 -B scripts/audit_rust_reexport_blocks.py crates
python3 -B scripts/audit_rust_export_completeness.py --root . --summary-only

cargo fmt --all -- --check
cargo metadata --format-version 1 --no-deps > /tmp/sasedev-knowledge-0.0.2-alpha.3.fix.1-metadata.json
cargo check --workspace
cargo clippy --workspace --all-targets --all-features -- -D warnings
cargo test -p knowledge-git-api --all-targets --all-features
cargo test -p knowledge-git-lib --all-targets --all-features
cargo test -p knowledge-git-lib --test git_read_path
cargo test --workspace --all-targets --all-features

python3 - <<'PY'
import json
from pathlib import Path

metadata = json.loads(Path("/tmp/sasedev-knowledge-0.0.2-alpha.3.fix.1-metadata.json").read_text(encoding="utf-8"))
packages = {package["name"] for package in metadata["packages"]}
expected = {
    "knowledge-domain-lib",
    "knowledge-git-api",
    "knowledge-git-lib",
    "knowledge-sync-api",
    "knowledge-web-lib",
    "knowledge-pgr-server",
    "knowledge-howtos-server",
    "knowledge-snippets-server",
}
assert packages == expected, packages
assert len(metadata["workspace_members"]) == 8, metadata["workspace_members"]
print("Knowledge 0.0.2-alpha.3.fix.1 Cargo metadata audit: clean")
PY

test -f Cargo.lock
git check-ignore -q Cargo.lock
if git ls-files --error-unmatch Cargo.lock >/dev/null 2>&1; then
    echo 'Cargo.lock must remain untracked for Knowledge' >&2
    exit 1
fi

test -z "$(git diff --name-only -- Web)"
test -z "$(git diff --name-only -- crates/knowledge-sync-api)"
test -z "$(git diff --name-only -- crates/knowledge-git-api/src)"
test -z "$(git diff --name-only -- crates/knowledge-git-lib/src)"
test -z "$(git diff --name-only -- prompts)"
test ! -e docs/rules
test ! -e crates/knowledge-app-lib
test ! -e crates/knowledge-forge-gitea-lib
test ! -e crates/knowledge-store-postgres-lib

git add -A
git diff --cached --check
git status --short

Transition

Si la gate est PASS :

history alpha.3.fix.1 = PASS
-> commit/push alpha.3.fix.1
-> préparer alpha.4 uniquement ensuite

Si la gate est FAIL, produire un nouveau fix ciblé ou REPLAN uniquement si le résultat révèle un problème structurel nouveau.