Sovereign Sync Architecture
Technology stack
| Component | Crate | Version | Purpose |
|---|---|---|---|
| P2P transport | iroh | 1.0.x | Encrypted QUIC connectivity, discovery, NAT traversal, relays |
| Gossip protocol | iroh-gossip | 0.101 | Topic-based broadcast to a connected peer set |
| CRDT engine | loro | 1.13.x | Snapshot, delta, version-vector, and conflict-free merge primitives |
| Domain storage | storage-provider | workspace | Local, Loro, and iroh-docs adapters plus the sync manifest |
| KBD authority | kbd-runtime | workspace | Flocked journal writes, signed events, deterministic replay, project identity |
| General sync persistence | redb | 2.x | Sovereign Sync's non-KBD state.redb store |
| MCP server | rmcp | 1.8.0 | Harness tool surface |
| HTTP server | axum | 0.8 | Loopback REST API and AG-UI SSE |
| Rust SDK | sovereign-client | 0.1.0 | REST, signed KBD command, claims, and typed SSE client |
Topic derivation and peer identity
Every paired group shares a random 256-bit secret:
topic = BLAKE3(group_secret || "sovereign-sync-v1")
The secret is created with the durable P2P identity and transferred only inside
an explicit pairing ticket. Each mode-0600 identity file also stores the iroh
secret key and an allow-list binding endpoint IDs to signing-key fingerprints.
Frames from unknown endpoints, wrong groups, signer mismatches, stale requests,
and replayed request IDs are rejected before domain import.
SyncManifest
SyncManifest is a default-deny registry. A domain is a string name plus the
storage-key prefix it owns:
pub enum PrivacyClass {
Public, // eligible for paired-peer replication
Trusted, // eligible only for explicitly trusted peers
Local, // never eligible for P2P export or import
}
pub struct SyncDomain(pub String);
pub struct DomainConfig {
pub privacy: PrivacyClass,
pub key_prefix: String,
}
Unregistered domains and Local domains both fail is_syncable(). Public
does not mean plaintext: iroh still encrypts transport. It means the content
owner has classified the payload as safe for any paired peer.
Two different convergence problems
Sovereign Sync separates:
- Replicated domain data, where Loro CRDT merge is appropriate.
- KBD command authority, where each replica journal write is atomic and the signed, grow-only Loro project document is authoritative.
KBD currently commits through one exclusive-flock journal transaction and rejects stale causal frontiers. Multi-replica convergence occurs through the project Loro document rather than an unjoined consensus configuration.
The canonical KBD runtime lives outside the repository under the platform application-data root:
<data-root>/prometheus/kbd/projects/<project-id>/
The repository’s .prometheus/project.json supplies the immutable project ID.
Files such as .kbd-orchestrator/current-waypoint.json, position.json, and
phase progress.json are compatibility projections or authored workflow
artifacts; they are not a second command authority.
CRDT merge
Domains use Loro for conflict-free snapshots and deltas:
doc.export(ExportMode::Snapshot)?
doc.export(ExportMode::Updates {
from: Cow::Owned(version_vector),
})?
doc.import(delta)?
The learner-model crate stores one CRDT document at
learner/<learner-id>/model.crdt. Its typed content includes concepts,
mastery observations, gaps, sessions, and FSRS cards. The store exposes a
merge_delta() operation. The daemon's domain adapter exports the local model,
merges Loro updates, and persists the converged typed value.
KBD control-plane storage
KBD stores one authoritative project.loro document per project and one
append-only replicas/<replica-id>/events.jsonl write-ahead journal plus lock
per replica. Each command holds the replica lock across fold, validation,
event preparation, append, and journal fsync, then imports/fsyncs Loro before
compatibility projections are updated.
redb is not part of the KBD authority; it remains only for the general sync
store in store.rs.
Every committed event is verified by the kbd-runtime signature/hash chain.
Diagnostics report replica journal path/size/Lamport, ingestion state, Loro
snapshot status/frontier/conflicts, lock and single-writer compatibility,
projection revision, device trust counts, and signature-chain validity.
There is no quorum or voter configuration. One journal transaction is the local
write boundary; Loro plus signed causal frontiers handle imported convergence.
The platform-level registry maps canonical paths to explicit project, replica, and machine IDs plus replica kind, parent linkage, HEAD, and read-only reason. Bare/CI replicas are read-only. Writable filesystem replicas must also pass a real child-process flock exclusion probe; a container volume whose exclusion cannot be proven fails closed as read-only.
The kbd-control:<project-id> gossip domain exports the complete Loro update
set from project.loro, wraps it with auxiliary presence, and signs the wire
envelope with an enrolled project device. Receivers verify project identity,
active device membership, envelope signature, every event signature/hash, and
grow-only semantics before fsyncing the merged authority. Replicas on one
machine converge through the shared document path without a network hop.
Parent repositories may append SubmodulePin events for Git links. The event
contains child project UUID, path, and gitlink SHA; child authority remains a
separate project. The converged authority can also be exported as canonical
per-device audit JSONL to refs/heads/audit/kbd without checking out or
importing that ref.
Mobile peers use kbd-mobile plus skill-ffi. They share the exact signed
kbd-control:<project-id> envelope and iroh topic derivation used by the
daemon, while host applications retain the secure device key. Mobile permits
signed events, claims, and adjudications but deliberately excludes Git,
adoption, submodule scans, and audit-ref writes.
P2P endpoint lifecycle
The daemon passes the atomically persisted iroh secret key into the endpoint
builder. The endpoint ID therefore remains stable across restarts. Pairing uses
pair-export and pair-import; tickets carry protocol version, group secret,
endpoint ID, and fingerprint without logging the complete ticket. The endpoint
identity is deliberately separate from the KBD device-signing key.
Intended domain data flow
The daemon retains the incoming receiver and implements this sequence for skill index, learner model, and signed KBD project authority domains.
MCP server tools
In --mode mcp, Sovereign Sync exposes four discovery/sync/search tools and six
KBD tools:
| Family | Tools |
|---|---|
| Discovery/sync | search-skills, sync-status, sync-push, sync-peers |
| KBD read/control | kbd_status, kbd_events, kbd_pause, kbd_revise, kbd_resume, kbd_cancel |
The CLI accepts --prefix-tools and logs the requested prefix mode, but the
generated router still exposes the stable names above.
Current verification boundary
The repository proves these pieces separately:
- manifest default-deny and
Localrejection; - Loro snapshot export/import and version vectors;
- secret-based topic derivation and durable endpoint restart identity;
- iroh-docs two-node sharing in the storage-provider crate;
- signed KBD envelopes and real domain push/import paths;
- single-writer journal ordering and causal-frontier conflict behavior.
The test battery proves two-node domain merge without live internet discovery; final deployment certification separately exercises real iroh peer discovery, signed KBD convergence, and applied-frontier reporting.
Canonical source: substrate/sovereign-sync.