fix(glyph): release-readiness — number parity, patch base, CI fail-closed, doc reconciliation - #13
Merged
Merged
Conversation
…osed, doc reconciliation Closes the external review's release blockers (reviewed at 95f868f). - Numbers: unify Python JSON-domain number typing to Go/JS via a safe-integer window in from_json_loose (integer-valued |n|<=2^53-1 -> int, else float64). Golden corpus 51/51 with 0 xfail; byte-identical across Go/Python/JS (all_impl_parity 24/24). canon_float untouched. - Patch base: Python now records/parses @base= and gains verify_patch_base / compute_base_fingerprint, standardized on the no-tabular state fingerprint (= fingerprint_loose[:16], the README invariant). The previously dormant Go TestTripleImpl_PatchParse is live and now checks Go<->Python<->JS base parity (canon.py and canon.mjs both emit baseFingerprint). _parse_path accepts the bare Go/JS path form so Python can parse their patches. - README: replace the unparseable @ops=[...] patch example with real syntax that parses identically in Py/JS/Go; correct the prose (no false JS standalone verifyPatchBase claim — JS enforces base via the GS1 cursor). - CI: remove silent `|| true` from the typechecks and the npm publish build (fail closed); add a release-meta job so a v* tag publishes only the registry whose package version matches the tag (no blind PyPI+npm fan-out). - Tests: tests/conftest.py excludes the three cross-impl scripts so `pytest tests/` is clean (no fixture errors / return-value warnings); the scripts still run and pass; stale vectors corrected to Go golden truth. - Docs: reconcile the float rule to one authoritative source (CANONICAL_FORMS §3) with the verified exp<=-5/>=6 boundary and a loose-vs-typed layer note; remove the stale "open divergence / threshold rule / known canonFloat bug" claims now that the rule is verified byte-identical. - cogs: default `go build`/`go vet` are clean; document that the cowrie require is dev-only and breaks external `go get` until cowrie is published or cogs is extracted to its own module (structural decision deferred). gitignore the AI context dumps. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
phenomenon0
force-pushed
the
release-readiness-fixes
branch
from
June 21, 2026 08:51
614fe4f to
70a9a61
Compare
Contributor
Author
Code review (high effort, recall-biased) — addressed in
|
Add a scenario-based acceptance suite that exercises every major GLYPH capability as realistic AI-workflow usage, runs each scenario identically across Go/Python/JS, applies one pass/fail evaluator with recorded evidence, and gates on a hard exit code. Harness (gauntlet/scenarios/): - gen_inputs.py -> inputs.json: single shared fixture source (same conditions) - runner.py / runner.cjs / go/cmd/gauntletrunner: per-language evidence runners (measure only; the orchestrator is the single evaluator) - gauntlet.py: runs all three, applies criteria incl. byte-for-byte cross-lang equality, writes report.json, exits non-zero on any failure Scenarios: S1 JSON bridge - S2 canonicalization - S3 fingerprint parity - S4 tabular compaction - S5 patch apply - S6 patch-base fail-closed - S7 GS1 framing + wire parity - S8 streaming firewall. First run was 6/8. Both failures were cross-language divergences where Go and JS agreed and Python was the outlier; fixed Python to match Go (source of truth): - Tabular header: emit `@tab _ rows=N cols=M [cols]` and accept it on parse (py/glyph/loose.py, py/glyph/parse.py). Python previously could not read Go/JS tabular output. - Patch @base: compute over canonicalize_loose, not the no-tabular fingerprint, matching Go/JS and LOOSE_MODE_SPEC (py/glyph/patch.py); reconcile the README invariant block accordingly. Result: 8/8. Existing suites stay green (py 444, py-gauntlet 81, go all, js 579, cross-impl parity gate all). Also lands in-progress branch work already staged in the tree: the per-language gauntlet tests (go/py/js), the JS loose-text parser (parse_loose.ts), the gauntlet web demo, and release-readiness doc updates. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Release-readiness pass that closes the external review's blockers (reviewed at
95f868f), plus a cross-language 8-scenario acceptance gauntlet that proves every major capability is byte-for-byte conformant across Go/Python/JS (see Update below). Verified across cross-language runs: Python 444 + gauntlet 81 · JS 579 · Go vet/build clean + glyph/stream pass · cross-impl parity gate (24/14/stress) green · gauntlet 8/8.Blockers closed
from_json_loose(integer-valued|n| <= 2^53-1→ int, else float64). Golden corpus 51/51, 0 xfail; byte-identical across Go/Python/JS (all_impl_parity_test.py24/24).canon_floatuntouched.@base=and gainsverify_patch_base/compute_base_fingerprint. Final basis:sha256(canonicalize_loose(state))[:16], matching Go/JS as the source of truth andLOOSE_MODE_SPEC §"Patch Base Fingerprint"(this supersedes the no-tabular basis the first commit shipped — see Update). The previously dormantTestTripleImpl_PatchParseis live and checks Go↔Python↔JS@baseparse parity;_parse_pathalso accepts the bare Go/JS path form so Python can parse their patches.@ops=[...]block with real syntax that parses identically in Py/JS/Go; corrected the prose (JS enforces base via the GS1 cursor).|| trueon the typechecks and the npm publish build; added arelease-metajob so av*tag publishes only the registry whose package version matches the tag.pytest tests/hygiene.tests/conftest.pyexcludes the three cross-impl scripts (they're__main__scripts, not pytest modules); the scripts still run and pass; stale vectors corrected to Go's golden truth.CANONICAL_FORMS §3); removed stale "open divergence / threshold rule / known canonFloat bug" claims now that the rule is verified byte-identical.Update — cross-language 8-scenario gauntlet (
a248ae6)Added a scenario-based acceptance suite under
gauntlet/scenarios/that exercises every major capability as realistic AI-workflow usage, runs each scenario identically across Go/Python/JS with one pass/fail evaluator + recorded evidence (report.json) + a hard exit-code gate.gen_inputs.py → inputs.json(single shared fixture source) ·runner.py/runner.cjs/go/cmd/gauntletrunner(per-language evidence runners, measure-only) ·gauntlet.py(orchestrator + single evaluator, byte-for-byte cross-language checks).First run was 6/8. Both failures were cross-language divergences where Go and JS agreed and Python was the outlier; fixed Python to match Go (the source of truth):
@tab _ rows=N cols=M [cols]and Python emitted the bare@tab _ [cols]and its parser rejected the Go/JS form — i.e. Python could not read Go/JS tabular output. Python now emits + parses the metadata form (py/glyph/loose.py,py/glyph/parse.py).@basebasis. Switched Python from the no-tabular fingerprint tocanonicalize_loose, matching Go/JS. This reverses the earlier "no-tabular" decision and resolves the deferred patch-base tabular-root edge item — all three now agree on Go's basis.@baseis therefore intentionally distinct from the value-identityfingerprint_loose(which remains no-tabular); the README invariant block is updated to match.Result: 8/8, with existing suites still green.
Deferred / known (not in this PR)
go get. Defaultgo build/vetare clean andgo.mod/README document the constraint, but externalgo getstill fails on the unpublishedcowrierequire. Structural fix is a follow-up: (A) park cogs toattic/+ drop the require (recommended); (B) extract cogs to its own module; (C) publish cowrie.CANONICAL_FORMS:257,318) not verified or touched; JS lacks a standaloneverifyPatchBase(Go+Py have it; JS enforces base via the GS1 cursor — covered by gauntlet S7).🤖 Generated with Claude Code