mcpocket 0.5.3 → 0.5.5

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -1,420 +1,420 @@
1
- <p align="center">
2
- <img src="https://img.shields.io/npm/v/mcpocket?color=blue&label=npm" alt="npm version" />
3
- <img src="https://img.shields.io/node/v/mcpocket" alt="node version" />
4
- <img src="https://img.shields.io/github/license/davidsmorais/carry-on" alt="license" />
5
- </p>
6
-
7
- <p align="center">
8
- <img src="./logo.png" alt="mcpocket logo" width="200" />
9
- </p>
10
-
11
- # mcpocket
12
-
13
- > Your AI setup. Every pocket. ✨
14
-
15
- **mcpocket** syncs your Claude Code agents, skills, plugins, and MCP server configurations across machines — so your full AI loadout follows you everywhere, like magic.
16
-
17
- ---
18
-
19
- ## The Problem
20
-
21
- You install 8 MCP servers, configure your Claude Code plugins, and build up a library of agents on your Linux workstation. Then you switch to your Windows laptop and… nothing. You start from scratch. Again.
22
-
23
- **mcpocket** fixes that with two commands: `push` from your source machine, `pull` on any other.
24
-
25
- ## How It Works
26
-
27
- <p align="center">
28
- <img src="./mcpocket.png" alt="mcpocket architecture diagram" width="800" />
29
- </p>
30
-
31
- mcpocket acts as a centralized sync hub for your AI setup. Push your configuration from any machine to GitHub (as a repo or gist), then pull it anywhere else. MCP servers, Claude Code agents, skills, plugins—everything syncs with end-to-end encryption for your secrets.
32
-
33
- ## Features
34
-
35
- - **Multi-client sync** — Claude Desktop, Claude Code, OpenCode, Copilot CLI, Cursor, Codex, and Antigravity configs in one shot
36
- - **Two storage backends** — private GitHub repo (full git history) or lightweight GitHub Gist
37
- - **Provider-scoped sync** — target one or more providers with flags like `--copilot-cli` or `--opencode`
38
- - **End-to-end encryption** — secrets in MCP `env`, `headers`, and `http_headers` are encrypted with AES-256-GCM using a passphrase you choose
39
- - **Cross-platform paths** — Windows ↔ Linux ↔ macOS paths round-trip seamlessly
40
- - **Additive pull** — pulling merges remote servers into your local config without overwriting anything
41
- - **De-duplicated file sync** — push/pull mirror synced files so stale agent, skill, and plugin files don't pile up
42
- - **Zero dependencies on external services** — only GitHub and Git
43
-
44
- ---
45
-
46
- ## Install
47
-
48
- ```bash
49
- npm install -g mcpocket
50
- ```
51
-
52
- Or with pnpm / yarn:
53
-
54
- ```bash
55
- pnpm add -g mcpocket
56
- # or
57
- yarn global add mcpocket
58
- ```
59
-
60
- ## Quick Start
61
-
62
- ```bash
63
- # 1. Initialize (once per machine)
64
- mcpocket init
65
-
66
- # 2. Push your setup to the cloud
67
- mcpocket push
68
-
69
- # 3. Pull on a new machine
70
- mcpocket pull
71
-
72
- # 4. Clean up pocket files interactively
73
- mcpocket cleanup
74
-
75
- # 5. Clean up using patterns from your config (local only, no remote sync)
76
- mcpocket cleanup --local
77
-
78
- # 6. Clean up stale synced files if needed
79
- mcpocket de-dupe
80
-
81
- # 7. Check sync status
82
- mcpocket status
83
- ```
84
-
85
- ---
86
-
87
- ## Commands
88
-
89
- ### `mcpocket init`
90
-
91
- Interactive setup wizard. Links your GitHub account, chooses a storage backend, and creates the remote pocket.
92
-
93
- ```
94
- $ mcpocket init
95
-
96
- ✦ First, let's link your GitHub account.
97
- Required scopes: repo (full control of private repositories)
98
-
99
- 🔑 GitHub token: ****
100
-
101
- ✦ Authenticated as davidsmorais — nice to meet you!
102
-
103
- ✦ Where should mcpocket store your config?
104
- [1] GitHub repo (private repo, full git history)
105
- [2] GitHub gist (lighter, no git clone needed)
106
-
107
- Pick one [1/2]: 1
108
- ```
109
-
110
- **Storage options:**
111
-
112
- | Option | Backend | Requires Git? | History |
113
- |---|---|---|---|
114
- | `1` — Repo | Private `mcpocket-sync` repo | Yes | Full git log |
115
- | `2` — Gist | Private GitHub Gist | No | Gist revisions |
116
-
117
- Requires a [GitHub personal access token](https://github.com/settings/tokens/new) with **`repo`** scope (for repo mode) or **`gist`** scope (for gist mode).
118
-
119
- ### `mcpocket push`
120
-
121
- Reads MCP configs, plugin manifests, agents, and skills from the current machine. Encrypts secrets with a passphrase you choose, then uploads to your private pocket.
122
-
123
- ```bash
124
- mcpocket push
125
- ```
126
-
127
- Target specific providers by passing one or more flags:
128
-
129
- ```bash
130
- mcpocket push --copilot-cli
131
- mcpocket push --cursor --codex
132
- ```
133
-
134
- When provider flags are present, they scope the whole command:
135
-
136
- - Only the selected providers' MCP configs are read and packed into `mcp-config.json`
137
- - Claude home assets (`~/.claude/plugins`, `~/.claude/agents`, `~/.claude/skills`) are only synced when `--claude-code` is included
138
-
139
- - In **repo mode**: commits and pushes to your private GitHub repo.
140
- - In **gist mode**: uploads files to your private GitHub Gist (directory structure is flattened with `__` separators).
141
-
142
- ### `mcpocket pull`
143
-
144
- Downloads your config from the remote pocket, decrypts secrets with your passphrase, and writes everything to the appropriate client config files:
145
-
146
- ```bash
147
- mcpocket pull
148
- ```
149
-
150
- You can also pull into only the providers you want:
151
-
152
- ```bash
153
- mcpocket pull --opencode
154
- mcpocket pull --cursor --copilot-cli
155
- ```
156
-
157
- With provider flags, pull only writes MCP servers to those selected providers. Claude home assets are only restored when `--claude-code` is included.
158
-
159
- | Client | Config file |
160
- |---|---|
161
- | Claude Desktop | `claude_desktop_config.json` |
162
- | Claude Code | `~/.claude/settings.json` |
163
- | OpenCode | `~/.config/opencode/config.json` |
164
- | Copilot CLI | VS Code/Copilot user `mcp.json` |
165
- | Cursor | `~/.cursor/mcp.json` |
166
- | Codex | `~/.codex/config.toml` |
167
- | Antigravity | `~/.gemini/antigravity/mcp_config.json` |
168
-
169
- Pull is **additive** — it adds servers that exist remotely but not locally, without overwriting your existing local config. Restart Claude Desktop after pulling to apply MCP changes.
170
-
171
- For synced files, pull also removes stale agent and skill files that were previously synced but no longer exist in your pocket.
172
-
173
- ### `mcpocket de-dupe`
174
-
175
- Refreshes the pocket, mirrors the current synced files, removes stale duplicates on both sides, and writes the cleaned result back to your configured backend.
176
-
177
- ```bash
178
- mcpocket de-dupe
179
- ```
180
-
181
- Use this if you already have duplicate or renamed agent/skill/plugin files from earlier syncs. In normal use, `push` and `pull` now keep these folders de-duplicated automatically.
182
-
183
- ### `mcpocket cleanup`
184
-
185
- Pulls your pocket from the remote, lets you interactively choose which files to keep, deletes the rest, then pushes the updated pocket back.
186
-
187
- ```bash
188
- mcpocket cleanup
189
- ```
190
-
191
- You will be presented with a numbered list of every file in your pocket and can enter comma-separated indices to select which ones to keep (pressing Enter keeps everything). After confirming, the unselected files are deleted and the pocket is pushed back to the remote.
192
-
193
- **Options:**
194
-
195
- | Flag | Description |
196
- |---|---|
197
- | `-l, --local` | Operate on the local pocket only — no pull/push; use patterns from `mcpocket.json` |
198
- | `--dry-run` | Preview which files would be deleted without making any changes |
199
- | `-y, --yes` | Skip the confirmation prompt |
200
-
201
- #### Local-only cleanup (`--local`)
202
-
203
- When running with `--local`, mcpocket reads `cleanupInclude` / `cleanupExclude` pattern arrays from `~/.mcpocket/config.json`:
204
-
205
- ```jsonc
206
- {
207
- // ... other config ...
208
- "cleanupInclude": ["agents/", "skills/"], // whitelist: only keep these
209
- "cleanupExclude": ["skills/nested/**"] // blacklist: also remove these
210
- }
211
- ```
212
-
213
- Pattern semantics:
214
- - `cleanupInclude`: only files matching **at least one** include pattern are kept. Omit or leave empty to include everything.
215
- - `cleanupExclude`: files matching any exclude pattern are removed (applied after include filtering).
216
- - `dir/` is shorthand for `dir/**` (matches all files inside that directory).
217
- - `*` matches any characters within a single path segment; `**` matches across segments.
218
-
219
- If no patterns are configured, `--local` falls back to the same interactive selection UI as the remote mode.
220
-
221
- ```bash
222
- mcpocket cleanup --local
223
- mcpocket cleanup --local --dry-run # preview without deleting
224
- mcpocket cleanup --local --yes # skip confirmation
225
- ```
226
-
227
- ### `mcpocket status`
228
-
229
- Shows a diff of what's synced, what's local-only, and what's remote-only:
230
-
231
- ```bash
232
- mcpocket status
233
- ```
234
-
235
- ```
236
- ── MCP Servers ──
237
-
238
- Synced:
239
- ✓ filesystem
240
- ✓ github
241
-
242
- Local only (run push):
243
- ↑ sqlite
244
-
245
- In pocket, not here (run pull):
246
- ↓ postgres
247
- ```
248
-
249
- ---
250
-
251
- ## What Gets Synced
252
-
253
- | Category | Source | Details |
254
- |---|---|---|
255
- | MCP server configs | Claude Desktop, Claude Code, OpenCode, Copilot CLI, Cursor, Codex, Antigravity | Merged across all selected providers |
256
- | Plugin manifests | `~/.claude/plugins/` | `installed_plugins.json`, `blocklist.json`, `known_marketplaces.json` |
257
- | Agents | `~/.claude/agents/` | All `*.md` files, recursively |
258
- | Skills | `~/.claude/skills/` | All files, recursively (excluding `node_modules`) |
259
-
260
- If you do not pass provider flags, `push` and `pull` operate on every supported provider. If you do pass flags, only those providers participate in the command.
261
-
262
- ### Never Synced
263
-
264
- - `.credentials.json`
265
- - `plugins/cache/`
266
- - Sessions and telemetry data
267
- - Your GitHub token (stays in local `~/.mcpocket/config.json`)
268
-
269
- ---
270
-
271
- ## Security
272
-
273
- | Concern | How mcpocket handles it |
274
- |---|---|
275
- | API keys & tokens | Encrypted with **AES-256-GCM** (via `scrypt` key derivation) before leaving your machine |
276
- | Passphrase storage | **Never stored** — you enter it on every push/pull |
277
- | Remote storage | Always **private** (private repo or secret gist) |
278
- | Local config | `~/.mcpocket/config.json` is `chmod 600` on Linux/macOS |
279
- | Git auth | Token is injected at runtime into HTTPS URLs, never persisted in git config |
280
- | Error output | Git errors are sanitized to strip tokens before display |
281
-
282
- ### Encryption Format
283
-
284
- Encrypted values are stored as:
285
-
286
- ```
287
- ENCRYPTED:<iv_hex>:<salt_hex>:<authTag_hex>:<ciphertext_hex>
288
- ```
289
-
290
- Each value uses a unique random salt and IV, so identical plaintext values produce different ciphertexts.
291
-
292
- ---
293
-
294
- ## Path Handling
295
-
296
- mcpocket normalizes paths for portability:
297
-
298
- | Direction | Transformation |
299
- |---|---|
300
- | Push | `/home/user/...` or `C:\Users\user\...` → `~/...` |
301
- | Pull | `~/...` → platform-native absolute path |
302
- | Commands | `.cmd` / `.exe` extensions stripped on push, restored on pull (Windows) |
303
-
304
- This means a config pushed from Linux works on Windows and vice versa.
305
-
306
- ---
307
-
308
- ## Configuration
309
-
310
- mcpocket stores its own config at `~/.mcpocket/config.json`:
311
-
312
- ```jsonc
313
- {
314
- "githubToken": "ghp_...",
315
- "storageType": "repo", // "repo" or "gist"
316
- // Repo mode:
317
- "repoFullName": "user/mcpocket-sync",
318
- "repoCloneUrl": "https://github.com/user/mcpocket-sync.git",
319
- "repoHtmlUrl": "https://github.com/user/mcpocket-sync",
320
- // Gist mode:
321
- "gistId": "abc123...",
322
- "gistUrl": "https://gist.github.com/abc123...",
323
- // Cleanup patterns (used by `mcpocket cleanup --local`):
324
- "cleanupInclude": ["agents/", "skills/"], // whitelist: only keep these
325
- "cleanupExclude": ["skills/nested/**"] // blacklist: also remove these
326
- }
327
- ```
328
-
329
- The local repo clone (used as a staging area) lives at `~/.mcpocket/repo/`.
330
-
331
- ---
332
-
333
- ## Requirements
334
-
335
- - **Node.js** 18+
336
- - **Git** in PATH (repo mode only — gist mode doesn't need git)
337
- - A **GitHub account** with a personal access token
338
-
339
- ---
340
-
341
- ## Project Structure
342
-
343
- ```
344
- src/
345
- cli.ts # Entry point, Commander setup
346
- config.ts # Config read/write, storage type definitions
347
- clients/
348
- claude-desktop.ts # Claude Desktop config reader/writer
349
- claude-code.ts # Claude Code settings reader/writer
350
- opencode.ts # OpenCode config reader/writer
351
- types.ts # Shared MCP server type definitions
352
- commands/
353
- cleanup.ts # Interactive/pattern-based pocket cleanup
354
- init.ts # Interactive setup wizard
355
- push.ts # Push local config to remote
356
- pull.ts # Pull remote config to local
357
- status.ts # Diff local vs. remote
358
- storage/
359
- github.ts # GitHub repo CRUD + git operations
360
- gist.ts # GitHub Gist CRUD + file flattening
361
- sync/
362
- agents.ts # Agent file sync logic
363
- mcp.ts # MCP server merge, pack/unpack, encrypt/decrypt
364
- plugins.ts # Plugin manifest sync logic
365
- skills.ts # Skills file sync logic
366
- utils/
367
- crypto.ts # AES-256-GCM encrypt/decrypt helpers
368
- paths.ts # Cross-platform path normalization
369
- prompt.ts # Interactive CLI input helpers
370
- sparkle.ts # CLI banners, spinners, and personality
371
- ```
372
-
373
- ---
374
-
375
- ## Troubleshooting
376
-
377
- ### "mcpocket is not initialized"
378
-
379
- Run `mcpocket init` first to set up your GitHub connection and storage backend.
380
-
381
- ### "Decryption failed — wrong passphrase"
382
-
383
- The passphrase you entered doesn't match the one used during `mcpocket push`. Passphrases are never stored — you need to remember the one you used.
384
-
385
- ### Push says "Nothing changed"
386
-
387
- Your local config matches what's already in the remote pocket. No commit/upload needed.
388
-
389
- ### MCP servers not appearing after pull
390
-
391
- Restart Claude Desktop to reload MCP server configurations. Claude Code and OpenCode pick up changes automatically.
392
-
393
- ### Git errors on push/pull (repo mode)
394
-
395
- Make sure `git` is installed and in your PATH. If you see auth errors, your GitHub token may have expired — run `mcpocket init` to re-authenticate.
396
-
397
- ---
398
-
399
- ## Contributing
400
-
401
- Contributions are welcome! Please open an issue or submit a pull request on [GitHub](https://github.com/davidsmorais/carry-on).
402
-
403
- ```bash
404
- git clone https://github.com/davidsmorais/carry-on.git
405
- cd carry-on
406
- pnpm install
407
- pnpm build
408
- ```
409
-
410
- ---
411
-
412
- ## Author
413
-
414
- **David Morais** — [david@davidmorais.com](mailto:david@davidmorais.com)
415
-
416
- - GitHub: [@davidsmorais](https://github.com/davidsmorais)
417
-
418
- ## License
419
-
420
- [MIT](LICENSE) © David Morais
1
+ <p align="center">
2
+ <img src="https://img.shields.io/npm/v/mcpocket?color=blue&label=npm" alt="npm version" />
3
+ <img src="https://img.shields.io/node/v/mcpocket" alt="node version" />
4
+ <img src="https://img.shields.io/github/license/davidsmorais/carry-on" alt="license" />
5
+ </p>
6
+
7
+ <p align="center">
8
+ <img src="./logo.png" alt="mcpocket logo" width="200" />
9
+ </p>
10
+
11
+ # mcpocket
12
+
13
+ > Your AI setup. Every pocket. ✨
14
+
15
+ **mcpocket** syncs your Claude Code agents, skills, plugins, and MCP server configurations across machines — so your full AI loadout follows you everywhere, like magic.
16
+
17
+ ---
18
+
19
+ ## The Problem
20
+
21
+ You install 8 MCP servers, configure your Claude Code plugins, and build up a library of agents on your Linux workstation. Then you switch to your Windows laptop and… nothing. You start from scratch. Again.
22
+
23
+ **mcpocket** fixes that with two commands: `push` from your source machine, `pull` on any other.
24
+
25
+ ## How It Works
26
+
27
+ <p align="center">
28
+ <img src="./mcpocket.png" alt="mcpocket architecture diagram" width="800" />
29
+ </p>
30
+
31
+ mcpocket acts as a centralized sync hub for your AI setup. Push your configuration from any machine to GitHub (as a repo or gist), then pull it anywhere else. MCP servers, Claude Code agents, skills, plugins—everything syncs with end-to-end encryption for your secrets.
32
+
33
+ ## Features
34
+
35
+ - **Multi-client sync** — Claude Desktop, Claude Code, OpenCode, Copilot CLI, Cursor, Codex, and Antigravity configs in one shot
36
+ - **Two storage backends** — private GitHub repo (full git history) or lightweight GitHub Gist
37
+ - **Provider-scoped sync** — target one or more providers with flags like `--copilot-cli` or `--opencode`
38
+ - **End-to-end encryption** — secrets in MCP `env`, `headers`, and `http_headers` are encrypted with AES-256-GCM using a passphrase you choose
39
+ - **Cross-platform paths** — Windows ↔ Linux ↔ macOS paths round-trip seamlessly
40
+ - **Additive pull** — pulling merges remote servers into your local config without overwriting anything
41
+ - **De-duplicated file sync** — push/pull mirror synced files so stale agent, skill, and plugin files don't pile up
42
+ - **Zero dependencies on external services** — only GitHub and Git
43
+
44
+ ---
45
+
46
+ ## Install
47
+
48
+ ```bash
49
+ npm install -g mcpocket
50
+ ```
51
+
52
+ Or with pnpm / yarn:
53
+
54
+ ```bash
55
+ pnpm add -g mcpocket
56
+ # or
57
+ yarn global add mcpocket
58
+ ```
59
+
60
+ ## Quick Start
61
+
62
+ ```bash
63
+ # 1. Initialize (once per machine)
64
+ mcpocket init
65
+
66
+ # 2. Push your setup to the cloud
67
+ mcpocket push
68
+
69
+ # 3. Pull on a new machine
70
+ mcpocket pull
71
+
72
+ # 4. Clean up pocket files interactively
73
+ mcpocket cleanup
74
+
75
+ # 5. Clean up using patterns from your config (local only, no remote sync)
76
+ mcpocket cleanup --local
77
+
78
+ # 6. Clean up stale synced files if needed
79
+ mcpocket de-dupe
80
+
81
+ # 7. Check sync status
82
+ mcpocket status
83
+ ```
84
+
85
+ ---
86
+
87
+ ## Commands
88
+
89
+ ### `mcpocket init`
90
+
91
+ Interactive setup wizard. Links your GitHub account, chooses a storage backend, and creates the remote pocket.
92
+
93
+ ```
94
+ $ mcpocket init
95
+
96
+ ✦ First, let's link your GitHub account.
97
+ Required scopes: repo (full control of private repositories)
98
+
99
+ 🔑 GitHub token: ****
100
+
101
+ ✦ Authenticated as davidsmorais — nice to meet you!
102
+
103
+ ✦ Where should mcpocket store your config?
104
+ [1] GitHub repo (private repo, full git history)
105
+ [2] GitHub gist (lighter, no git clone needed)
106
+
107
+ Pick one [1/2]: 1
108
+ ```
109
+
110
+ **Storage options:**
111
+
112
+ | Option | Backend | Requires Git? | History |
113
+ |---|---|---|---|
114
+ | `1` — Repo | Private `mcpocket-sync` repo | Yes | Full git log |
115
+ | `2` — Gist | Private GitHub Gist | No | Gist revisions |
116
+
117
+ Requires a [GitHub personal access token](https://github.com/settings/tokens/new) with **`repo`** scope (for repo mode) or **`gist`** scope (for gist mode).
118
+
119
+ ### `mcpocket push`
120
+
121
+ Reads MCP configs, plugin manifests, agents, and skills from the current machine. Encrypts secrets with a passphrase you choose, then uploads to your private pocket.
122
+
123
+ ```bash
124
+ mcpocket push
125
+ ```
126
+
127
+ Target specific providers by passing one or more flags:
128
+
129
+ ```bash
130
+ mcpocket push --copilot-cli
131
+ mcpocket push --cursor --codex
132
+ ```
133
+
134
+ When provider flags are present, they scope the whole command:
135
+
136
+ - Only the selected providers' MCP configs are read and packed into `mcp-config.json`
137
+ - Claude home assets (`~/.claude/plugins`, `~/.claude/agents`, `~/.claude/skills`) are only synced when `--claude-code` is included
138
+
139
+ - In **repo mode**: commits and pushes to your private GitHub repo.
140
+ - In **gist mode**: uploads files to your private GitHub Gist (directory structure is flattened with `__` separators).
141
+
142
+ ### `mcpocket pull`
143
+
144
+ Downloads your config from the remote pocket, decrypts secrets with your passphrase, and writes everything to the appropriate client config files:
145
+
146
+ ```bash
147
+ mcpocket pull
148
+ ```
149
+
150
+ You can also pull into only the providers you want:
151
+
152
+ ```bash
153
+ mcpocket pull --opencode
154
+ mcpocket pull --cursor --copilot-cli
155
+ ```
156
+
157
+ With provider flags, pull only writes MCP servers to those selected providers. Claude home assets are only restored when `--claude-code` is included.
158
+
159
+ | Client | Config file |
160
+ |---|---|
161
+ | Claude Desktop | `claude_desktop_config.json` |
162
+ | Claude Code | `~/.claude/settings.json` |
163
+ | OpenCode | `~/.config/opencode/config.json` |
164
+ | Copilot CLI | VS Code/Copilot user `mcp.json` |
165
+ | Cursor | `~/.cursor/mcp.json` |
166
+ | Codex | `~/.codex/config.toml` |
167
+ | Antigravity | `~/.gemini/antigravity/mcp_config.json` |
168
+
169
+ Pull is **additive** — it adds servers that exist remotely but not locally, without overwriting your existing local config. Restart Claude Desktop after pulling to apply MCP changes.
170
+
171
+ For synced files, pull also removes stale agent and skill files that were previously synced but no longer exist in your pocket.
172
+
173
+ ### `mcpocket de-dupe`
174
+
175
+ Refreshes the pocket, mirrors the current synced files, removes stale duplicates on both sides, and writes the cleaned result back to your configured backend.
176
+
177
+ ```bash
178
+ mcpocket de-dupe
179
+ ```
180
+
181
+ Use this if you already have duplicate or renamed agent/skill/plugin files from earlier syncs. In normal use, `push` and `pull` now keep these folders de-duplicated automatically.
182
+
183
+ ### `mcpocket cleanup`
184
+
185
+ Pulls your pocket from the remote, lets you interactively choose which files to keep, deletes the rest, then pushes the updated pocket back.
186
+
187
+ ```bash
188
+ mcpocket cleanup
189
+ ```
190
+
191
+ You will be presented with a numbered list of every file in your pocket and can enter comma-separated indices to select which ones to keep (pressing Enter keeps everything). After confirming, the unselected files are deleted and the pocket is pushed back to the remote.
192
+
193
+ **Options:**
194
+
195
+ | Flag | Description |
196
+ |---|---|
197
+ | `-l, --local` | Operate on the local pocket only — no pull/push; use patterns from `mcpocket.json` |
198
+ | `--dry-run` | Preview which files would be deleted without making any changes |
199
+ | `-y, --yes` | Skip the confirmation prompt |
200
+
201
+ #### Local-only cleanup (`--local`)
202
+
203
+ When running with `--local`, mcpocket reads `cleanupInclude` / `cleanupExclude` pattern arrays from `~/.mcpocket/config.json`:
204
+
205
+ ```jsonc
206
+ {
207
+ // ... other config ...
208
+ "cleanupInclude": ["agents/", "skills/"], // whitelist: only keep these
209
+ "cleanupExclude": ["skills/nested/**"] // blacklist: also remove these
210
+ }
211
+ ```
212
+
213
+ Pattern semantics:
214
+ - `cleanupInclude`: only files matching **at least one** include pattern are kept. Omit or leave empty to include everything.
215
+ - `cleanupExclude`: files matching any exclude pattern are removed (applied after include filtering).
216
+ - `dir/` is shorthand for `dir/**` (matches all files inside that directory).
217
+ - `*` matches any characters within a single path segment; `**` matches across segments.
218
+
219
+ If no patterns are configured, `--local` falls back to the same interactive selection UI as the remote mode.
220
+
221
+ ```bash
222
+ mcpocket cleanup --local
223
+ mcpocket cleanup --local --dry-run # preview without deleting
224
+ mcpocket cleanup --local --yes # skip confirmation
225
+ ```
226
+
227
+ ### `mcpocket status`
228
+
229
+ Shows a diff of what's synced, what's local-only, and what's remote-only:
230
+
231
+ ```bash
232
+ mcpocket status
233
+ ```
234
+
235
+ ```
236
+ ── MCP Servers ──
237
+
238
+ Synced:
239
+ ✓ filesystem
240
+ ✓ github
241
+
242
+ Local only (run push):
243
+ ↑ sqlite
244
+
245
+ In pocket, not here (run pull):
246
+ ↓ postgres
247
+ ```
248
+
249
+ ---
250
+
251
+ ## What Gets Synced
252
+
253
+ | Category | Source | Details |
254
+ |---|---|---|
255
+ | MCP server configs | Claude Desktop, Claude Code, OpenCode, Copilot CLI, Cursor, Codex, Antigravity | Merged across all selected providers |
256
+ | Plugin manifests | `~/.claude/plugins/` | `installed_plugins.json`, `blocklist.json`, `known_marketplaces.json` |
257
+ | Agents | `~/.claude/agents/` | All `*.md` files, recursively |
258
+ | Skills | `~/.claude/skills/` | All files, recursively (excluding `node_modules`) |
259
+
260
+ If you do not pass provider flags, `push` and `pull` operate on every supported provider. If you do pass flags, only those providers participate in the command.
261
+
262
+ ### Never Synced
263
+
264
+ - `.credentials.json`
265
+ - `plugins/cache/`
266
+ - Sessions and telemetry data
267
+ - Your GitHub token (stays in local `~/.mcpocket/config.json`)
268
+
269
+ ---
270
+
271
+ ## Security
272
+
273
+ | Concern | How mcpocket handles it |
274
+ |---|---|
275
+ | API keys & tokens | Encrypted with **AES-256-GCM** (via `scrypt` key derivation) before leaving your machine |
276
+ | Passphrase storage | **Never stored** — you enter it on every push/pull |
277
+ | Remote storage | Always **private** (private repo or secret gist) |
278
+ | Local config | `~/.mcpocket/config.json` is `chmod 600` on Linux/macOS |
279
+ | Git auth | Token is injected at runtime into HTTPS URLs, never persisted in git config |
280
+ | Error output | Git errors are sanitized to strip tokens before display |
281
+
282
+ ### Encryption Format
283
+
284
+ Encrypted values are stored as:
285
+
286
+ ```
287
+ ENCRYPTED:<iv_hex>:<salt_hex>:<authTag_hex>:<ciphertext_hex>
288
+ ```
289
+
290
+ Each value uses a unique random salt and IV, so identical plaintext values produce different ciphertexts.
291
+
292
+ ---
293
+
294
+ ## Path Handling
295
+
296
+ mcpocket normalizes paths for portability:
297
+
298
+ | Direction | Transformation |
299
+ |---|---|
300
+ | Push | `/home/user/...` or `C:\Users\user\...` → `~/...` |
301
+ | Pull | `~/...` → platform-native absolute path |
302
+ | Commands | `.cmd` / `.exe` extensions stripped on push, restored on pull (Windows) |
303
+
304
+ This means a config pushed from Linux works on Windows and vice versa.
305
+
306
+ ---
307
+
308
+ ## Configuration
309
+
310
+ mcpocket stores its own config at `~/.mcpocket/config.json`:
311
+
312
+ ```jsonc
313
+ {
314
+ "githubToken": "ghp_...",
315
+ "storageType": "repo", // "repo" or "gist"
316
+ // Repo mode:
317
+ "repoFullName": "user/mcpocket-sync",
318
+ "repoCloneUrl": "https://github.com/user/mcpocket-sync.git",
319
+ "repoHtmlUrl": "https://github.com/user/mcpocket-sync",
320
+ // Gist mode:
321
+ "gistId": "abc123...",
322
+ "gistUrl": "https://gist.github.com/abc123...",
323
+ // Cleanup patterns (used by `mcpocket cleanup --local`):
324
+ "cleanupInclude": ["agents/", "skills/"], // whitelist: only keep these
325
+ "cleanupExclude": ["skills/nested/**"] // blacklist: also remove these
326
+ }
327
+ ```
328
+
329
+ The local repo clone (used as a staging area) lives at `~/.mcpocket/repo/`.
330
+
331
+ ---
332
+
333
+ ## Requirements
334
+
335
+ - **Node.js** 18+
336
+ - **Git** in PATH (repo mode only — gist mode doesn't need git)
337
+ - A **GitHub account** with a personal access token
338
+
339
+ ---
340
+
341
+ ## Project Structure
342
+
343
+ ```
344
+ src/
345
+ cli.ts # Entry point, Commander setup
346
+ config.ts # Config read/write, storage type definitions
347
+ clients/
348
+ claude-desktop.ts # Claude Desktop config reader/writer
349
+ claude-code.ts # Claude Code settings reader/writer
350
+ opencode.ts # OpenCode config reader/writer
351
+ types.ts # Shared MCP server type definitions
352
+ commands/
353
+ cleanup.ts # Interactive/pattern-based pocket cleanup
354
+ init.ts # Interactive setup wizard
355
+ push.ts # Push local config to remote
356
+ pull.ts # Pull remote config to local
357
+ status.ts # Diff local vs. remote
358
+ storage/
359
+ github.ts # GitHub repo CRUD + git operations
360
+ gist.ts # GitHub Gist CRUD + file flattening
361
+ sync/
362
+ agents.ts # Agent file sync logic
363
+ mcp.ts # MCP server merge, pack/unpack, encrypt/decrypt
364
+ plugins.ts # Plugin manifest sync logic
365
+ skills.ts # Skills file sync logic
366
+ utils/
367
+ crypto.ts # AES-256-GCM encrypt/decrypt helpers
368
+ paths.ts # Cross-platform path normalization
369
+ prompt.ts # Interactive CLI input helpers
370
+ sparkle.ts # CLI banners, spinners, and personality
371
+ ```
372
+
373
+ ---
374
+
375
+ ## Troubleshooting
376
+
377
+ ### "mcpocket is not initialized"
378
+
379
+ Run `mcpocket init` first to set up your GitHub connection and storage backend.
380
+
381
+ ### "Decryption failed — wrong passphrase"
382
+
383
+ The passphrase you entered doesn't match the one used during `mcpocket push`. Passphrases are never stored — you need to remember the one you used.
384
+
385
+ ### Push says "Nothing changed"
386
+
387
+ Your local config matches what's already in the remote pocket. No commit/upload needed.
388
+
389
+ ### MCP servers not appearing after pull
390
+
391
+ Restart Claude Desktop to reload MCP server configurations. Claude Code and OpenCode pick up changes automatically.
392
+
393
+ ### Git errors on push/pull (repo mode)
394
+
395
+ Make sure `git` is installed and in your PATH. If you see auth errors, your GitHub token may have expired — run `mcpocket init` to re-authenticate.
396
+
397
+ ---
398
+
399
+ ## Contributing
400
+
401
+ Contributions are welcome! Please open an issue or submit a pull request on [GitHub](https://github.com/davidsmorais/carry-on).
402
+
403
+ ```bash
404
+ git clone https://github.com/davidsmorais/carry-on.git
405
+ cd carry-on
406
+ pnpm install
407
+ pnpm build
408
+ ```
409
+
410
+ ---
411
+
412
+ ## Author
413
+
414
+ **David Morais** — [david@davidmorais.com](mailto:david@davidmorais.com)
415
+
416
+ - GitHub: [@davidsmorais](https://github.com/davidsmorais)
417
+
418
+ ## License
419
+
420
+ [MIT](LICENSE) © David Morais