coulomb-social/docs/architecture/spike-checklist.md
tegwick a79a9e6e77 Add ArchitectureBlueprint and content-plane spike checklist
Document coulomb layering (NetKingdom, Railiance, PageOps, markitect-tool),
compare thin store vs shard-wiki vs kontextual-engine, and outline asset-store
extraction from kontextual BlobStorage. Include executable spike checklist.
2026-08-12 18:38:27 +02:00

7.8 KiB
Raw Blame History

Spike checklist — content plane & assets

Field Value
Blueprint ArchitectureBlueprint.md
Goal Falsify or confirm options A/B/C and asset extraction before ADR-0003/0004
Time box Prefer ≤23 working days per major spike; stop when decision quality is enough

Scoring legend for each spike: Pass / Partial / Fail / Skip with one-line evidence.


Spike 0 — Shared page document fixture

Owner: coulomb-social
Depends on: none

  • Define one stage-1 page markdown fixture:
    • frontmatter: id, type, title, abstract, visual, space
    • body: short markdown
    • backmatter: e.g. relations or provenance stub
  • Define one space container convention (page-type vs directory).
  • Define export package layout (pages/**, assets/**, MANIFEST.json).
  • Commit fixtures under docs/space-fixtures/ or docs/architecture/fixtures/.

Pass when: fixture is stable enough that all later spikes use the same bytes.


Spike 1 — markitect-tool as structure lib

Owner: coulomb-social (+ markitect-tool if API gaps)
Depends on: Spike 0

  • From Python in coulomb (or throwaway script): parse fixture with markitect-tool public API.
  • Round-trip serialize without losing title/abstract/visual fields.
  • Validate required frontmatter fields (even minimal schema).
  • Note missing APIs (backmatter support, field maps) as markitect-tool gaps.

Pass when: coulomb can treat markitect-tool as dependency for read/write structure without shelling out to mkt for the happy path.

Fail when: only CLI works or public API cannot preserve frontmatter stably.


Spike 2 — Thin folder/git store (Option A)

Owner: coulomb-social
Depends on: Spike 01

  • Layout: spaces/<slug>/pages/<page>.md + assets/.
  • Implement throwaway PageOps: list, get, put, copy, transfer (filesystem).
  • Reindex card projection into SQLite/Postgres (title, abstract, visual path, space).
  • Export = tar/zip of tree; reimport without DB.
  • Measure: copy/transfer LOC and failure modes (broken links, name collision).

Pass when: stage-1 verbs work on files alone; export/import demonstrated.

Decision input: Is A enough for 36 months without federation?


Spike 3 — shard-wiki thin slice (Option B)

Owner: coulomb-social + shard-wiki
Depends on: Spike 0

  • Boot one InformationSpace with single FolderAdapter or native engine shard.
  • Ingest/edit stage-1 page; read via headless API (no UI).
  • Implement or map: list, get, put; prototype copy/transfer (engine op or app-level).
  • Attach fake Actor from static OIDC-like subject; confirm authz hooks exist or gap list.
  • Document API surface coulomb would depend on (count endpoints/concepts).
  • Stress “structure tax”: can card UI ignore federation/overlays entirely?

Pass when: thin slice delivers page CRUD without coulomb importing federation UX concepts.

Fail when: product code must understand multi-shard resolution for basic CRUD.

Decision input: structure surface area vs future multi-shard value.


Spike 4 — kontextual-engine page + markdown SoR (Option C)

Owner: coulomb-social + kontextual-engine
Depends on: Spike 01

  • Create KnowledgeAsset for stage-1 page; store source representation as markdown bytes (BlobStorage).
  • Put title/abstract/visual in metadata and/or inside markdown frontmatter (document which is authoritative for export).
  • Get content stream; reconstruct .md file bit-identical (or document lossiness).
  • Run markitect-tool adapter on stored markdown (existing boundary tests as reference).
  • Prototype copy = new asset + blob refs; transfer = metadata/relationship change to space context entity.
  • Export package: write assets + markdown to filesystem from engine API.

Pass when: user-visible export is clean markdown+assets; engine IDs are additive not mandatory for reuse.

Fail when: content is only queryable as opaque registry rows without faithful markdown export.

Decision input: governance/lineage value vs stage-1 complexity.


Spike 5 — NetKingdom / PolicyGateway wiring

Owner: coulomb + kontextual (and/or flex-auth)
Depends on: Spike 3 or 4

  • Map live or mocked OIDC claims → Actor(external_ref=issuer|sub, groups=...).
  • Implement deny-by-default PolicyGateway stub that allows only same-tenant resource metadata.
  • Optional: call flex-auth check with coulomb vocabulary (if service available).
  • Prove fail-closed: missing policy → no content bytes.
  • Document gap list for production adapter ownership.

Pass when: written design + failing/passing test for cross-tenant deny.

Fail when: only AllowAll can run the stack.


Spike 6 — Asset / Visual path

Owner: coulomb (+ kontextual or extracted store)
Depends on: Spike 2 or 4

  • Store a cover image via content-addressed put; reference from page frontmatter visual: sha256:… or asset:….
  • Serve image for card UI (signed URL, app proxy, or static mount — pick one).
  • GC/unreferenced dry-run once.
  • Compare effort: in-process kontextual BlobStorage vs copy port to shared package.

Pass when: card shows visual without storing image bytes in Postgres.

Decision input for extraction: is a second consumer ready? If no → keep in kontextual for now.


Spike 7 — Asset-store extraction feasibility

Owner: platform / kontextual
Depends on: Spike 6

  • Inventory kontextual BlobStorage + adapters (fs/s3/memory) public surface.
  • Inventory markitect-main markitect/assets/ for ideas only (dedupe, packaging); do not port wholesale.
  • Draft package name + repo boundary: bytes only vs registry.
  • Estimate extraction PR: move port+adapters, leave KnowledgeAsset in kontextual.
  • List consumers: coulomb, kontextual, shard-wiki (optional).

Pass when: one-page extraction proposal with “extract now / later / never” recommendation.

Default bias: later until two consumers need it.


Spike 8 — Cross-option decision workshop

Owner: founder + implementers
Depends on: Spikes 16 results

  • Fill scorecard (below).
  • Choose primary content plane for stage 1 + migration path.
  • Choose asset strategy (in-kontextual vs extract vs folder-only).
  • File ADR-0003 (page model + SoR) and ADR-0004 (content plane).
  • Update docs/capability/model-v0.yaml feature wording if PageOps replaces Forgejo-centric features.

Scorecard (15, higher better)

Criterion A thin store B shard-wiki C kontextual
Markdown export fidelity
Stage-1 speed
Structure tax (inverse)
Copy/transfer naturalness
Visual/blob readiness
NetKingdom/authz fit
Multi-shard / federation later
Multi-format / ECM later
Railiance operability
Aligns with fleet layers
Total

Suggested order

0 fixture → 1 markitect → 2 thin store (always, baseline)
                ├→ 3 shard-wiki thin
                └→ 4 kontextual page+blob
         → 5 authz on winner(s)
         → 6 visual
         → 7 extraction feasibility
         → 8 decision / ADRs

Spike 2 is the control experiment: even if B or C wins, A defines the export contract users feel.


Exit criteria for this checklist

Stop spiking when:

  1. One primary content plane is chosen for stage 1 with explicit residuals, and
  2. Asset strategy is chosen (where Visual bytes live), and
  3. NetKingdom policy gap is owned (who implements PolicyGateway adapter), and
  4. ADR-0003/0004 drafts exist or are scheduled.