emceepee 0.2.8 → 0.3.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
@@ -17,10 +17,11 @@ npx emceepee
17
17
 
18
18
  **emceepee solves both.** It's a proxy that exposes the entire MCP protocol as tools. Any client that supports tool calling can now:
19
19
 
20
- - Connect to new MCP servers dynamically
20
+ - Connect to new MCP servers dynamically (HTTP or stdio)
21
+ - Spawn and manage MCP server processes with automatic crash recovery
21
22
  - Access resources and resource templates
22
23
  - Use prompts
23
- - Receive notifications and logs
24
+ - Receive notifications and logs (with source filtering)
24
25
  - Handle sampling requests (bidirectional LLM calls)
25
26
  - Handle elicitations (user input requests)
26
27
 
@@ -68,6 +69,57 @@ The LLM will use emceepee's tools to connect, explore, and interact with the ser
68
69
 
69
70
  emceepee exposes a **static set of tools** that never change. These tools provide access to the full MCP protocol, letting any tool-capable client use features it doesn't natively support.
70
71
 
72
+ ## Server Transports
73
+
74
+ emceepee supports two transport types for connecting to backend MCP servers:
75
+
76
+ ### HTTP/SSE Transport
77
+ Connect to remote MCP servers over HTTP with Server-Sent Events:
78
+ ```
79
+ add_server(name: "myserver", url: "http://localhost:3001/mcp")
80
+ ```
81
+
82
+ ### Stdio Transport (Process Management)
83
+ Spawn and manage MCP servers as child processes communicating via stdin/stdout:
84
+ ```
85
+ add_server(name: "myserver", command: "node", args: ["server.js"])
86
+ ```
87
+
88
+ **Stdio features:**
89
+ - **Automatic crash recovery** with exponential backoff restart
90
+ - **Stderr capture** for debugging (exposed via `get_logs` with `source: "stderr"`)
91
+ - **Lifecycle events** for monitoring process state
92
+ - **Configurable restart behavior** (max attempts, delays, backoff multiplier)
93
+
94
+ ### Process Lifecycle Events
95
+
96
+ When using stdio transport, emceepee tracks the full process lifecycle:
97
+
98
+ | Event | Description |
99
+ |-------|-------------|
100
+ | `process_started` | Process spawned successfully |
101
+ | `process_crashed` | Process exited unexpectedly |
102
+ | `restarting` | Attempting to restart (with attempt count) |
103
+ | `restarted` | Successfully restarted after crash |
104
+ | `restart_failed` | Max restart attempts exceeded |
105
+ | `process_stopped` | Process stopped cleanly |
106
+
107
+ ### Restart Configuration
108
+
109
+ Customize crash recovery behavior per server:
110
+
111
+ ```json
112
+ {
113
+ "restartConfig": {
114
+ "enabled": true,
115
+ "maxAttempts": 5,
116
+ "baseDelayMs": 1000,
117
+ "maxDelayMs": 60000,
118
+ "backoffMultiplier": 2
119
+ }
120
+ }
121
+ ```
122
+
71
123
  ## Tools
72
124
 
73
125
  ### Server Management
@@ -102,7 +154,17 @@ emceepee exposes a **static set of tools** that never change. These tools provid
102
154
  | Tool | Description |
103
155
  |------|-------------|
104
156
  | `get_notifications` | Get buffered server notifications |
105
- | `get_logs` | Get buffered log messages |
157
+ | `get_logs` | Get buffered log messages with source filtering |
158
+
159
+ The `get_logs` tool supports filtering by log source:
160
+ - `protocol`: MCP protocol messages and notifications
161
+ - `stderr`: Process stderr output (for stdio servers)
162
+ - `stdout`: Process stdout capture (for local HTTP servers)
163
+
164
+ Example: Get only protocol logs by excluding stderr/stdout:
165
+ ```json
166
+ { "exclude_sources": ["stderr", "stdout"] }
167
+ ```
106
168
 
107
169
  ### Sampling (bidirectional LLM requests)
108
170
  | Tool | Description |
@@ -189,12 +251,26 @@ npx emceepee-http --config servers.json
189
251
 
190
252
  ### Configuration File
191
253
 
192
- Pre-configure backend servers:
254
+ Pre-configure backend servers (HTTP and stdio):
193
255
 
194
256
  ```json
195
257
  {
196
258
  "servers": [
197
- { "name": "myserver", "url": "http://localhost:3001/mcp" }
259
+ {
260
+ "name": "remote-server",
261
+ "url": "http://localhost:3001/mcp"
262
+ },
263
+ {
264
+ "name": "local-server",
265
+ "type": "stdio",
266
+ "command": "node",
267
+ "args": ["./my-mcp-server.js"],
268
+ "env": { "DEBUG": "true" },
269
+ "restartConfig": {
270
+ "maxAttempts": 3,
271
+ "baseDelayMs": 1000
272
+ }
273
+ }
198
274
  ]
199
275
  }
200
276
  ```
@@ -221,6 +297,65 @@ LLM: [uses read_resource with uri="minecraft://state"]
221
297
  Player is at position (100, 64, -200), health: 18/20
222
298
  ```
223
299
 
300
+ ## Library Usage
301
+
302
+ emceepee can also be used as a library for building custom MCP integrations:
303
+
304
+ ### MCPStdioClient
305
+
306
+ Spawn and manage MCP servers as child processes:
307
+
308
+ ```typescript
309
+ import { MCPStdioClient } from "emceepee";
310
+
311
+ const client = new MCPStdioClient({
312
+ name: "my-server",
313
+ command: "node",
314
+ args: ["server.js"],
315
+ restartConfig: {
316
+ maxAttempts: 5,
317
+ baseDelayMs: 1000,
318
+ },
319
+ onLifecycleEvent: (event) => {
320
+ console.log(`${event.event}: ${JSON.stringify(event)}`);
321
+ },
322
+ onLog: (log) => {
323
+ if (log.source === "stderr") {
324
+ console.error(`[stderr] ${log.data}`);
325
+ }
326
+ },
327
+ });
328
+
329
+ await client.connect();
330
+
331
+ // Use the client
332
+ const tools = await client.listTools();
333
+ const result = await client.callTool("my-tool", { arg: "value" });
334
+
335
+ // Clean shutdown
336
+ await client.disconnect();
337
+ ```
338
+
339
+ ### IMCPClient Interface
340
+
341
+ Both HTTP and stdio clients implement the common `IMCPClient` interface:
342
+
343
+ ```typescript
344
+ import { IMCPClient, isStdioClient, isHttpClient } from "emceepee";
345
+
346
+ function handleClient(client: IMCPClient) {
347
+ if (isStdioClient(client)) {
348
+ // Stdio-specific operations (e.g., access stderr buffer)
349
+ } else if (isHttpClient(client)) {
350
+ // HTTP-specific operations
351
+ }
352
+
353
+ // Common operations work on both
354
+ const tools = await client.listTools();
355
+ const info = client.getInfo();
356
+ }
357
+ ```
358
+
224
359
  ## Development
225
360
 
226
361
  ```bash
@@ -228,9 +363,26 @@ bun install # Install dependencies
228
363
  bun run dev # stdio server (development)
229
364
  bun run dev:http # HTTP server (development)
230
365
  bun run check # TypeScript + ESLint
366
+ bun run test # Run tests
231
367
  bun run build # Production build
232
368
  ```
233
369
 
370
+ ### Testing
371
+
372
+ The test suite includes integration tests for the stdio client:
373
+
374
+ ```bash
375
+ bun run test # Run all tests
376
+ bun run test:stdio # Run stdio client tests specifically
377
+ ```
378
+
379
+ Tests cover:
380
+ - Connection lifecycle (connect, disconnect)
381
+ - Tool listing and invocation
382
+ - Stderr capture with source indication
383
+ - Crash handling and automatic restart with exponential backoff
384
+ - Lifecycle events (process_started, crashed, restarting, restarted, stopped)
385
+
234
386
  ## License
235
387
 
236
388
  MIT © Andrew Jefferson