A language x package matrix (each cell a tested snippet or "not yet"), a C# first-call test and a TypeScript first-call test that the docs link, and a pointer from the top of README.md.
Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
A write owns the record at its key when the written type declares the
record's schema id, or reads an older undeclared id of its own schema name
whole (ruling own-entry-reads-whole); every other registered type's record
is refused, in every cache, with or without a backing store
(cache-refuses-retype).
Removing a record and adding one of another type in a single batch is
staged as the held record's eviction then the add, so validators, Claim,
the store judges and the change journal see what they see staged apart
(one-batch-retype-is-eviction-then-add); Watch<old> gets Removed and
Watch<new> Added. A one-batch retype across home stores is refused by the
batch-spans rule and must be staged apart. A variant rebase changes type
exactly where a plain write may (variant-rebase-follows-plain-write).
Store kinds outside the library get one protected per-key judge
(store-kind-per-key-judge), exercised by tests/GameCult.Caching.OutsideStoreTests.
Spec variants:cut_spec:cut-write-ownership-cs.r1; reports h1-h5;
Soul s5 clears the merge (verdict variants:verdict:cut-write-ownership-cs.s5).
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
A real LiteNetLib pair on ephemeral loopback ports carries the handlers' answers to a client that decodes them with the
production schema decoder; no fixed port and no global frame provider. The delete under a schema alias and a null
decision are pinned where each is decided.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Mutation triage: removing the refusal exception's constructor body survived
because the handler threw on the uninitialized peer either way; the helper now
requires the failure to come from the peer's send, not from building the message.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Captured-bytes case in cultnet-rs error_message.rs, asserted byte-for-byte by
the C# schema contract test; the cultnet-distributed-database contract and the
Networking README state the remote write authority invariant.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
CultNetDatabaseServerOptions.RemoteWriteAuthority is asked once per received
write, after the schema resolves and before the shard does; none configured
refuses every remote write; an authority that throws refuses and is logged.
A refusal applies, publishes, logs and forwards nothing. The host's own
CultNetDatabase.ApplyPutAsync/ApplyDeleteAsync ask no remote authority.
Existing server tests whose subject is not the grant pass a test-local
granting authority.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
The package ships MessagePackAssumedFormattable(typeof(CultRecordRef<>)) as an
MSBuild AssemblyAttribute in buildTransitive, so generated resolvers defer the
ref to CultDocumentResolver. Geometry imports the targets and drops its three
per-member [MessagePackFormatter] workarounds. GeneratorConsumer is the
generator-on twin of ConsumerBuild.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
A cacheless call that writes nothing declares nothing and no written entry can claim the record, so the removal is refused and the file left as it was. Red under the Any-to-All mutant of the declared predicate in OwnsOnDisk, which owns every id when no entry is written.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
The lent-shape test omitted the old id from the passed entry, so the base code refused it for the id and not for the shape. It now lists them, making the registry's wider entry the only thing that could own the record.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
CatalogEntryLookup now takes the lent registry and answers from the written entries plus the registry's other types (descriptors whose schema id no written entry has). The registry Owns overload, the subset predicate and OwnsOnDisk's lent branch are deleted; the passed entry alone describes the written type, so a lent registry only adds claimants and can only refuse more.
Not yet built or run (verified by the job that follows).
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
The console logger repeated each line, so a raw count was 28 for 14 refusals. Names now prints the source (committed or live) and the gate counts distinct 'OLD-READER <runtime> refused <label>' lines.
Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
The console logger repeats every test's output in its summary, so the log held 28 lines for 14 refusals.
Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
A case that returned or passed early is Passed but prints no 'OLD-READER <runtime> refused' line. Each stage now requires the pinned number of those lines (14 C#, 3 Rust, 4 Python, 3 TypeScript) and fails '<stage>-refused-count' otherwise.
Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
The cacheless written test now holds on the entry passed: the claimant's compatible ids must all be listed by the written entry of its id.
CHANGELOG and WriteRecord's registry doc describe the refusal through another registered type's listed id, the condition on own drift, and the Shared caveat. Not yet built or tested here.
Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
C# stages count TRX results with outcome Passed per class and fail '<stage>-notpassed' on any other
outcome (an [Ignore]d case is NotExecuted); Python also fails on skipped=, expected failures= and
unexpected successes=. Every stage prints its passed count. The committed 1.0.60 writer vector is
compared to a recorded sha256 (the 1.0.60 writer stamps wall-clock times, so no writer stage can
reproduce its bytes).
Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
Kills the written-by-name mutant (the claimant condition compared schema names instead of ids).
Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
Owns takes a condition on the claimant's answer (mayClaim): the cache arm accepts any
claimant, the cacheless arm only one of the entries the call writes. Another registered
type's record, under its current id or an old one it lists, is refused as at 0e57bf11.
Tests pin P1a/P1e/P1f shapes, the writer's own drift under a larger registry, and that a
second same-name type in the lent registry only refuses. CHANGELOG entry for the cacheless
claimant; stale comments on the store's owns predicate and WriteDocument's registry doc fixed.
Builds not yet run when committed; verified on Yggdrasil before push.
Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
summary_of ended in a grep that exits 1 on no match; under set -e that killed the script before it named the failed stage. With the
head ref-list test red (owns-declares-only) the gate exited 1 naming nothing; it now names head-ref-list and summary-diff.
Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
The five TestCaseSource tests each run over two sources (committed, live): ten cases, plus the one OldReaderRefListProbe case. The
first run of the count check reported 10 and 1.
Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
OldReaderRefListProbe.cs is staged into the 2.0.1 tree by old-reader-refusal.sh and is not part of this tree's build; its method
lacked a closing brace at fd9bbaf4, which the gate's 2.0.1-reader stage reported.
Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
old-reader-refusal.sh pins the expected case count of each stage as a constant (C# stages from the TRX the run writes, by class; Rust,
Python and TypeScript from their own output) and fails naming '<stage>-count' on any other number, so a probe renamed out of its filter
or a skipped leaf test no longer passes with nothing run.
Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
Only StoredAt moves (Soul s1 vec2.log); the writer is deterministic (two runs, identical trees). The directory page is renamed by its new
content hash. A README says how they are made and compared.
Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
The 1.0.60 ref-list summary is taken after attach, an upsert of alpha, beta and the list reversed, and a flush, at 2.0.1 and at
head, and names records by schema id (the restamp-on-write ruling makes them equal). C2aGateWriter stamps every record with one
instant and compares the committed vectors byte for byte, the directory store as relative path and bytes with lock files left out.
The committed vectors are regenerated in the next commit, so TheCommittedVectorsAreWhatC2aWrites is red at this commit; it builds.
Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
Kills the two survivors of the claimant lookup over written entries (Named inverted, Owner dropped).
Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
ReadStore refuses a record whose schema the catalog does not publish, so the
file-level scenario the spec named cannot be built; the rule is pinned where it is decided.
Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
CultDocumentRegistry.Claimant is now the only precedence that decides which entry
reads a persisted catalog entry, static over a lookup (a registry's indexes, or the
entries a registry-less cacheless write writes). ClaimantEntry is deleted. A cacheless
WriteDocument or WriteRecord lent a registry is never more permissive than a cache
registering the same types; an unpublished id is carried, not owned, through Owns' catch.
Fixes the four Low findings of variants:verdict:cut-restamp-on-write.s2.
Not yet verified on Yggdrasil when committed.
Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
Owns is now a static rule over (declared, claimantOf): a registry supplies both from its indexes, a cacheless writer supplies its one entry, so
the hand-written cacheless lambda is deleted and a renamed entry listing the writer's id is owned by both. The schema-name check is the
claimant selection and is pinned. Variant read-whole flag pinned for rewrite, flatten and remove.
Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
Stryker found the true default and the two Wrote sets equivalent: a constructed or written record is stored under its type's declared id, so the flag is never asked. Not run at this commit.
Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
The spec's account (guess null, then a successful attach) takes two gates, not three: the guess gate is taken only for a non-null guess.
Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
The ForeignRecordTests read-only fixtures (another runtime's deck, the moving deck) had the same shape as the deck, which the
type now reads whole and owns; each gets a slot the deck lacks, so it is read only by dropping it. RestampOnWriteTests and the
successful-churn gate test are corrected from the first run. Not run at this commit.
Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
CultDocumentRegistry.Owns replaces Declares as the one answer to whether a writer may write, relabel or remove a record under a
schema id: the id is declared, or the type that reads it reads it whole (equal content hash, or compatible shapes with no persisted
slot ignored). Staging asks the declared half or CultStoredDocument.StoredSchemaReadWhole; the apply halves (single file,
directory, cacheless CultMesh) ask Owns over the durable catalog, once per distinct id. A record read only by dropping slots
stays read-only until its id is declared compatible.
Not built or run at this commit: verified on Yggdrasil at the cut's head.
Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
A cacheless write that re-enters its own store's hold now consults Cache first, so a journal's WriteDocument or WriteRecord gets the same refusal during an attach as after it (the attached text); the re-entry text no longer names an attach's pull. InStoreHold takes the store instead of its gate.
CacheBackingStore.GateTakes (internal, thread-static) counts the gates Gate takes; OneStoreCallTakesAtMostThreeGatesUnderFailingAttachChurn asserts at most three per call under failing-attach churn, which pins the stale-guess loop (M4b).
The contract and AddBackingStore say what holds: other threads may guess the tentative cache, but none runs a body against it.
Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
The folded-in writedoc case used to assert the refusal left the attach's registry in place and a later PullAll succeeded; the per-entry-point test now asserts that for every entry point.
Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>