Lane F R26 (v5.0-beta): the manifest consumed, the tolerance retired — tag HELD on the mint-id rule
EVERY CRATE IS DIFFERENT, and F measured it rather than taking G's 15/15 on trust — from the indexes of record, not by entering one lucky shop: 15 keyed crates, 105 pairs, 0 sharing a title; 0 crates overlap the generic v2 pack; 0 ids reused across crates (G's sku fix holds at scale — the R24 vacuity dead at the source, not papered over in F's gate). 4 crates in Red Hill + 11 in Newtown = the manifest's 15 exactly, and the manifest lists nothing not on disk. SOURCING, NOT TIER — C was right and the gate follows C. `tier` is the charter's ladder rung and a mint atlas is ALSO rung 1: still a file, still offline, still deterministic. What differs is where the stock came from. 15/15 indexes declare sourcing, every one agrees with the manifest, a mint crate can never report as real, and the gate PRINTS it per room — provenance a human never reads isn't doing anything (R24's licence lesson, one round on). THE 404 TOLERANCE IS DELETED, NOT TUNED. R24 probed every keyed shop and ate a 404 per atlas-less one; F's smoke could only cope by NAMING them, and a tolerance is a confession. F filed the real fix as a contract ask rather than inventing it; G built the manifest; F now consumes it — the shell asks for nothing unlisted. Zero 404s because nothing absent gets asked for, not because the gate stopped looking. AND DELETING IT IMMEDIATELY CAUGHT A LEFTOVER: F had wired the boot preload but left a second blind probe at the door, 404ing on every keyed-but-unfetchable shop. While the gate said "8 probes, expected", a ninth was invisible too. A named exception starts protecting new bugs the moment the real fix exists. F's beta gate GREEN: distinctness · sourcing (real + mint rooms) · soft fall silent · ZERO 404s · 0 console errors, no attribution exceptions. Selfcheck ALL GREEN 156,212/156,212. TAG HELD — atlas-QA FAIL, 14 errors, and it is not the product. E's SLOT_ID_PREFIX = "sku_" (validate_atlas.py:73) applies to every pack; E reads `sourcing` at :178 but the slot-id check is sourcing-blind. All 14 mint crates fail; the real crate passes. A mint crate HAS no POS sku — it was never in that shop's till — so the rule demands what cannot exist, the same shape as R24's sweep demanding a cafe carry a godverseShopId. F measured the rule's intent and it holds: mint_<dealgod listing id>, non-positional, sorted by it, seeded bake, 0 ids reused across all 15 crates. Only the literal prefix fails. And G refused to go green the easy way for the best reason — F's own R24 collision grown up: a POS sku and a dealgod listing id are different id spaces, and filing one under `sku_` recreates that bug INSIDE the economy, where tier-2's sold-means-gone looks up POS skus. R24's collision entered the wrong shop; the same collision in the money layer sells the wrong record. F did not fix E's one line: E's file, C's contract, C's call as its author (the principle Fable ratified when C overruled `tier`) — and F is the party that benefits, since that line is the only thing between F and the tag. Cost of waiting: one line. Cost of F being quietly wrong: a gate that green-lights id-space collisions in the layer that moves money. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
parent
a9a5ef05d8
commit
528829eeba
@ -4,6 +4,35 @@
|
||||
|
||||
---
|
||||
|
||||
## Round 26 (v5.0-beta — EVERY CRATE DIFFERENT) — F: the manifest consumed, the tolerance retired
|
||||
|
||||
**Every crate is different, and F measured it rather than taking G's word.** Not by entering one lucky
|
||||
shop — from the indexes of record: **15 keyed crates, 105 pairs, 0 sharing a title**; **0 crates overlap
|
||||
the generic v2 pack**; **0 ids reused across crates** (G's sku fix holds at scale — the R24 vacuity dead
|
||||
at the source, not papered over in F's gate). 4 crates in Red Hill + 11 in Newtown = the manifest's 15
|
||||
exactly, and the manifest lists nothing that isn't on disk.
|
||||
|
||||
**Sourcing, not tier — C was right.** `tier` is the charter's ladder rung, and a mint atlas is *also* rung
|
||||
1: still a file, still offline, still deterministic. What differs is where the stock came from, which is
|
||||
`sourcing: real|mint`. E built to C's contract over the brief on the principle that the contract's author
|
||||
owns the contract's shape. F's gate asserts it: 15/15 declare sourcing, every index agrees with the
|
||||
manifest, **a mint crate can never report as real**, and the gate PRINTS it per room — provenance a human
|
||||
never reads isn't doing anything (the R24 licence lesson, one round on).
|
||||
|
||||
**The 404 tolerance is deleted, not tuned.** R24 probed every keyed shop and ate a 404 per atlas-less one;
|
||||
F's smoke could only cope by *naming* them — and a tolerance is a confession. F filed the real fix as a
|
||||
contract ask instead of inventing it; G built the manifest; **F now consumes it**, and the shell asks for
|
||||
nothing that isn't listed. Zero 404s because nothing absent gets asked for, not because the gate stopped
|
||||
looking. **And deleting the tolerance immediately caught a leftover**: F had wired the *boot* preload but
|
||||
left a second blind probe at the *door*, which 404'd on every keyed-but-unfetchable shop. While the gate
|
||||
said "8 probes, expected", a ninth would have been invisible too. A named exception protects new bugs the
|
||||
moment the real fix exists.
|
||||
|
||||
**Gate: `flags_check` GREEN** — distinctness · sourcing (real + mint rooms) · soft fall silent · **ZERO
|
||||
404s** · **0 console errors, no attribution exceptions**. Full record: `LANE_F_NOTES` §26.
|
||||
|
||||
---
|
||||
|
||||
## Round 24 (v5.0-alpha — THE ALPHA COMPLETION) — **the crate WALKS; F held the tag on A's gate**
|
||||
|
||||
**THE CRATE WALKS.** Boot `redhill_godverse`, walk down Musgrave Road into **Monster Robot Party**,
|
||||
|
||||
@ -1112,3 +1112,93 @@ the cache's shop entries, A+G) so the shell preloads exactly the shops that have
|
||||
mean a genuinely missing file, which is what fail-soft is *for*. **Filed as a contract ask, not
|
||||
invented.** Until it lands, F's smoke counts the probes, names them, and fails on any other error —
|
||||
tolerance stated out loud, never blanket-ignored.
|
||||
|
||||
---
|
||||
|
||||
## 26. Round 26 — v5.0-beta EVERY CRATE DIFFERENT. F: the manifest consumed, the tolerance retired.
|
||||
|
||||
### The 404 tolerance is gone — and that is the point
|
||||
R24's wire preloaded a pack for **every keyed shop** and ate a `404` for each one with no atlas. That was
|
||||
the fail-soft law working, and it was also **console errors on every godverse boot**. F's smoke could only
|
||||
cope by *naming* the probes — and **a tolerance is a confession, not a fix**. F filed the real fix as a
|
||||
contract ask rather than inventing it: *an atlas index in G's namespace, so we never ask for what isn't
|
||||
there.* G built it. **F now consumes it** (`assets/stock_godverse/index.json` → `{godverseShopId, types[],
|
||||
sourcing}`): the shell preloads only manifest-listed `(shop, type)` pairs, and the gate asserts **ZERO
|
||||
404s with no attribution exceptions**. The 404s are gone because there is nothing absent to ask for — not
|
||||
because the gate stopped looking. Fail-soft still covers the case that matters (manifest says yes, file is
|
||||
gone), which is what fail-soft was always *for*. Fetched only when the town has keyed shops, so a plain
|
||||
town stays byte-identical: no manifest, no fetch.
|
||||
|
||||
### Distinctness — G reported 15/15; F measured it, from the indexes of record
|
||||
Not by entering one lucky shop: **105 pairs across all 15 keyed crates, 0 sharing a title**; **0 crates
|
||||
overlapping the generic v2 pack**; **0 ids reused across crates** — G's sku fix holds at scale, which is
|
||||
the R24 vacuity dead at the source rather than papered over in F's gate. 4 crates in Red Hill + 11 in
|
||||
Newtown = the manifest's 15 exactly, and the manifest lists nothing that isn't on disk.
|
||||
|
||||
### Sourcing, not tier — C was right and the gate follows C
|
||||
C ruled the brief's `tier` field wrong: `tier` is the **charter's ladder rung**, and a mint atlas is *also*
|
||||
rung 1 — a mint crate is still a deterministic file, still offline, still tier 1. What differs is where the
|
||||
stock **came from**, which is `sourcing: real|mint`. E built to C's contract over Fable's brief on the
|
||||
principle that *the contract's author is the authority for the contract's shape*, and Fable ratified it.
|
||||
F's gate asserts `sourcing`: every index declares it, every index agrees with the manifest, and **a mint
|
||||
crate can never report as real**. The gate prints it per room, because provenance a human never reads is
|
||||
provenance that isn't doing anything — the same lesson as R24's silent licence line.
|
||||
|
||||
*Note for whoever reads the runtime:* C's pack (`stockpack.js`) does **not** carry `sourcing` through —
|
||||
the gate reads it from the index of record, which is correct (the index is the artifact; B's street mark
|
||||
reads the manifest). Not a gap; recorded so nobody re-derives it.
|
||||
|
||||
### ⚠ The tolerance came out and immediately caught the leftover
|
||||
F wired the **boot** preload to the manifest, ran the gate with the 404 tolerance **deleted**, and it went
|
||||
red on exactly one 404: `stock_godverse/31/stock_opshop_index.json`. That was F's *other* probe — R24 also
|
||||
preloaded a shop's pack **on entry**, so walking into a keyed shop whose type has no atlas fired a fetch
|
||||
that could only ever 404. Removed: the door does a lookup, never a fetch. The manifest is consulted once,
|
||||
at boot, and by the time a door opens the pack is either resolved or was never going to exist.
|
||||
|
||||
The lesson is the round's, not just the bug's: **the tolerance was hiding a second instance of the very
|
||||
thing it tolerated.** While the gate said "8 atlas-probe 404s, expected", the ninth would have been
|
||||
invisible too. A named exception is still an exception; it earns its keep only until the real fix exists,
|
||||
and the moment it does, the exception must die or it starts protecting new bugs.
|
||||
|
||||
### The gate, green
|
||||
`DISTINCTNESS 15 crates / 105 pairs / 0 shared · 0 vs the generic pack · SOURCING 15/15 declared, all
|
||||
agreeing with the manifest · Monster Robot Party → sourcing REAL, 120/120 own titles, 2 own textures / 0
|
||||
generic · Presents of Mind → sourcing MINT, 16/16 own, 1 own / 0 generic · soft fall silent · ZERO 404s ·
|
||||
0 console errors, no attribution exceptions.`
|
||||
|
||||
### ⚠ THE HOLD — `v5.0-beta` NOT tagged. `atlas-QA FAIL — 14 error(s)`, and it is not the product.
|
||||
`qa.sh --strict --matrix` is **RED at the manifest validator**: E's `validate_atlas` rejects **all 14 mint
|
||||
crates** (the real crate passes). Selfcheck is ALL GREEN 156,212/156,212; F's own beta gate is GREEN;
|
||||
`flags_check` GREEN. The red is one assertion.
|
||||
|
||||
**The conflict:** `SLOT_ID_PREFIX = "sku_"` (`validate_atlas.py:73`) is a module constant applied to
|
||||
**every** pack — E reads `sourcing` at :178 but the slot-id check is **sourcing-blind**. C §7.2a's rule is
|
||||
*"derive from the source's own stable key, never position, unique across ALL packs"*, and it specifies
|
||||
`sku_<POS sku>` **"for a real-stock (godverse) pack"**. **A mint crate has no POS sku by construction** —
|
||||
it was never in that shop's till. Demanding one demands a thing that cannot exist: the same shape as R24's
|
||||
sweep demanding a cafe carry a `godverseShopId`, and as the brief's `tier` demanding a rung where the
|
||||
question was provenance.
|
||||
|
||||
**F measured the rule's INTENT, and it holds:** mint ids are `mint_<dealgod listing id>` — a real external
|
||||
key, **non-positional**, items sorted by it, the bake seeded (`random.Random(158)` over an id-ordered
|
||||
pool), and **0 ids reused across all 15 crates** (F's own pairwise measurement). Stable, unique,
|
||||
non-positional. Only the literal prefix fails.
|
||||
|
||||
**G refused to go green the easy way, and was right to** — worth recording, because it is F's own R24
|
||||
finding grown up: *"a POS sku and a dealgod listing id are different id spaces; filing dealgod listing ids
|
||||
under `sku_` recreates that bug INSIDE the economy — tier-2's sold-means-gone looks up POS skus, and
|
||||
`sku_6031122` (a dealgod id) is indistinguishable by shape from a real sku."* R24's plan-id-31 vs
|
||||
godverse-id-31 collision entered the wrong shop; the same collision in the money layer sells the wrong
|
||||
record. G caught it **before** shipping rather than after. Emitting `sku_` would have made this gate green
|
||||
and the economy wrong.
|
||||
|
||||
**Why F did not fix E's one line:** identical to R24's conflict #2, and the answer has not changed. It is
|
||||
**E's file implementing C's contract**, the question ("does §7.2a's sku rule bind a mint pack?") is **C's
|
||||
to answer as the contract's author** — the principle Fable ratified when C overruled `tier` — and **F is
|
||||
the party that benefits**, since the fix is the only thing between F and the tag it was sent to place.
|
||||
F's whole worth is that F never shades a result. Cost of waiting: one line. Cost of F being quietly wrong:
|
||||
a gate that green-lights id-space collisions in the layer that moves money.
|
||||
|
||||
**The fix (C rules, E lands it, one line):** gate `SLOT_ID_PREFIX` on `sourcing == 'real'`; for `mint`,
|
||||
assert `mint_`-prefixed + non-positional + unique — which F has already measured true. Then F re-gates
|
||||
and tags. **Everything else for the beta is done and green.**
|
||||
|
||||
@ -1004,100 +1004,143 @@ def smoke_gigs(p):
|
||||
|
||||
|
||||
GODVERSE_TOWN = 'redhill_godverse'
|
||||
GODVERSE_SHOP = 3962749 # Monster Robot Party, 147 Musgrave Rd, Red Hill QLD — the real shop
|
||||
GODVERSE_SHOP = 3962749 # Monster Robot Party, 147 Musgrave Rd, Red Hill QLD — the one REAL crate
|
||||
GODVERSE_BASE = f'assets/stock_godverse/{GODVERSE_SHOP}/'
|
||||
STOCK_MANIFEST = 'assets/stock_godverse/index.json'
|
||||
|
||||
|
||||
def smoke_real_crate(p):
|
||||
"""R24 — THE REAL CRATE, gated so it cannot pass without touching its subject (the vacuous-gate law).
|
||||
"""R26 — THE BETA GATE: every crate different, sourcing visible, and NOT ONE 404.
|
||||
|
||||
R23's #7a would have gone green on "real covers render" while the room held the generic v2 pack and
|
||||
stock_godverse/ was never fetched once. R24's brief then specified id equality — which ALSO cannot
|
||||
discriminate, because both packs number items positionally (rec_0000…), so all 120 of the atlas's ids
|
||||
are generic-pack ids too. Presence proves nothing; slot numbers prove nothing. This smoke asserts the
|
||||
two things a wrong pack cannot fake:
|
||||
1. TITLE equality — the room's pack titles are the atlas's (0 of them exist in the generic pack).
|
||||
2. TEXTURE provenance — the URL the GPU samples IS the shop's atlas file.
|
||||
Plus the rungs either side: a keyed shop with no atlas falls SOFT to parody, and a plain town is
|
||||
untouched. Subject absent (no town/atlas) ⇒ explicit SKIP with the reason, never a quiet pass."""
|
||||
head(f'SMOKE: the real crate (R24 — {GODVERSE_TOWN} · Monster Robot Party · per-shop atlas identity)')
|
||||
The lineage of this gate is the epoch's whole argument. R23's #7a would have gone green on "real
|
||||
covers render" while the room held the generic v2 pack. R24's brief then said assert id equality —
|
||||
which also couldn't discriminate, because both packs numbered items positionally and every atlas id
|
||||
was a generic-pack id too. What survives is what a wrong pack cannot fake: TITLES only this crate
|
||||
has, and the TEXTURE URL the GPU actually samples.
|
||||
|
||||
R26 adds the two beta claims. DISTINCTNESS: 15 keyed crates, pairwise title-disjoint — asserted
|
||||
across the indexes of record, so it cannot pass by entering one lucky shop. SOURCING (C's §7.2b,
|
||||
which correctly overruled the brief's `tier`): every index declares real|mint, a mint crate can
|
||||
never report as real, and the gate PRINTS it.
|
||||
|
||||
And the 404s are gone for the right reason. R24 probed every keyed shop and ate a 404 for each one
|
||||
with no atlas; F's smoke could only tolerate that by naming it — a tolerance is a confession. G's
|
||||
manifest now says which (shop, type) pairs exist, so the shell asks for nothing else. ZERO console
|
||||
errors, NO attribution exceptions. Subject absent ⇒ SKIP with the reason, never a quiet pass."""
|
||||
head(f'SMOKE: the beta crate gate (R26 — 15 crates distinct · sourcing · zero 404s · {GODVERSE_TOWN})')
|
||||
b, pg, errs = new_page(p)
|
||||
missing = [] # atlas probes that 404 — the fail-soft path, counted not hand-waved
|
||||
pg.on('response', lambda r: missing.append(r.url) if (r.status == 404 and 'stock_godverse/' in r.url) else None)
|
||||
four04 = []
|
||||
pg.on('response', lambda r: four04.append(r.url) if r.status == 404 else None)
|
||||
try:
|
||||
pg.goto(f'{HOST}/assets/towns/{GODVERSE_TOWN}.json')
|
||||
if 'godverse+osm' not in pg.content():
|
||||
print(f'· SKIP: {GODVERSE_TOWN} cache absent or not godverse+osm — subject absent, nothing asserted (Lane G/E)')
|
||||
return
|
||||
pg.goto(f'{HOST}/{STOCK_MANIFEST}')
|
||||
if 'godverseShopId' not in pg.content():
|
||||
print('· SKIP: no atlas manifest — subject absent, nothing asserted (Lane G)'); return
|
||||
boot(pg, f'plansrc=osm&town={GODVERSE_TOWN}&stock=real&dig=1')
|
||||
res = pg.evaluate("""async ({shop, base}) => {
|
||||
res = pg.evaluate("""async ({manifest, real, base}) => {
|
||||
const D = window.DBG, P = window.PROCITY;
|
||||
const idxR = await fetch(base + 'stock_record_index.json');
|
||||
if (!idxR.ok) return { skip: 'atlas absent for ' + shop };
|
||||
const atlas = new Set(((await idxR.json()).items || []).map(i => i.title));
|
||||
const town = new Set((((await (await fetch('assets/models/stock_record_index.json')).json()).items) || [])
|
||||
const man = await (await fetch(manifest)).json();
|
||||
|
||||
// ── DISTINCTNESS across the indexes of record (not just the shop we walk into) ──
|
||||
const crates = [];
|
||||
for (const sh of (man.shops || [])) for (const t of (sh.types || [])) {
|
||||
const u = `assets/stock_godverse/${sh.godverseShopId}/stock_${t}_index.json`;
|
||||
const r = await fetch(u);
|
||||
if (!r.ok) return { fail: `manifest lists ${u} but it 404s` };
|
||||
const idx = await r.json();
|
||||
crates.push({ id: sh.godverseShopId, type: t, manSourcing: sh.sourcing,
|
||||
sourcing: idx.sourcing || null,
|
||||
titles: (idx.items || []).map(i => i.title) });
|
||||
}
|
||||
const gen = {};
|
||||
for (const t of ['record', 'book', 'toy'])
|
||||
gen[t] = new Set((((await (await fetch(`assets/models/stock_${t}_index.json`)).json()).items) || [])
|
||||
.map(i => i.title));
|
||||
const entered = D.enterShop(shop);
|
||||
await new Promise(r => setTimeout(r, 1400));
|
||||
const si = D.stockInfo();
|
||||
if (!si || si.error) return { fail: 'no room: ' + JSON.stringify(si) };
|
||||
// a keyed shop with NO atlas must fall soft to parody, not inherit this crate
|
||||
const other = (P.plan.shops || []).find(s => s.godverseShopId && s.godverseShopId !== shop);
|
||||
let soft = null;
|
||||
// 'g:<id>' — NOT the bare number: plan ids and godverse ids share a numeric space, so a
|
||||
// bare id can silently enter a different shop and pass this assertion for the wrong reason.
|
||||
if (other) { D.exitShop(); await new Promise(r => setTimeout(r, 300));
|
||||
D.enterShop('g:' + other.godverseShopId); await new Promise(r => setTimeout(r, 900));
|
||||
const o = D.stockInfo();
|
||||
soft = { name: o.name, gid: o.godverseShopId, want: other.godverseShopId,
|
||||
packItems: o.packItems }; }
|
||||
return {
|
||||
entered, base: si.base, name: si.name, gid: si.godverseShopId,
|
||||
inAtlas: si.packTitles.filter(t => atlas.has(t)).length,
|
||||
inTown: si.packTitles.filter(t => town.has(t)).length,
|
||||
packItems: si.packItems,
|
||||
fromAtlasTex: si.texUrls.filter(u => u.includes(base)).length,
|
||||
fromTownTex: si.texUrls.filter(u => u.includes('assets/models/stock_')).length,
|
||||
soft,
|
||||
let shared = 0, vsGeneric = 0, noSourcing = 0, manMismatch = 0;
|
||||
for (let i = 0; i < crates.length; i++) {
|
||||
if (!crates[i].sourcing) noSourcing++;
|
||||
if (crates[i].sourcing !== crates[i].manSourcing) manMismatch++;
|
||||
if (crates[i].titles.some(t => gen[crates[i].type] && gen[crates[i].type].has(t))) vsGeneric++;
|
||||
for (let j = i + 1; j < crates.length; j++) {
|
||||
const a = new Set(crates[i].titles);
|
||||
if (crates[j].titles.some(t => a.has(t))) shared++;
|
||||
}
|
||||
}
|
||||
|
||||
// ── the ROOM binds to the right crate: one REAL, one MINT, one soft fall ──
|
||||
const byId = new Map((man.shops || []).map(s => [s.godverseShopId, s]));
|
||||
const stocked = (P.plan.shops || []).filter(s => { const e = byId.get(s.godverseShopId);
|
||||
return e && (e.types || []).includes(s.type); });
|
||||
const unfetch = (P.plan.shops || []).find(s => { if (!s.godverseShopId) return false;
|
||||
const e = byId.get(s.godverseShopId);
|
||||
return !e || !(e.types || []).includes(s.type); });
|
||||
const visit = async (shop) => {
|
||||
D.exitShop(); await new Promise(r => setTimeout(r, 250));
|
||||
D.enterShop('g:' + shop.godverseShopId); await new Promise(r => setTimeout(r, 1200));
|
||||
const si = D.stockInfo();
|
||||
const c = crates.find(c => c.id === shop.godverseShopId && c.type === shop.type);
|
||||
const own = c ? new Set(c.titles) : new Set();
|
||||
return { name: si.name, gid: si.godverseShopId, want: shop.godverseShopId, type: si.type,
|
||||
base: si.base, packItems: si.packItems,
|
||||
sourcing: c ? c.sourcing : null,
|
||||
inOwn: si.packTitles.filter(t => own.has(t)).length,
|
||||
fromOwnTex: si.texUrls.filter(u => u.includes(`stock_godverse/${shop.godverseShopId}/`)).length,
|
||||
fromGenericTex: si.texUrls.filter(u => u.includes('assets/models/stock_')).length };
|
||||
};
|
||||
}""", {'shop': GODVERSE_SHOP, 'base': GODVERSE_BASE})
|
||||
if res.get('skip'):
|
||||
print(f"· SKIP: {res['skip']} — subject absent, nothing asserted (Lane G)"); return
|
||||
const realShop = stocked.find(s => s.godverseShopId === real);
|
||||
const mintShop = stocked.find(s => (byId.get(s.godverseShopId) || {}).sourcing === 'mint');
|
||||
const out = { crates: crates.length, shared, vsGeneric, noSourcing, manMismatch,
|
||||
stocked: stocked.length,
|
||||
realRoom: realShop ? await visit(realShop) : null,
|
||||
mintRoom: mintShop ? await visit(mintShop) : null };
|
||||
if (unfetch) { D.exitShop(); await new Promise(r => setTimeout(r, 250));
|
||||
D.enterShop('g:' + unfetch.godverseShopId); await new Promise(r => setTimeout(r, 900));
|
||||
const o = D.stockInfo();
|
||||
out.softFall = { name: o.name, gid: o.godverseShopId, want: unfetch.godverseShopId,
|
||||
packItems: o.packItems }; }
|
||||
return out;
|
||||
}""", {'manifest': STOCK_MANIFEST, 'real': GODVERSE_SHOP, 'base': GODVERSE_BASE})
|
||||
if res.get('fail'):
|
||||
FAIL(f"the crate: {res['fail']}"); return
|
||||
print(f" room: {res['name']} (godverse {res['gid']}) → base {res['base']}")
|
||||
OK(f"resolves its OWN base ({res['base']})") if res['base'] == GODVERSE_BASE else FAIL(f"base is {res['base']}, expected {GODVERSE_BASE}")
|
||||
OK(f"TITLE equality: {res['inAtlas']}/{res['packItems']} titles are the shop's own atlas") \
|
||||
if (res['packItems'] > 0 and res['inAtlas'] == res['packItems']) \
|
||||
else FAIL(f"TITLE equality: only {res['inAtlas']}/{res['packItems']} titles are the shop's atlas")
|
||||
OK(f"TITLE equality: 0/{res['packItems']} titles from the generic pack — the crate is not the v2 pack") \
|
||||
if res['inTown'] == 0 \
|
||||
else FAIL(f"TITLE equality: {res['inTown']}/{res['packItems']} titles came from the GENERIC pack")
|
||||
OK(f"TEXTURE provenance: {res['fromAtlasTex']} tex from the shop's atlas, {res['fromTownTex']} generic — the pixels' own file") \
|
||||
if (res['fromAtlasTex'] > 0 and res['fromTownTex'] == 0) \
|
||||
else FAIL(f"TEXTURE provenance: {res['fromAtlasTex']} atlas / {res['fromTownTex']} generic — the GPU is sampling the wrong file")
|
||||
if res.get('soft') is not None:
|
||||
sf = res['soft']
|
||||
# the subject must BE a keyed shop, or this assertion proves nothing (it passed on an
|
||||
# unkeyed cafe first time round — a vacuous pass inside the anti-vacuous-pass gate)
|
||||
if sf.get('gid') != sf.get('want'):
|
||||
FAIL(f"soft fall: entered the WRONG shop — wanted godverse {sf.get('want')}, got {sf.get('gid')} (\"{sf['name']}\")")
|
||||
elif sf['packItems'] == 0:
|
||||
OK(f"soft fall: keyed-but-atlas-less \"{sf['name']}\" (godverse {sf['gid']}) → parody, not this crate")
|
||||
else:
|
||||
FAIL(f"soft fall BROKEN: \"{sf['name']}\" inherited {sf['packItems']} items")
|
||||
# Console errors: the ONLY tolerated ones are the atlas probes that 404 — that IS the fail-soft
|
||||
# path (a keyed shop with no atlas → null → parody), and it is counted and named here, never
|
||||
# waved through. Any other error fails. The 404 noise itself is a real cost of probing blind;
|
||||
# the fix is an atlas index in G's namespace so we never ask for what isn't there (F, R24 §24).
|
||||
probes = len(missing)
|
||||
if probes and len(errs) == probes:
|
||||
print(f' · {probes} atlas-probe 404(s) — the fail-soft path, expected; 0 other console errors')
|
||||
print(f' (cost of probing blind; fix = an atlas index so we never probe an absent shop)')
|
||||
elif errs:
|
||||
FAIL(f'the crate: {len(errs)} console error(s), {probes} explained as atlas probes; first: {errs[0][:120]}')
|
||||
else:
|
||||
print(' · 0 page errors')
|
||||
FAIL(f"beta crate gate: {res['fail']}"); return
|
||||
|
||||
# ── distinctness (independently measured; G reported 15/15) ──
|
||||
pairs = res['crates'] * (res['crates'] - 1) // 2
|
||||
OK(f"DISTINCTNESS: {res['crates']} keyed crates, {pairs} pairs, {res['shared']} sharing a title") \
|
||||
if res['shared'] == 0 else FAIL(f"DISTINCTNESS: {res['shared']} crate pair(s) share titles")
|
||||
OK(f"DISTINCTNESS: 0/{res['crates']} crates overlap the generic v2 pack") \
|
||||
if res['vsGeneric'] == 0 else FAIL(f"{res['vsGeneric']} crate(s) overlap the generic pack")
|
||||
# ── sourcing (C §7.2b — an index with no `sourcing` FAILS; the gate PRINTS it) ──
|
||||
OK(f"SOURCING: {res['crates']}/{res['crates']} indexes declare sourcing") \
|
||||
if res['noSourcing'] == 0 else FAIL(f"SOURCING: {res['noSourcing']} index(es) declare none")
|
||||
OK('SOURCING: every index agrees with the manifest') \
|
||||
if res['manMismatch'] == 0 else FAIL(f"SOURCING: {res['manMismatch']} index/manifest disagreement(s)")
|
||||
|
||||
for label, want in (('realRoom', 'real'), ('mintRoom', 'mint')):
|
||||
r = res.get(label)
|
||||
if not r:
|
||||
FAIL(f"{label}: no {want} crate reachable in {GODVERSE_TOWN}"); continue
|
||||
if r['gid'] != r['want']:
|
||||
FAIL(f"{label}: entered the WRONG shop — wanted {r['want']}, got {r['gid']}"); continue
|
||||
print(f" room: {r['name']} (godverse {r['gid']}, {r['type']}) → {r['base']} [sourcing: {r['sourcing']}]")
|
||||
OK(f" {want}: sourcing reports '{r['sourcing']}'") if r['sourcing'] == want \
|
||||
else FAIL(f" {want} crate reports sourcing '{r['sourcing']}' — a {want} crate must never report otherwise")
|
||||
OK(f" {want}: TITLE equality {r['inOwn']}/{r['packItems']} from its OWN crate") \
|
||||
if (r['packItems'] > 0 and r['inOwn'] == r['packItems']) \
|
||||
else FAIL(f" {want}: only {r['inOwn']}/{r['packItems']} titles are its own")
|
||||
OK(f" {want}: TEXTURE provenance {r['fromOwnTex']} own / {r['fromGenericTex']} generic") \
|
||||
if (r['fromOwnTex'] > 0 and r['fromGenericTex'] == 0) \
|
||||
else FAIL(f" {want}: textures {r['fromOwnTex']} own / {r['fromGenericTex']} generic — wrong file")
|
||||
|
||||
sf = res.get('softFall')
|
||||
if sf:
|
||||
if sf['gid'] != sf['want']: FAIL(f"soft fall: entered the wrong shop ({sf['gid']} != {sf['want']})")
|
||||
elif sf['packItems'] == 0: OK(f"soft fall: keyed, unfetchable type \"{sf['name']}\" → parody, silently")
|
||||
else: FAIL(f"soft fall BROKEN: \"{sf['name']}\" inherited {sf['packItems']} items")
|
||||
|
||||
# ── ZERO 404s. No exceptions. The manifest is what makes this honest. ──
|
||||
OK('ZERO 404s — the manifest means we never ask for an atlas that is not there') \
|
||||
if not four04 else FAIL(f"{len(four04)} unexpected 404(s) — the manifest should have prevented every one; first: {four04[0]}")
|
||||
OK('0 console errors (no attribution exceptions)') if not errs \
|
||||
else FAIL(f'the crate: {len(errs)} console error(s); first: {errs[0][:140]}')
|
||||
finally:
|
||||
b.close()
|
||||
|
||||
|
||||
@ -205,12 +205,25 @@ const STOCK_REAL = params.get('stock') === 'real' && !NOASSETS;
|
||||
// parody: fail-soft runs through the same path, and that is the tier-0 rung of the ladder, live.
|
||||
if (STOCK_REAL) {
|
||||
preloadStockPack('record'); preloadStockPack('book'); preloadStockPack('toy');
|
||||
const seen = new Set();
|
||||
for (const s of (plan.shops || [])) {
|
||||
const gBase = godverseBaseFor(s);
|
||||
if (!gBase || seen.has(gBase + s.type)) continue;
|
||||
seen.add(gBase + s.type);
|
||||
preloadStockPack(s.type, { base: gBase });
|
||||
// [Lane F R26 §7 — THE MANIFEST KILLS THE PROBES] R24 preloaded a pack for EVERY keyed shop and ate a
|
||||
// 404 for each one that had no atlas. That was fail-soft working, but it was also console errors on
|
||||
// every godverse boot, and F's smoke could only tolerate them by NAMING them — a tolerance is a
|
||||
// confession, not a fix. G's manifest (F's R24 finding #4/#7) says exactly which (shop, type) pairs
|
||||
// exist, so now we ask for nothing else: zero 404s because there is nothing absent to ask for, not
|
||||
// because we stopped looking. Fail-soft still covers the real case — manifest says yes, file is gone.
|
||||
// Only fetched when the town actually has keyed shops, so a plain town stays byte-identical (no fetch).
|
||||
if ((plan.shops || []).some((s) => s.godverseShopId)) {
|
||||
try {
|
||||
const r = await fetch('assets/stock_godverse/index.json', { cache: 'force-cache' });
|
||||
if (r.ok) {
|
||||
const man = await r.json();
|
||||
const byId = new Map((man.shops || []).map((s) => [s.godverseShopId, s]));
|
||||
for (const s of (plan.shops || [])) {
|
||||
const e = byId.get(s.godverseShopId);
|
||||
if (e && (e.types || []).includes(s.type)) preloadStockPack(s.type, { base: godverseBaseFor(s) });
|
||||
}
|
||||
}
|
||||
} catch (e) { /* no manifest ⇒ no per-shop packs ⇒ parody. The ladder's bottom rung, unchanged. */ }
|
||||
}
|
||||
}
|
||||
// [Lane F R8 — Lane C buy loop v0] ONE session wallet (seeded start cash) bound to the dig BUY across shops.
|
||||
|
||||
@ -15,7 +15,7 @@
|
||||
// The interior renders into its OWN dark THREE.Scene (the street scene is frozen, not disposed —
|
||||
// CITY_SPEC L3 "pause, not dispose"), so returning to the street is instant.
|
||||
|
||||
import { buildInterior, getStockPack, makeStockAdapter, preloadStockPack } from '../interiors/interiors.js';
|
||||
import { buildInterior, getStockPack, makeStockAdapter } from '../interiors/interiors.js';
|
||||
import { KeeperManager } from '../citizens/keepers.js'; // Lane D — shopkeeper behind the counter
|
||||
import { GigCrew } from '../citizens/band.js'; // Lane D — band trio + audience (R12, ?gigs=1)
|
||||
import { createDig, binSeed } from '../interiors/dig.js'; // Lane C — crate-riffle (v2, gated on ?dig=1)
|
||||
@ -206,8 +206,13 @@ export function createInteriorMode({ THREE, renderer, camera, plan, fleet = null
|
||||
// coexist instead of the per-shop pack silently inheriting the town-wide one (the R23 bug that held
|
||||
// the tag). Missing atlas → 404 → null → parody: the fail-soft law runs through the SAME path.
|
||||
// Gated on stockReal, never on the id alone: ?noassets ⇒ stockReal false ⇒ not one byte fetched.
|
||||
// [R26] NO probe here. R24 preloaded this shop's pack on entry — which meant walking into a keyed
|
||||
// shop whose type has no atlas fired a fetch that could only 404. The shell now preloads every
|
||||
// (shop, type) the manifest actually lists, at boot, so by the time a door opens the pack is either
|
||||
// resolved or was never going to exist; asking again at the door can only ask for the absent one.
|
||||
// F's own gate caught this leftover the moment the 404 tolerance came out — which is the argument
|
||||
// for taking tolerances out. Lookup only: a shop with no pack gets null → parody, silently.
|
||||
const gBase = stockReal ? godverseBaseFor(shop) : undefined;
|
||||
if (gBase) preloadStockPack(shop.type, { base: gBase }); // idempotent; re-entry is a cache hit
|
||||
currentAdapter = stockReal ? makeStockAdapter(getStockPack(shop.type, gBase)) : null;
|
||||
// [Lane F R13 THE DISTRICT] Is THIS shop the venue with a gig on right now? Per-venue query — a town has
|
||||
// 2–4 venues, each with its own latch keyed by shop id. Lane C only stamps room.audio.gigKey when we pass
|
||||
|
||||
Loading…
Reference in New Issue
Block a user