CultLib/src/GameCult.Caching.MessagePack
Repository files (latest commit first)
Filename Latest commit message Latest commit date
Meta Vens 7c4bc2bdc0 Make generated and reflective document members one rule
The generator and CultDocumentRegistry now discover members by the same
steps: most-derived declaration first, override chain collapsed to one
member, attributes read up the override chain, rejections in one order
with one text (GCC001 / InvalidOperationException).

- Accessors are named per document, so documents sharing a [CultName] or
  [CultIndex] base member no longer emit duplicate methods (CS0111).
- Duplicate [Key] slots are refused, including new-hidden fields and
  properties; a hidden persisted member with a different slot is refused.
- String [Key("x")] gets its own message instead of "has no [Key]".
- A persisted property whose set accessor is private, protected or init,
  or a readonly field, is refused instead of CS0272 in generated code.
- Overrides: MessagePack's DynamicObjectResolver reads the base
  declaration's [Key]/[IgnoreMember] (it throws "key is duplicated" for a
  re-keyed override and serializes an override marked [IgnoreMember]).
  An override that changes them is refused in both paths; an override
  that repeats or omits them is accepted and byte-pinned.
- Typed Serialize<T>/Deserialize<T> used static Options and skipped
  generated codecs and declared resolvers; deleted. CultNetDocumentBinding
  and CultMeshSnapshots route through the untyped path with their registry.

DocumentShapeSweepTests compiles each shape through the generator and
compares generated vs reflective schema id, catalog, name/index values
and payload against MessagePack's own bytes, or equal rejection text.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
2026-09-13 22:00:16 +02:00
..
CultCacheFormatterResolverAttribute.cs Own serialization options by the document's assembly 2026-09-13 21:12:53 +02:00
CultCacheMessagePack.cs Route each document type to one home store; attach hydrates; commit explicit batches 2026-09-13 17:57:58 +02:00
CultDocumentMessagePackSerialization.cs Make generated and reflective document members one rule 2026-09-13 22:00:16 +02:00
CultMessagePackSecurity.cs Own serialization options by the document's assembly 2026-09-13 21:12:53 +02:00
CultRecordRefFormatter.cs Strip doc comments from the Caching projects 2026-09-13 16:54:43 +02:00
DirectoryMessagePackBackingStore.cs Publish each hold's own changes to its own caller 2026-09-13 19:46:18 +02:00
GameCult.Caching.MessagePack.csproj Stop MessagePack's source generator flowing to consumers 2026-09-13 21:09:16 +02:00
README.md Remove alternate CultCache backing stores 2026-05-08 02:42:11 +01:00

GameCult.Caching.MessagePack

GameCult.Caching.MessagePack provides the canonical CultCache persistence format for the attribute-first GameCult.Caching stack.

Included Types

  • SingleFileMessagePackBackingStore
  • CultDocumentMessagePackSerialization
  • CultDocumentResolver
  • CultRecordRefFormatter<T>

When a project declares [CultDocument] models, wire in the GameCult.Caching.MessagePack.Generator analyzer there as well. It emits assembly-local metadata providers for the cache registry. Cult documents then serialize through explicit generated slot codecs, while the store snapshot format is written by hand against MessagePackWriter/MessagePackReader.

What It Does

  • stores whole CultCache snapshots in MessagePack
  • serializes plain attributed document payloads through explicit generated slot codecs
  • keeps explicit CultRecordRef<T> values compact on disk/wire
  • preserves the cache/store split where metadata lives outside the domain model

Example Model

using GameCult.Caching;
using MessagePack;

[CultDocument("gamecult.item_data", "gamecult.item_data.v1")]
public sealed class ItemData
{
    [Key(0)] [CultName] public string Name = string.Empty;
    [Key(1)] public int Value;
}

Typical Usage

using GameCult.Caching;
using GameCult.Caching.MessagePack;

var cache = new CultCache();
var store = new SingleFileMessagePackBackingStore("Data.msgpack");

cache.AddBackingStore(store);
await cache.PullAllBackingStoresAsync();

Notes

  • Payload bytes are MessagePack. Store metadata and schema catalogs are also persisted through hand-written MessagePack array layouts in this package.
  • The generator package now targets attributed document types instead of DatabaseEntry subclasses.
  • The raw CultNet document lane should treat these payload bytes as already blessed, not decode and re-encode them for sport.