Skip to content

Instantly share code, notes, and snippets.

@bonus414
Last active April 30, 2026 21:24
Show Gist options
  • Select an option

  • Save bonus414/d3522b98bd8d8df28cd551132bbd0df9 to your computer and use it in GitHub Desktop.

Select an option

Save bonus414/d3522b98bd8d8df28cd551132bbd0df9 to your computer and use it in GitHub Desktop.
brain-sync: bridge your two Claudes' memory with a Slack channel

brain-sync: bridge your two Claudes' memory with a Slack channel

If you use both Claude Code (terminal, desktop) and claude.ai (web, mobile), you have two Claudes with two separate memory systems. Whatever you teach one, the other doesn't know. Over months the claude.ai side drifts.

This skill fixes that by using a Slack channel as a human-gated bridge. Claude Code drafts a structured memory digest. You approve. It posts. Your claude.ai Claude reads the channel at session start and proposes memory edits on that side. You approve there too.

Two files in this gist:

  • brain-sync.md — the Claude Code skill. Drop it in .claude/skills/ (project-scoped) or ~/.claude/skills/ (global).
  • This README — setup for both sides.

Why a Slack channel

  • Durable, timestamped, human-owned. The approvals stay on your side.
  • No MCP to build, no webhook to host, no polling.
  • Works from any claude.ai surface (desktop, phone, web) without reaching your dev machine.
  • Searchable if you want to look back at what changed when.

Sender-side setup (Claude Code)

  1. Create a Slack channel. Name it whatever — #claudeai-memory is what I use. Grab the channel ID by right-clicking the channel in Slack → Copy link; the ID is the last path segment (looks like C0XXXXXXXXX).
  2. Connect the claude.ai-native Slack MCP in Claude Code. You want mcp__claude_ai_Slack__slack_send_message available. The generic mcp__slack__* will technically also post, but the claude.ai-native MCP matches the surface your reader is on.
  3. Put brain-sync.md in .claude/skills/ (or ~/.claude/skills/ for global). Open it and replace YOUR_CHANNEL_ID and YOUR_WORKSPACE_NAME.
  4. Invoke with /brain-sync or say "brain sync" after a session where something durable changed.

Reader-side setup (claude.ai)

At the start of any claude.ai session where you want memory refreshed, paste this:

Read the most recent post in #claudeai-memory in my Slack workspace. It's a structured memory digest from my Claude Code side. Summarize what changed since the last update and propose memory edits using the REPLACE, ADD, and REMOVE verbs as written in the post. I'll approve the ones that should persist.

The REPLACE / ADD / REMOVE verbs are load-bearing: they map 1-to-1 onto claude.ai's memory_user_edits tool (its three modes are replace, add, remove). When you approve, the translation to tool calls is mechanical — the reader-Claude doesn't have to guess what you meant.

Two things worth knowing up front

1. Slack mrkdwn is not standard markdown. The Slack API rejects ## headers and **bold**. Use single asterisks for bold (*like this*) and skip hash headers. The skill is already written for Slack mrkdwn. This is just context so you don't try to "fix" the format.

2. The review gate is load-bearing. You'll be tempted to automate: skip the approve step on the sender side, have claude.ai auto-persist on the reader side. Don't. Claude Code tends toward thoroughness and will surface more than you want to persist. The gate forces the question "is this still true next week?".

Calibration

Good "memory-worthy" entries:

  • A tool swap with date and reason: REPLACE: "uses Neo4j" → "uses Memgraph (switched 2026-04-11 after stability issues)"
  • A durable new pattern or workflow: ADD: "runs brain-sync skill to bridge Claude memory via Slack"
  • A declared direction: ADD: "moving toward maximally private/local stack"

Skip:

  • One-off debugging or test runs
  • Minor code tweaks
  • Temporary status ("currently working on X" — use the Context dump section instead)

State file

The skill writes .claude/brain-sync-state.json after each post so the next run knows the diff window:

{
  "last_posted_ts": "1234567890.123456",
  "last_posted_at": "2026-04-18T10:58:00-05:00",
  "last_posted_link": "https://..."
}

If you use Claude Code from multiple machines, commit this file so both sides share the marker.

If you want to adapt

The skill is the entire contract. The format is the API. Feel free to fork and change:

  • Channel name, workspace, path conventions → just edit the placeholders
  • Add a "since" field to the Changes section if you want the reader to know the window explicitly
  • Swap the Slack MCP for a different durable destination (a Notion database, a Linear comment thread)

The one thing I'd leave alone: the REPLACE / ADD / REMOVE verbs. They're the reason the reader side works without guessing.

name brain-sync
description Draft and post a structured memory digest to a Slack channel that your claude.ai Claude reads, so it can propose memory edits on that side. Bridges the two Claudes' separate memory systems. Use when the user says "/brain-sync", "brain sync", or when something durable (tool swap, project status shift, direction change) just happened and is worth syncing.

brain-sync

Purpose

The user has two Claudes — Claude Code (this one, with filesystem access) and claude.ai (browser/mobile). They have separate memory systems. This skill is the bridge: write a structured update here, the user approves, post to a shared Slack channel, and the claude.ai-side Claude reads it at session start and proposes memory edits there.

Channel: #YOUR_CHANNEL_NAME in YOUR_WORKSPACE_NAME Slack workspace Channel ID: YOUR_CHANNEL_ID MCP: mcp__claude_ai_Slack__slack_send_message State file: .claude/brain-sync-state.json — stores last-posted timestamp for the "since" marker

Before first use: replace the three YOUR_* placeholders above with your real values.

When to use

  • User says /brain-sync, "brain sync", "sync the brain", "push to claudeai memory"
  • Just after a tooling/infra swap, project status shift, or decision that should persist on the claude.ai side
  • Not for every session — only when something durable changed

When NOT to use

  • Routine daily work, minor debugging, session summaries
  • Weekly digests or meeting notes — different tools for that
  • Updating this Claude's memory — ask the user directly, no Slack involved

Workflow

1. Gather context

Read the state file to find the "since" marker:

cat .claude/brain-sync-state.json

If missing, treat as 7 days ago.

Then gather what's changed since. Useful signals (in parallel):

  • Recent git log
  • Recent session notes / logs
  • Recent memory file updates
  • Anything the user flagged mid-session as memory-worthy or a swap/decision

Build a mental list of: tooling swaps (X → Y), infra changes, project status shifts, decisions with durability, people/org facts.

Skip: one-off debugging, test runs, small tweaks, ephemeral state.

2. Draft in the exact format

Write the draft to drafts/brain-sync-YYYY-MM-DD-HHMM.md. The format is load-bearing — the claude.ai Claude parses by section. Do not improvise structure.

IMPORTANT — Slack mrkdwn, not standard markdown. Slack's API rejects ## headers and **bold**. Use:

  • Section titles: *Section* (single asterisks = bold in Slack)
  • Bullets: or -
  • Code/paths: standard backticks
  • No ## / ### headers
  • No **bold**

Format:

*YYYY-MM-DD · <session focus in one phrase>*

*Changes since last update*
• <factual bullet: what shipped, swapped, broke, was retired>
• <another>

*Memory-worthy*
• REPLACE: "<old memory fragment>" → "<new>"
• ADD: "<new fact to persist>"
• REMOVE: "<fact no longer true>"

*Context dump* (optional — omit section entirely if nothing)
<paragraph or bullets>

*Next update should cover*
Changes after: <this post's timestamp, filled in after posting>

Rules for content:

  • Direct, factual, lowercase-forward. Infra notes voice, not marketing.
  • No preamble, no sign-off, no "hope this helps"
  • Be conservative on Memory-worthy: only things still true next week
  • Each Memory-worthy bullet uses REPLACE / ADD / REMOVE — these map 1:1 onto the claude.ai memory tool's edit modes
  • If nothing is memory-worthy, write • (nothing this session) explicitly. Don't pad

3. Show the user the draft and wait

Print the full draft in chat. Ask: "good to post, edits, or kill?"

Do not post yet. This is the review gate. The user might:

  • Approve as-is → go to step 4
  • Edit specific bullets → update the draft file, reprint, re-ask
  • Kill the whole thing → delete the draft file, report "killed, nothing posted"

4. Post to Slack on approval

Use mcp__claude_ai_Slack__slack_send_message:

  • channel_id: YOUR_CHANNEL_ID
  • message: the draft body (Slack-mrkdwn formatted)

Capture message_ts and message_link from the response.

5. Update state and confirm

Write the new state file:

{
  "last_posted_ts": "<message_ts from response>",
  "last_posted_at": "<ISO timestamp>",
  "last_posted_link": "<message_link>"
}

Commit the state file if you work across multiple machines.

Report: Slack link + "posted, state updated". One sentence.

Calibration examples

Memory-worthy (post it):

  • REPLACE: "uses Neo4j for knowledge graph" → "uses Memgraph (switched 2026-04-11, Neo4j stability issues)"
  • ADD: "runs local MLX Qwen3-14B as primary local LLM"
  • REMOVE: "actively evaluating Model X" (ruled out, reason)

Not memory-worthy (skip):

  • Ran a one-off eval on Tuesday
  • Fixed a typo
  • Tried three prompts for a draft
  • Asked a question

Red flags — stop and re-draft

  • More than ~5 Memory-worthy bullets on an incremental run → over-persisting, trim to durable ones
  • A bullet says "currently working on X" → status, not memory, move to Context dump
  • You're narrating what the user did ("Person and Claude explored…") → strip to facts
  • You added emojis → remove, this is infra notes
  • You're tempted to skip the review gate because "it's obvious" → don't, the user owns the persist decision
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment