fix(paths): de-absolute truths — REPO_ROOT placeholder normalization — dichotomy wave
The frozen corpus recorded the FREEZE-TIME checkout's absolute paths
(repo_root -> /mnt/workdrive/rune-wave-bd, crate_dir ->
/mnt/workdrive/rune-wave-bd/src/rust/<name>), so the battery failed in
every other checkout (6 subtests). Same law applied backward in repair:
absolute paths must never enter frozen truth.
- gen_paths_truth.py: derivation rows frozen REPO-RELATIVE
({REPO_ROOT}, {REPO_ROOT}/src/rust/<name>).
- truth_test.go: expandExpect substitutes the CURRENT root at replay
time and FAILS any derivation row that carries a raw absolute path
(the law is now self-enforcing).
- tests/test_paths_port.py: oracle replay substitutes identically +
asserts the placeholder law on the corpus itself; shape test updated
for the paths.go/phaseb.go split.
Verified: gofmt/vet/go test green in THIS worktree AND from a scratch
checkout at a different root (placeholder substitution proof); pytest
4/4, ruff clean.
This commit is contained in:
1 parent
3b89972227
commit
19a0638abd
4 files changed
+78
-20
No files matched your search
@@ -9,7 +9,15 @@ SET (override), since env-reading is a branch.
|
||||
|
||||
HOME is ALWAYS frozen to a concrete value per row: expanduser-bearing
|
||||
defaults ($HOME/.rune) must replay byte-stably in Go, which has no
|
||||
pwd-module fallback for an unset HOME. Output: src/go/paths/truth.json
|
||||
pwd-module fallback for an unset HOME.
|
||||
|
||||
MACHINE-BOUND LAW (no absolute paths in frozen truth): outputs derived
|
||||
from the FREEZE-TIME repo root (repo_root, crate_dir) are recorded as
|
||||
REPO-RELATIVE paths ("{REPO_ROOT}" for the root itself,
|
||||
"{REPO_ROOT}/src/rust/<name>" for crates). Replay sides substitute the
|
||||
placeholder with their CURRENT repo root before comparing. Everything
|
||||
else (env overrides, compile-time defaults) is already absolute-safe.
|
||||
Output: src/go/paths/truth.json
|
||||
"""
|
||||
from __future__ import annotations
|
||||
|
||||
@@ -37,13 +45,18 @@ def case(fn: str, name: str, args: dict, env: dict):
|
||||
# HOME always concrete (see module docstring).
|
||||
if frozen_env["HOME"] is None:
|
||||
frozen_env["HOME"] = os.environ.get("HOME")
|
||||
# Neutralize the freeze-time checkout: the oracle's repo_root is a
|
||||
# machine-bound absolute path; the corpus records it REPO-RELATIVE.
|
||||
freeze_root = paths.repo_root()
|
||||
saved = {k: os.environ.pop(k, None) for k in ENV_KEYS}
|
||||
try:
|
||||
os.environ.update({k: v for k, v in frozen_env.items() if v is not None})
|
||||
if fn == "repo_root":
|
||||
expect = paths.repo_root()
|
||||
expect = "{REPO_ROOT}"
|
||||
elif fn == "crate_dir":
|
||||
expect = paths.crate_dir(**copy.deepcopy(args))
|
||||
full = paths.crate_dir(**copy.deepcopy(args))
|
||||
assert full.startswith(freeze_root + "/"), full
|
||||
expect = "{REPO_ROOT}" + full[len(freeze_root):]
|
||||
elif fn == "deploy_root":
|
||||
expect = paths.deploy_root()
|
||||
elif fn == "rune_home":
|
||||
@@ -100,9 +113,11 @@ doc = {
|
||||
"frozen_ts": "2026-10-13T06:15:00Z",
|
||||
"generator": "scripts/gen_paths_truth.py",
|
||||
"note": "HOME is frozen per row so expanduser-bearing defaults "
|
||||
"(rune_home) replay byte-stably in both languages; the Go "
|
||||
"battery sets the row env verbatim and compares against the "
|
||||
"frozen oracle output.",
|
||||
"(rune_home) replay byte-stably in both languages; "
|
||||
"freeze-time repo-root outputs are recorded REPO-RELATIVE "
|
||||
"({REPO_ROOT} placeholder) — replay sides substitute their "
|
||||
"CURRENT root. The Go battery sets the row env verbatim and "
|
||||
"compares against the substituted oracle output.",
|
||||
"cases": cases,
|
||||
}
|
||||
OUT.parent.mkdir(parents=True, exist_ok=True)
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
"module": "paths",
|
||||
"frozen_ts": "2026-10-13T06:15:00Z",
|
||||
"generator": "scripts/gen_paths_truth.py",
|
||||
"note": "HOME is frozen per row so expanduser-bearing defaults (rune_home) replay byte-stably in both languages; the Go battery sets the row env verbatim and compares against the frozen oracle output.",
|
||||
"note": "HOME is frozen per row so expanduser-bearing defaults (rune_home) replay byte-stably in both languages; freeze-time repo-root outputs are recorded REPO-RELATIVE ({REPO_ROOT} placeholder) \u2014 replay sides substitute their CURRENT root. The Go battery sets the row env verbatim and compares against the substituted oracle output.",
|
||||
"cases": [
|
||||
{
|
||||
"fn": "repo_root",
|
||||
@@ -15,7 +15,7 @@
|
||||
"RUNE_WR_CODE": null,
|
||||
"HOME": "/home/nick"
|
||||
},
|
||||
"expect": "/mnt/workdrive/rune-wave-bd"
|
||||
"expect": "{REPO_ROOT}"
|
||||
},
|
||||
{
|
||||
"fn": "crate_dir",
|
||||
@@ -30,7 +30,7 @@
|
||||
"RUNE_WR_CODE": null,
|
||||
"HOME": "/home/nick"
|
||||
},
|
||||
"expect": "/mnt/workdrive/rune-wave-bd/src/rust/evidence_provenance"
|
||||
"expect": "{REPO_ROOT}/src/rust/evidence_provenance"
|
||||
},
|
||||
{
|
||||
"fn": "crate_dir",
|
||||
@@ -45,7 +45,7 @@
|
||||
"RUNE_WR_CODE": null,
|
||||
"HOME": "/home/nick"
|
||||
},
|
||||
"expect": "/mnt/workdrive/rune-wave-bd/src/rust/outcome_utility"
|
||||
"expect": "{REPO_ROOT}/src/rust/outcome_utility"
|
||||
},
|
||||
{
|
||||
"fn": "crate_dir",
|
||||
@@ -60,7 +60,7 @@
|
||||
"RUNE_WR_CODE": null,
|
||||
"HOME": "/home/nick"
|
||||
},
|
||||
"expect": "/mnt/workdrive/rune-wave-bd/src/rust/memory_types"
|
||||
"expect": "{REPO_ROOT}/src/rust/memory_types"
|
||||
},
|
||||
{
|
||||
"fn": "crate_dir",
|
||||
@@ -75,7 +75,7 @@
|
||||
"RUNE_WR_CODE": null,
|
||||
"HOME": "/home/nick"
|
||||
},
|
||||
"expect": "/mnt/workdrive/rune-wave-bd/src/rust/paths"
|
||||
"expect": "{REPO_ROOT}/src/rust/paths"
|
||||
},
|
||||
{
|
||||
"fn": "crate_dir",
|
||||
@@ -90,7 +90,7 @@
|
||||
"RUNE_WR_CODE": null,
|
||||
"HOME": "/home/nick"
|
||||
},
|
||||
"expect": "/mnt/workdrive/rune-wave-bd/src/rust/a/b/c"
|
||||
"expect": "{REPO_ROOT}/src/rust/a/b/c"
|
||||
},
|
||||
{
|
||||
"fn": "deploy_root",
|
||||
|
||||
@@ -5,10 +5,16 @@ package main
|
||||
// with the env matrix frozen per row, HOME pinned) VERBATIM. Every row
|
||||
// sets its frozen env, calls the Go port, and byte-compares against the
|
||||
// frozen oracle output.
|
||||
//
|
||||
// MACHINE-BOUND LAW: repo-root-derived rows are recorded REPO-RELATIVE
|
||||
// ("{REPO_ROOT}" placeholder); expandExpect substitutes the CURRENT
|
||||
// checkout's root before comparing, so the battery passes in ANY
|
||||
// checkout. Absolute paths must never enter frozen truth.
|
||||
|
||||
import (
|
||||
"encoding/json"
|
||||
"os"
|
||||
"strings"
|
||||
"testing"
|
||||
)
|
||||
|
||||
@@ -63,6 +69,22 @@ func applyRowEnv(t *testing.T, env map[string]*string) {
|
||||
}
|
||||
}
|
||||
|
||||
// expandExpect — substitute the {REPO_ROOT} placeholder with the
|
||||
// CURRENT checkout's root (fails the test if a derivation row carries a
|
||||
// raw absolute path — that is a frozen-truth-law violation).
|
||||
func expandExpect(t *testing.T, row TruthRow) string {
|
||||
t.Helper()
|
||||
if strings.HasPrefix(row.Expect, "{REPO_ROOT}") {
|
||||
return RepoRoot() + strings.TrimPrefix(row.Expect, "{REPO_ROOT}")
|
||||
}
|
||||
if row.Fn == "repo_root" || row.Fn == "crate_dir" {
|
||||
t.Fatalf("%s (%s): frozen expect %q is a raw absolute path — "+
|
||||
"derivation rows must use the {REPO_ROOT} placeholder",
|
||||
row.Fn, row.Name, row.Expect)
|
||||
}
|
||||
return row.Expect
|
||||
}
|
||||
|
||||
func TestFrozenTruthReplaysVerbatim(t *testing.T) {
|
||||
doc := loadTruth(t)
|
||||
for _, row := range doc.Rows {
|
||||
@@ -86,9 +108,10 @@ func TestFrozenTruthReplaysVerbatim(t *testing.T) {
|
||||
default:
|
||||
t.Fatalf("unknown frozen fn %q", row.Fn)
|
||||
}
|
||||
if got != row.Expect {
|
||||
want := expandExpect(t, row)
|
||||
if got != want {
|
||||
t.Fatalf("%s (%s): got %q, want frozen oracle %q",
|
||||
row.Fn, row.Name, got, row.Expect)
|
||||
row.Fn, row.Name, got, want)
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
@@ -69,13 +69,30 @@ def _apply_env(env):
|
||||
os.environ[k] = v
|
||||
|
||||
|
||||
def _expand_expect(row):
|
||||
"""Substitute the {REPO_ROOT} placeholder with the CURRENT checkout's
|
||||
root (mirrors expandExpect in truth_test.go)."""
|
||||
expect = row["expect"]
|
||||
if expect.startswith("{REPO_ROOT}"):
|
||||
return paths.repo_root() + expect[len("{REPO_ROOT}"):]
|
||||
if row["fn"] in ("repo_root", "crate_dir"):
|
||||
raise AssertionError(
|
||||
f"{row['name']}: frozen expect {expect!r} is a raw absolute "
|
||||
"path — derivation rows must use the {REPO_ROOT} placeholder")
|
||||
return expect
|
||||
|
||||
|
||||
def test_frozen_truth_replays_verbatim_oracle(frozen_env):
|
||||
for row in TRUTH["cases"]:
|
||||
a = copy.deepcopy(row["args"])
|
||||
_apply_env(row["env"])
|
||||
got = CALLABLES[row["fn"]](a)
|
||||
want = row["expect"]
|
||||
want = _expand_expect(row)
|
||||
assert got == want, f"{row['name']}: {got!r} != {want!r}"
|
||||
# the placeholder law itself: no derivation row may carry an absolute
|
||||
for row in TRUTH["cases"]:
|
||||
if row["fn"] in ("repo_root", "crate_dir"):
|
||||
assert row["expect"].startswith("{REPO_ROOT}"), row
|
||||
|
||||
|
||||
def test_go_battery_replays_same_corpus(frozen_env):
|
||||
@@ -88,12 +105,15 @@ def test_go_battery_replays_same_corpus(frozen_env):
|
||||
|
||||
|
||||
def test_go_module_shape_name_preserving():
|
||||
"""Every public Python symbol has a Go counterpart."""
|
||||
"""Every public Python symbol has a Go counterpart (paths.go carries
|
||||
the derivation pair + constant; phaseb.go the env resolvers)."""
|
||||
main_go = (ROOT / "src" / "go" / "paths" / "paths.go").read_text()
|
||||
for go_symbol in ("func RepoRoot(", "func CrateDir(", "func DeployRoot(",
|
||||
"func RuneHome(", "func HarnessScripts(",
|
||||
"func WaitResumeDir(", "RepoRootPath"):
|
||||
phaseb_go = (ROOT / "src" / "go" / "paths" / "phaseb.go").read_text()
|
||||
for go_symbol in ("func RepoRoot(", "func CrateDir(", "RepoRootPath"):
|
||||
assert go_symbol in main_go, f"missing Go counterpart: {go_symbol}"
|
||||
for go_symbol in ("func DeployRoot(", "func RuneHome(",
|
||||
"func HarnessScripts(", "func WaitResumeDir("):
|
||||
assert go_symbol in phaseb_go, f"missing Go counterpart: {go_symbol}"
|
||||
|
||||
|
||||
def test_corpus_covers_every_public_function_and_branch():
|
||||
|
||||
Reference in new issue
Block a user