Spines are additive/separate/selectable layers: NOT project sources, spine-side edges, 'Organize by' picker¶
Angelo › zettelkasten › Phase 2: Literature Review System › Workshop tab: Reading Syllabus (learn) + claim-centric Review/Outline (write) › Organizations: project-level lenses + spines (matrix builder redesign) › Spine promotion: materialize a matrix lens into a graph (cols+rows, bulk-attach)
Type: Decision · Status: active · Created: 2026-06-25
Tags: zettelkasten,spine,promotion,graph-view,overlay,layers,organizational-principle,separation,cluster-graph,design
User requirement: building a new spine must be ADDITIVE to the cluster graph but SEPARATE, and the viewer must be able to pick which spine / organizational principle is active.
Problem found: today the composite cluster graph only excludes source/subsource/citation nodes (GraphView.tsx ~400), so a materialized apex/dimension/hub node would currently cluster in as a fake note — spines would pollute the base graph.
Decisions: (1) Keep spines OUT of project sources entirely (chosen the cleaner-separation option over flag-as-source). Promotion does NOT add_to_project the synthesis graph — this diverges from prep_structure which registers it; the shared spine.py materializer registers into a spine CATALOG instead, and the org registry already provides that catalog (orgs with state==spine + spine_ref). Composite never includes spine nodes by construction. (2) Store membership/attach edges on the SPINE side as OUTGOING cross-graph links (dim/hub -> member note) instead of note->dim, so base note files stay pristine (truly additive/separate, clean teardown on spine delete). _group_link_scopes already supports incoming/outgoing so read-back works. This reverses prep_structure's claim->dim convention for the promotion path (open question: converge extraction or keep two paths). (3) Filter key = target graph: an attach edge belongs to spine X iff its synthesis endpoint is spine_ref(X); 'show only spine X' = filter to that graph, no per-edge tagging.
View feature: an 'Organize by' selector [Semantic clusters | Tags | Source | Spine: A | Spine: B ...]. Selecting a spine loads it as an overlay (new endpoint GET .../organizations/{id}/overlay -> apex+dimensions+hubs+membership edges), recolors/groups base notes by which dim/hub they attach to in that spine, and hides other spines. A spine thus becomes a new clustering MODE — non-destructive, stackable, switchable. This view work may warrant its own phase (spans GraphView + backend overlay endpoint).
Reconcile: prep_structure refactored onto shared materializer must stop registering spines as plain sources too; validate the scribe's cross-graph attach still works (loads synthesis graph by name regardless of source registration). Captured in documents/260625_spine-promotion.md §9b + open questions.
Referenced files¶
documents/260625_spine-promotion.md@bfc8ed2coordinator/extraction.py@3119873zettelkasten/dashboard/frontend/src/components/GraphView.tsx@bfc8ed2
Source: memory entry deci-bb69e4a9.