@dolusoft/claude-collab 1.10.3 → 1.11.0

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
@@ -7,13 +7,12 @@ Real-time collaboration between Claude Code terminals via MCP (Model Context Pro
7
7
 
8
8
  ## Overview
9
9
 
10
- Claude Collab lets multiple Claude Code terminals communicate with each other in real-time. One machine starts a hub server via MCP tool others on the same LAN auto-discover and connect via mDNS. No manual IP sharing, no terminal commands.
10
+ Claude Collab lets multiple Claude Code terminals communicate directly no central server needed. Each peer runs its own node; peers discover each other automatically on the LAN via UDP multicast and connect directly over WebSocket.
11
11
 
12
12
  ```
13
- alice ──outbound──→ ┌─────────────────┐ ←──outbound── bob
14
- charlie─outbound──→ │ hub server │ ←──outbound── dave
15
- (auto-discover)
16
- └─────────────────┘
13
+ alice ◄──────────────────► bob
14
+ direct WebSocket
15
+ (auto-discovered)
17
16
  ```
18
17
 
19
18
  ## Setup
@@ -28,55 +27,39 @@ claude mcp add claude-collab -- npx -y @dolusoft/claude-collab --name <your-name
28
27
  |-------------|-------------|
29
28
  | `<your-name>` | Your identifier on the network (e.g. `alice`, `backend`, `frontend`) |
30
29
 
31
- > Your name is saved permanently in Claude Code's MCP config. No server address needed the hub is discovered automatically on the LAN.
30
+ ### Step 2Connect to peers
32
31
 
33
- ### Step 2 One person starts the hub (via MCP tool)
34
-
35
- In Claude Code, call the `start_hub` tool:
32
+ Call `peer_find` in Claude Code:
36
33
 
37
34
  ```
38
- start_hub() # uses default port 9999
39
- start_hub(port=8888) # custom port
35
+ peer_find()
40
36
  ```
41
37
 
42
38
  This will:
43
- 1. Start the hub server on your machine
44
- 2. Show a **Windows UAC prompt** once click **Yes** to open the firewall port
45
- 3. Advertise the hub on your LAN via mDNS
46
-
47
- Everyone else will auto-connect within seconds. No IP address sharing needed.
39
+ 1. Open a **Windows UAC prompt** — click **Yes** to open your firewall
40
+ 2. Wait 30 seconds while peers are discovered and connected
41
+ 3. Close the firewall (another UAC prompt) existing connections persist
48
42
 
49
- ### Step 3 Stop the hub when done
43
+ Everyone on the team should call `peer_find` at the same time when setting up.
50
44
 
51
- ```
52
- stop_hub()
53
- ```
54
-
55
- This stops the server and removes the firewall rule (UAC prompt shown once).
56
-
57
- ---
45
+ ### Step 3 — Adding a new peer later
58
46
 
59
- ### Manual / advanced mode
47
+ Only the **new peer** needs to call `peer_find`. Existing peers will connect to them automatically — no action needed from others.
60
48
 
61
- If you prefer to manage the hub yourself (e.g. on a server), you can still use the legacy approach:
49
+ ### Step 4 After a disconnect or restart
62
50
 
63
- ```bash
64
- # Start hub manually in a terminal:
65
- npx @dolusoft/claude-collab --hub --port 9999
51
+ The disconnecting peer calls `peer_find` again. Others reconnect automatically.
66
52
 
67
- # Add to Claude Code with explicit server address:
68
- claude mcp add claude-collab -- npx -y @dolusoft/claude-collab --name <your-name> --server <hub-ip>:<hub-port>
69
- ```
53
+ ---
70
54
 
71
55
  ## MCP Tools
72
56
 
73
57
  | Tool | Description |
74
58
  |------|-------------|
75
- | `start_hub` | Start a hub server on this machine. Opens firewall via UAC, advertises on LAN via mDNS. |
76
- | `stop_hub` | Stop the running hub. Removes firewall rule via UAC. |
77
- | `ask` | Ask another peer a question by name. Waits up to 5 minutes for a response. |
78
- | `reply` | Reply to an incoming question (called automatically by Claude when a question arrives). |
79
- | `peers` | Show currently connected peers and your own name. |
59
+ | `peer_find` | Discover and connect to peers. Opens firewall, waits 30s, closes firewall. |
60
+ | `ask` | Ask a peer a question by name. Waits up to 5 minutes for a reply. |
61
+ | `reply` | Reply to an incoming question. |
62
+ | `peers` | Show connected peers and your own name/port. |
80
63
  | `history` | Show past questions and answers from this session. |
81
64
 
82
65
  ## Example
@@ -85,38 +68,145 @@ claude mcp add claude-collab -- npx -y @dolusoft/claude-collab --name <your-name
85
68
  # Alice asks Bob
86
69
  ask("bob", "What's the response format for the /users endpoint?")
87
70
 
88
- # Bob sees the question automatically and replies
89
- reply("q_abc123", "Returns JSON: { id, name, email }")
71
+ # Bob sees the question injected into his terminal and replies
72
+ reply("<question-id>", "Returns JSON: { id, name, email }")
73
+
74
+ # Alice receives the answer
75
+ ```
76
+
77
+ ## Use Case: Sharing Context Between Agents
78
+
79
+ Claude Code works best when focused on a single context — one terminal per feature, service, or role. But when multiple Claude instances work in parallel, they can't share what they know.
90
80
 
91
- # Alice sees the answer
81
+ **Claude Collab bridges that gap.** If a user told Alice Claude Code about an API key 10 messages ago, Bob Claude Code can ask Alice Claude Code directly — and Alice Claude Code answers from her own conversation context. No copy-paste. No switching tabs. The knowledge travels between agents.
82
+
83
+ Alice Claude Code and Bob Claude Code are both connected via Claude Collab. During Alice Claude Code's session, the user manually entered an API key:
84
+
85
+ > *"My API key is sk-abc123..."*
86
+
87
+ This is now part of Alice Claude Code's context. Bob Claude Code doesn't know — he's been working in a separate terminal and needs the key to make API calls.
88
+
89
+ Bob Claude Code asks Alice Claude Code directly:
90
+
91
+ ```
92
+ ask("alice", "What is the API key?")
92
93
  ```
93
94
 
94
- ## Architecture
95
+ Alice Claude Code's terminal receives the question, and she replies from what she already knows:
95
96
 
96
97
  ```
97
- src/
98
- ├── infrastructure/
99
- │ ├── hub/
100
- │ │ ├── hub-server.ts # WebSocket hub — routes messages by name
101
- │ │ ├── hub-client.ts # Connects to hub, implements ICollabClient
102
- │ │ ├── hub-manager.ts # Orchestrates hub + firewall + mDNS advertising
103
- │ │ └── hub-protocol.ts # Wire protocol types
104
- │ ├── mdns/
105
- │ │ ├── mdns-advertiser.ts # Broadcasts hub presence on LAN via mDNS
106
- │ │ └── mdns-discovery.ts # Discovers hub on LAN via mDNS
107
- │ └── terminal-injector/ # Injects incoming questions into Claude Code
108
- └── presentation/
109
- └── mcp/ # MCP server + tools (start_hub, stop_hub, ask, reply, peers, history)
98
+ reply("<question-id>", "sk-abc123...")
110
99
  ```
111
100
 
101
+ Bob Claude Code gets the answer and continues working — without the user having to repeat themselves.
102
+
103
+ ```mermaid
104
+ sequenceDiagram
105
+ participant User
106
+ participant Alice Claude Code
107
+ participant Bob Claude Code
108
+
109
+ Alice Claude Code->>Alice Claude Code: peer_find()
110
+ Note over Alice Claude Code: UAC popup → firewall opens
111
+ Bob Claude Code->>Bob Claude Code: peer_find()
112
+ Note over Bob Claude Code: UAC popup → firewall opens
113
+
114
+ Alice Claude Code-)Bob Claude Code: UDP multicast discovery
115
+ Bob Claude Code-)Alice Claude Code: UDP multicast discovery
116
+ Alice Claude Code->>Bob Claude Code: WebSocket HELLO
117
+ Bob Claude Code-->>Alice Claude Code: HELLO_ACK
118
+ Note over Alice Claude Code,Bob Claude Code: P2P connection established
119
+
120
+ Note over Alice Claude Code: firewall closes (connection persists)
121
+ Note over Bob Claude Code: firewall closes (connection persists)
122
+
123
+ User->>Alice Claude Code: "My API key is sk-abc123..."
124
+ Note over Alice Claude Code: Stored in context
125
+
126
+ Bob Claude Code->>Alice Claude Code: ask("alice", "What is the API key?")
127
+ Alice Claude Code-->>Bob Claude Code: ASK_ACK
128
+ Note over Alice Claude Code: Question injected into terminal
129
+ Alice Claude Code->>Bob Claude Code: reply(questionId, "sk-abc123...")
130
+ Note over Bob Claude Code: Uses API key
131
+ ```
132
+
133
+ ---
134
+
135
+ ## How it works
136
+
137
+ ```
138
+ Startup:
139
+ Each peer binds a WebSocket server on a random port (10000–19999)
140
+ Each peer broadcasts UDP multicast (239.255.42.42:11776) every 5s
141
+
142
+ Discovery:
143
+ Peer A hears Peer B's multicast → connects outbound to B's WS port
144
+ If multicast is one-way (e.g. VMware + WiFi), the receiving side
145
+ sends a unicast reply so both peers discover each other
146
+
147
+ peer_find:
148
+ Opens firewall (inbound TCP + UDP 11776) → wait → closes firewall
149
+ Established connections persist after firewall closes (stateful TCP)
150
+ New peers only need to open their own firewall — existing peers
151
+ connect outbound to them automatically
152
+ ```
153
+
154
+ ## Limitations
155
+
156
+ - **Windows only** — terminal injection uses `kernel32.dll` Win32 APIs (`AttachConsole`, `WriteConsoleInput`) compiled via PowerShell. macOS and Linux are not supported.
157
+ - **LAN only** — UDP multicast TTL is set to 1, so packets cannot cross routers. Does not work over the internet or VPNs that don't forward multicast.
158
+ - **No encryption** — peer connections use plain `ws://` WebSocket. Traffic is unencrypted on the network.
159
+ - **5-minute answer timeout** — if the peer does not reply within 5 minutes, `ask()` times out. The question is not retried automatically.
160
+ - **One queued answer per offline peer** — if a peer is offline and you reply to multiple questions from them, only the last reply is queued and delivered on reconnect.
161
+ - **No persistence** — all questions, answers, and history are stored in memory. Restarting the process clears everything.
162
+ - **No broadcast** — `ask()` targets a single peer by name. There is no tool to send a message to all peers at once.
163
+ - **Peer names are not unique** — if two peers join with the same name, the second connection is silently dropped.
164
+
165
+ ---
166
+
112
167
  ## Development
113
168
 
114
169
  ```bash
115
170
  git clone https://github.com/dolusoft/claude-collab.git
116
171
  cd claude-collab
117
172
  pnpm install
118
- pnpm build
119
- pnpm test
173
+ pnpm build # tsup → dist/mcp-main.js + dist/cli.js
174
+ pnpm typecheck # tsc --noEmit
175
+ pnpm test # vitest unit tests
176
+ ```
177
+
178
+ ### Testing locally with two peers
179
+
180
+ Open two terminals on the same machine and run:
181
+
182
+ ```bash
183
+ # Terminal 1
184
+ node dist/mcp-main.js --name alice
185
+
186
+ # Terminal 2
187
+ node dist/mcp-main.js --name bob
188
+ ```
189
+
190
+ Both nodes will bind on random ports in the `10000–19999` range and discover each other via UDP multicast automatically.
191
+
192
+ ### Project structure
193
+
194
+ ```
195
+ src/
196
+ ├── infrastructure/
197
+ │ ├── discovery/
198
+ │ │ └── multicast-discovery.ts # UDP multicast (239.255.42.42:11776) + unicast reply
199
+ │ ├── firewall/
200
+ │ │ └── firewall.ts # Windows Firewall via UAC-elevated netsh
201
+ │ ├── p2p/
202
+ │ │ ├── p2p-node.ts # WS server + client + peer management
203
+ │ │ └── p2p-protocol.ts # Wire protocol: HELLO, ASK, ASK_ACK, ANSWER
204
+ │ └── terminal-injector/
205
+ │ └── windows-injector.ts # Injects questions into Claude Code via WriteConsoleInput
206
+ └── presentation/
207
+ └── mcp/
208
+ ├── server.ts # MCP server setup
209
+ └── tools/ # ask, reply, peers, history, peer_find
120
210
  ```
121
211
 
122
212
  ## License