Skip to content

Epic: pair the algorithms + component stores with GitHub gists — real version history when connected, local-first when not #4202

Description

@kevinthelago

Give the two graph stores GitHub's native version control — every curation a gist revision, with real
diffs, restore, and sync across machines — while keeping the library fully usable with no GitHub account.

What already exists (this epic does NOT rebuild it)

What is missing is the difference between sharing and syncing: today a gist is a one-shot export
someone chooses to publish. Nothing keeps a gist as the store's living remote, so the store's own evolution
has no remote history.

Why the in-app history is not already this

A component record carries rev + history, but a history entry is
{"at","by","changed":["composes","srcText"],"rev":9} — it records that a change happened and which
fields
, never the previous content. So today you cannot diff a curation, see what a field used to hold,
or restore it. Gist revisions give exactly that, for free, and pair with the rev we already keep.

The principle this must not break

Local stays authoritative; the gist is a synced remote. #2444 established render local-first and never
token-gate. If a gist were the store, a user with no GitHub connection would have no algorithms library
and no component library — the Design Studio and the librarian would both stop working. Every write
therefore lands locally first and syncs when connected; disconnected behaviour is byte-identical to today.

Shape: ONE GIST PER STORE

  • algorithms.json — the algorithms library document.
  • components.json — the component store's JSON projection.

One gist per store gives a clean linear history (one revision per curation, one document to reconcile).
Per-RECORD gists would give finer history and conflict-free parallel edits, but that is ~120 algorithms +
~267 components = hundreds of remote objects and a rate-limit problem on every full sync. Start here;
per-record granularity is a later refinement if whole-document conflicts prove painful in practice.

Reuse the fingerprint we already have

#4192 put the sha256-of-body stamp contract in bsc-cli-util::vendored, shared by both emitters. The
same hash decides whether a remote revision is ahead, behind, or diverged from local — the sync must
reuse it rather than invent a second content comparison.

Slices

  1. Sync core — push the local document as a gist revision on change; pull on connect. Local wins on
    write; a pull that would overwrite local changes stops and reports rather than clobbering (the
    Diverged verdict, same shape as emit sync).
  2. Connection-aware, never gating — with no token the store behaves exactly as today, and the UI says
    "not synced" rather than failing or hiding the library.
  3. bsc graph gist / bsc ui giststatus · push · pull · url, so a live session (and the
    librarian/designer) can see and drive sync from its own shell.
  4. History surfacing — the record inspector links its gist revisions, so "what did this look like
    before" is one click. This is the payoff the in-app history cannot deliver alone.
  5. Conflict reporting — a diverged store is a stated, actionable state (which side is newer, what
    differs), never a silent overwrite in either direction.

Acceptance for the epic

  • With GitHub connected, a curation to either store lands as a gist revision without the user asking.
  • With GitHub NOT connected, both stores behave exactly as they do today — no error, no empty library,
    no prompt.
  • A store changed on two machines reports a divergence rather than silently picking a winner.
  • The sync reuses the bsc-cli-util::vendored hash contract rather than a second comparison.

Metadata

Metadata

Assignees

No one assigned

    Labels

    P2Next milestoneenhancementNew feature or request

    Projects

    No projects

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions