# Symmetric Sync Protocol Architecture

This document describes the symmetric synchronization architecture used in `ibgib`. It leverages the unique properties of ibGib (content-addressability, intrinsic timeline history) to create a robust, audit-trail-based synchronization protocol.

## Core Concepts

The synchronization process is modeled as a "Saga" — a linear but distributed conversation between two nodes.

*   **[SyncSagaIbGib_V1](file:./sync-types.mts)**: The timeline that encapsulates the entire sync process. This acts as the **shared audit trail**. By the end of a successful sync, both the Local and Remote nodes will have an identical copy of this saga timeline, proving exactly what was exchanged and when.
*   **[SyncSagaCoordinator](file:./sync-saga-coordinator.mts)**: The "Driver" (State Machine) that manages the saga. It is symmetric: both Alice (Source) and Bob (Destination) use the exact same coordinator logic to evolve the saga frame.
*   **[SyncPeerWitness](file:./sync-peer/sync-peer-types.mts)**: The interface for the "Transport Layer". It abstracts the communication channel (Method Call, HTTP, WebSocket) into a simple Witness pattern: `(SyncSagaContextIbGib_V1) => Promise<SyncSagaContextIbGib_V1>` ("ping-pong" exchange).
    *   **[SyncPeer_V1](file:./sync-peer/sync-peer-v1.mts)** provides the base plumbing.
    *   Concrete implementations (e.g., in-memory) handle the actual byte transfer.
*   **[SyncSagaContextIbGib_V1](file:./sync-saga-context/sync-saga-context-types.mts)**: The "Transport Envelope" passed to the `SyncPeer_V1`. 
    * Contains the current Saga Frame, the Message Stone(s) (Data), and any cryptographic proofs required for the step.

## Workflow

Init -> Ack -> Delta(s) -> Conflict/Commit via "ping pong" exchange.

1.  **Init**: Sender initiates sync.
    * Creates the `SyncSagaIbGib_V1` with an `Init` msg frame containing knowledge about domain ibgibs to sync.
    * Optionally creates session keystone based off of Sender's primary keystone.
    * Wraps the saga ibgib in a `SyncSagaContextIbGib_V1` and passes to the `SyncPeer_V1`.
2.  **Ack**: Receiver gets incoming `SyncSagaContextIbGib_V1` and passes to its `SyncSagaCoordinator`.
    * Handles the `Init` frame, comparing knowledge with Receiver's own status of each timeline/stone in domain ibgibs.
    * Creates an `Ack` frame, evolves the `SyncSagaIbGib_V1` with this, wraps in `SyncSagaContextIbGib_V1` and returns to Sender.
      * The `Ack` frame carries both synchronization data (requests/offers) AND conflict information.
      * If the Receiver detects divergence (timeline tips differ and receiver doesn't recognize Sender's tip), it includes a `conflicts` array.
      * Each conflict includes the `tjpAddr`, `localAddr` (Receiver's Tip), `remoteAddr` (Sender's Tip), and crucially `timelineAddrs` (History).
3.  **Delta**: Sender now has enough information to send `Delta` frame if needed.
    * Both Sender and Receiver can send `Delta` frames.
    * `Delta` frames soft link to `payloadAddrsControl` and `payloadAddrsDomain` and act as a manifest, while the actual data transmitted happens according to the `SyncPeer_V1` implementation.
      * `SyncPeer_V1.payloadIbGibsDomainReceived$` is an observable for the actual domain payload ibgibs transmitted.
      * So the a node sends domain payloads out in bulk to the `SyncPeer_V1`, receives the return saga ibgib with a manifest, but may have to wait for the observable to complete to actually process the ibgibs.
    * `Delta` frame can include `requests` (e.g., asking for missing conflict history).
    * Once no deltas required, `Delta` frame sets `proposeCommit` flag. If the other has nothing to add, the session transitions to `Commit`.
4.  **Commit**: When receive `Delta` frame with `proposeCommit`,  should trigger the receiver of this to start its commit. If that is successful, it should return a `Commit` frame, which signals the commit was successful on their end. When this `Commit` frame is received, this end should not perform its own commit. 
    * For local-only syncs, the `SyncPeer_V1` implementation is responsible for moving verified `ibGibs` from the temporary saga space to the durable/persistent domain space.
*   From each endpoint's POV, the cleanup should remove the temp spaces used, in addition to any other required transaction cleanup (like closing any connections). 

### Ephemeral Identity (`useSessionIdentity`)
The sync protocol can optionally generate an ephemeral Keystone Identity for the duration of the saga.
*   **Purpose**: Allows secure, signed exchanges even if the Node doesn't have a long-lived identity, or wishes to isolate the sync session.
*   **Mechanism**: If `useSessionIdentity: true` (default) is passed to `sync()`, a new Keystone frame is generated and linked to the Saga.
*   **Pending Work**: Full verification of these ephemeral signatures is currently pending implementation.

## 📚 Documentation
*   **[Architecture](./docs/architecture.md)**: Detailed design of the Saga Protocol, State Machine, and Smart Diff logic.
*   **[Verification](./docs/verification.md)**: Test matrix, scenarios, and verification results.

## Features
*   **Symmetric Design**: No distinct "Client" or "Server" logic.
*   **Smart Diff**: Efficient "Knowledge Vector" exchange to transfer only missing deltas (though some inefficiencies may exist early on).
*   **Timelines && Constants**: Support for syncing both mutable histories and immutable constant ibgibs.
*   **Optimistic Conflict Resolution**: (In Progress) Branch detection and merge strategies.

## Verification
We rely on rigorous In-Memory Simulation (`InnerSpace`) to verify complex graph scenarios. See **[Verification](./docs/verification.md)** for the full status.
