Sync Claude Code conversations across machines — GitHub-authed CLI + server (Postgres metadata, R2 blobs).
Project description
cync — code sync for Claude Code conversations
Sync your Claude Code conversations across machines, signed in with GitHub.
Your conversation metadata lives in your Supabase Postgres (per-user, RLS),
the transcripts live in your Cloudflare R2 bucket, and a small FastAPI
server brokers both. Like git, but for your chats: cync push on one machine,
cync pull on another, and claude --resume picks up where you left off — plus
a web viewer to browse them.
Browser / CLI ── GitHub login (Supabase Auth) ──┐
▼ JWT
FastAPI ── Postgres (metadata, per-user RLS)
── R2 (transcript blobs)
How it works
- Sign in once per machine with
cync login(GitHub via Supabase, browser PKCE). - A project is a first-class record you own; create one with
cync init <name>and link a directory to it. Conversations are keyed by their Claude session UUID. pushuploads~/.claude/projects/<repo>/<id>.jsonl;pullwrites it back on the other machine and rewrites the embeddedcwdsoclaude --resumejust works.- Everything is scoped to your GitHub user — projects/conversations are private to you.
Install & use (hosted)
The command is cync. No server setup — it points at the hosted cync by default.
curl -fsSL https://cync.run/install.sh | sh
Installs a self-contained binary to ~/.local/bin (no Python needed, MCP bundled).
macOS Apple Silicon and Linux x86_64. For other platforms: pipx install cync-cli.
Then:
cync login # sign in with GitHub
cd ~/path/to/your/project
cync init myproject && cync push # machine A
cync link myproject && cync pull # machine B → claude --resume
Self-hosting
Prefer your own stack? Point the CLI at your deployment via CYNC_SERVER_URL
(env or ~/.config/cync/config.toml), then deploy the server + provision your
own Supabase + R2:
1. Provision (one time)
- Cloudflare R2: create a bucket (default name
cync) and an API token with Object Read & Write. - Supabase: create a project, then run
supabase/schema.sqlin the SQL editor. Enable Auth → Providers → GitHub (create a GitHub OAuth App with callbackhttps://<ref>.supabase.co/auth/v1/callback). Under Auth → URL Configuration, add redirect URLshttp://127.0.0.1:8765/callback(CLI) andhttp://localhost:5173/auth/callback(web).
2. Server
uv venv && source .venv/bin/activate
uv pip install -e ".[server]"
cp .env.example .env # fill in R2_* and SUPABASE_* (URL, anon, service_role)
cync-server # http://127.0.0.1:8787
For cross-machine use, expose the server over HTTPS (Tailscale, Fly.io, Railway). The CLI refuses non-HTTPS server URLs except on localhost.
3. CLI (each machine)
uv pip install -e . # base install
export CYNC_SERVER_URL=http://127.0.0.1:8787 # or your https URL / config.toml
cync login # sign in with GitHub (opens a browser)
cd ~/path/to/your/project
cync init droneforge # create + link a project (machine A)
cync push
# on machine B: cync link droneforge && cync pull → claude --resume
4. Web viewer (optional)
cd client
pnpm install
cp .env.example .env # PUBLIC_SUPABASE_URL, PUBLIC_SUPABASE_ANON_KEY, CYNC_SERVER_URL
pnpm dev # http://localhost:5173 → "Sign in with GitHub"
The SvelteKit server holds the token (Supabase SSR cookies); browse at /p/<project>.
Commands
| Command | What it does |
|---|---|
cync login / logout / whoami |
GitHub auth session |
cync init <name> |
create a project + link this directory |
cync link <name> |
link this directory to an existing project |
cync unlink |
remove this directory's link |
cync status |
show login, linked project, and local-vs-server sync state |
cync push [id] |
upload this project's conversation(s) |
cync pull [id] |
download into ~/.claude (overwrite/add) |
cync list |
list this project's conversations |
cync rm <id> |
delete one conversation from the server (local copy kept) |
cync open |
open the web viewer for this project |
cync install-hooks |
auto-sync via Claude Code hooks (pull on start, push on end) |
cync project list / rm <name> |
manage your projects |
cync --version |
print the version |
MCP server (optional)
Let Claude (or any MCP host) read your synced conversations as context — pull a past chat into the model mid-conversation, not just sync files.
pipx install 'cync-cli[mcp]' # the mcp extra
cync login # the server uses your cync session
Add it to your MCP host (Claude Code .mcp.json, Claude Desktop config, etc.):
{ "mcpServers": { "cync": { "command": "cync", "args": ["mcp"] } } }
Tools: list_projects, list_conversations(project), get_conversation(project, id).
Migrating from v0.2
If you have v0.2 (static-token) data still in R2, after cync login:
python scripts/migrate_legacy.py --slug <name> --email <your-github-email> [--purge]
Or simply re-cync push from a machine that has the conversations locally.
Security
- Per-user GitHub auth (Supabase JWT); every project/conversation is owner-scoped, with Postgres RLS as a backstop. The server holds R2 + Supabase keys; clients never do.
- CLI login uses PKCE + a single-use loopback callback; the session (refresh token)
is stored
0600at~/.config/cync/session.json. - Request bodies are capped (
CYNC_MAX_BODY_BYTES, default 64 MB).
Layout
src/cync/ server (FastAPI), CLI, auth, Supabase + R2 stores
client/ SvelteKit web viewer (GitHub login)
supabase/ Postgres schema + RLS
scripts/ legacy migration
Limitations
- Last-writer-wins; no version history yet.
- Syncs the
.jsonltranscript only (enough for--resume); nottodos/sidecars. - Don't
pusha conversation that's open in Claude Code — quit first so it isn't mid-write. - Listing reads one object per conversation from Postgres (fine for personal scale).
Project details
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file cync_cli-0.7.0.tar.gz.
File metadata
- Download URL: cync_cli-0.7.0.tar.gz
- Upload date:
- Size: 59.8 kB
- Tags: Source
- Uploaded using Trusted Publishing? Yes
- Uploaded via: twine/6.1.0 CPython/3.13.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
7bb11b5a159f89a5b2a752a6551ea34a8db5f5fa58920334b31181366400e8ab
|
|
| MD5 |
0f2bd707570f98973da6dcb8445ea30e
|
|
| BLAKE2b-256 |
b0a7bb6efb03842a5396509e7d41041c8819643ae863185cab7e80d506e71b02
|
Provenance
The following attestation bundles were made for cync_cli-0.7.0.tar.gz:
Publisher:
publish.yml on 03hgryan/cync
-
Statement:
-
Statement type:
https://in-toto.io/Statement/v1 -
Predicate type:
https://docs.pypi.org/attestations/publish/v1 -
Subject name:
cync_cli-0.7.0.tar.gz -
Subject digest:
7bb11b5a159f89a5b2a752a6551ea34a8db5f5fa58920334b31181366400e8ab - Sigstore transparency entry: 2065759105
- Sigstore integration time:
-
Permalink:
03hgryan/cync@7ab0321a8a2bde0a477f82764bc2618ca19f9550 -
Branch / Tag:
refs/tags/v0.7.0 - Owner: https://github.com/03hgryan
-
Access:
private
-
Token Issuer:
https://token.actions.githubusercontent.com -
Runner Environment:
github-hosted -
Publication workflow:
publish.yml@7ab0321a8a2bde0a477f82764bc2618ca19f9550 -
Trigger Event:
push
-
Statement type:
File details
Details for the file cync_cli-0.7.0-py3-none-any.whl.
File metadata
- Download URL: cync_cli-0.7.0-py3-none-any.whl
- Upload date:
- Size: 26.6 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? Yes
- Uploaded via: twine/6.1.0 CPython/3.13.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
9a2ad4d26c44811b0292b16ca69b2ae2c0dbb23bf956c019f32535e6bf95bea1
|
|
| MD5 |
95749886212ee829c8196fcb0a54535d
|
|
| BLAKE2b-256 |
07160fde7bf371036f5a5c96dc150152714811f22655b6575b42f77e3c29dd9c
|
Provenance
The following attestation bundles were made for cync_cli-0.7.0-py3-none-any.whl:
Publisher:
publish.yml on 03hgryan/cync
-
Statement:
-
Statement type:
https://in-toto.io/Statement/v1 -
Predicate type:
https://docs.pypi.org/attestations/publish/v1 -
Subject name:
cync_cli-0.7.0-py3-none-any.whl -
Subject digest:
9a2ad4d26c44811b0292b16ca69b2ae2c0dbb23bf956c019f32535e6bf95bea1 - Sigstore transparency entry: 2065759189
- Sigstore integration time:
-
Permalink:
03hgryan/cync@7ab0321a8a2bde0a477f82764bc2618ca19f9550 -
Branch / Tag:
refs/tags/v0.7.0 - Owner: https://github.com/03hgryan
-
Access:
private
-
Token Issuer:
https://token.actions.githubusercontent.com -
Runner Environment:
github-hosted -
Publication workflow:
publish.yml@7ab0321a8a2bde0a477f82764bc2618ca19f9550 -
Trigger Event:
push
-
Statement type: