mcp-server-opencode 1.0.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.
Files changed (70) hide show
  1. package/README.md +129 -0
  2. package/build/src/index.d.ts +3 -0
  3. package/build/src/index.d.ts.map +1 -0
  4. package/build/src/index.js +35 -0
  5. package/build/src/index.js.map +1 -0
  6. package/build/src/modules/prompts/delegate_task.d.ts +3 -0
  7. package/build/src/modules/prompts/delegate_task.d.ts.map +1 -0
  8. package/build/src/modules/prompts/delegate_task.js +33 -0
  9. package/build/src/modules/prompts/delegate_task.js.map +1 -0
  10. package/build/src/modules/prompts/index.d.ts +3 -0
  11. package/build/src/modules/prompts/index.d.ts.map +1 -0
  12. package/build/src/modules/prompts/index.js +5 -0
  13. package/build/src/modules/prompts/index.js.map +1 -0
  14. package/build/src/modules/shared/config.d.ts +12 -0
  15. package/build/src/modules/shared/config.d.ts.map +1 -0
  16. package/build/src/modules/shared/config.js +33 -0
  17. package/build/src/modules/shared/config.js.map +1 -0
  18. package/build/src/modules/shared/mcp-result.d.ts +16 -0
  19. package/build/src/modules/shared/mcp-result.d.ts.map +1 -0
  20. package/build/src/modules/shared/mcp-result.js +14 -0
  21. package/build/src/modules/shared/mcp-result.js.map +1 -0
  22. package/build/src/modules/shared/opencode-client.d.ts +27 -0
  23. package/build/src/modules/shared/opencode-client.d.ts.map +1 -0
  24. package/build/src/modules/shared/opencode-client.js +58 -0
  25. package/build/src/modules/shared/opencode-client.js.map +1 -0
  26. package/build/src/modules/shared/server-registry.d.ts +10 -0
  27. package/build/src/modules/shared/server-registry.d.ts.map +1 -0
  28. package/build/src/modules/shared/server-registry.js +17 -0
  29. package/build/src/modules/shared/server-registry.js.map +1 -0
  30. package/build/src/modules/shared/task-registry.d.ts +9 -0
  31. package/build/src/modules/shared/task-registry.d.ts.map +1 -0
  32. package/build/src/modules/shared/task-registry.js +11 -0
  33. package/build/src/modules/shared/task-registry.js.map +1 -0
  34. package/build/src/modules/tools/get_task_result.d.ts +3 -0
  35. package/build/src/modules/tools/get_task_result.d.ts.map +1 -0
  36. package/build/src/modules/tools/get_task_result.js +47 -0
  37. package/build/src/modules/tools/get_task_result.js.map +1 -0
  38. package/build/src/modules/tools/get_task_status.d.ts +3 -0
  39. package/build/src/modules/tools/get_task_status.d.ts.map +1 -0
  40. package/build/src/modules/tools/get_task_status.js +29 -0
  41. package/build/src/modules/tools/get_task_status.js.map +1 -0
  42. package/build/src/modules/tools/index.d.ts +3 -0
  43. package/build/src/modules/tools/index.d.ts.map +1 -0
  44. package/build/src/modules/tools/index.js +18 -0
  45. package/build/src/modules/tools/index.js.map +1 -0
  46. package/build/src/modules/tools/list_agents.d.ts +3 -0
  47. package/build/src/modules/tools/list_agents.d.ts.map +1 -0
  48. package/build/src/modules/tools/list_agents.js +74 -0
  49. package/build/src/modules/tools/list_agents.js.map +1 -0
  50. package/build/src/modules/tools/start_server.d.ts +3 -0
  51. package/build/src/modules/tools/start_server.d.ts.map +1 -0
  52. package/build/src/modules/tools/start_server.js +51 -0
  53. package/build/src/modules/tools/start_server.js.map +1 -0
  54. package/build/src/modules/tools/start_task.d.ts +3 -0
  55. package/build/src/modules/tools/start_task.d.ts.map +1 -0
  56. package/build/src/modules/tools/start_task.js +75 -0
  57. package/build/src/modules/tools/start_task.js.map +1 -0
  58. package/build/src/modules/tools/stop_server.d.ts +3 -0
  59. package/build/src/modules/tools/stop_server.d.ts.map +1 -0
  60. package/build/src/modules/tools/stop_server.js +34 -0
  61. package/build/src/modules/tools/stop_server.js.map +1 -0
  62. package/build/src/modules/tools/wait_for_task.d.ts +3 -0
  63. package/build/src/modules/tools/wait_for_task.d.ts.map +1 -0
  64. package/build/src/modules/tools/wait_for_task.js +86 -0
  65. package/build/src/modules/tools/wait_for_task.js.map +1 -0
  66. package/build/src/test-utils/fake-mcp-server.d.ts +10 -0
  67. package/build/src/test-utils/fake-mcp-server.d.ts.map +1 -0
  68. package/build/src/test-utils/fake-mcp-server.js +33 -0
  69. package/build/src/test-utils/fake-mcp-server.js.map +1 -0
  70. package/package.json +51 -0
package/README.md ADDED
@@ -0,0 +1,129 @@
1
+ # opencode-mcp
2
+
3
+ An MCP (Model Context Protocol) server that lets Claude Code drive an [OpenCode](https://opencode.ai) instance and delegate work to its subagents — so orchestrator models like Opus or Fable can hand off tasks to the other models OpenCode exposes.
4
+
5
+ ```
6
+ Claude Code
7
+
8
+
9
+ MCP Server (this project)
10
+
11
+
12
+ OpenCode SDK / CLI
13
+
14
+
15
+ Subagents
16
+ ```
17
+
18
+ ## Status
19
+
20
+ Functional. All tools are wired to real OpenCode instances via `@opencode-ai/sdk` (`createOpencodeServer` / `createOpencodeClient`), covered by a Vitest suite. The server also installs `SIGHUP`/`SIGINT`/`SIGTERM`/`exit` handlers so no `opencode serve` child process outlives the MCP process.
21
+
22
+ ## Design
23
+
24
+ Task delegation is **asynchronous**: starting a task returns immediately with a `task_id` instead of blocking until the subagent finishes. This lets Claude Code fire multiple `opencode_start_task` calls in parallel — each one opens an isolated OpenCode `Session` — without hitting MCP client timeouts on long-running work. Status and results are fetched separately via polling.
25
+
26
+ ## Tools
27
+
28
+ | Tool | Description |
29
+ | --- | --- |
30
+ | `opencode_start_server` | Start (or attach to) an OpenCode server instance |
31
+ | `opencode_stop_server` | Stop a running OpenCode server instance |
32
+ | `opencode_list_agents` | List agents/models available on a server instance |
33
+ | `opencode_start_task` | Delegate a task to an agent by starting a new session and prompt |
34
+ | `opencode_get_task_status` | Poll the status of a delegated task (`pending` / `running` / `completed` / `failed`) |
35
+ | `opencode_get_task_result` | Fetch the final result of a completed task |
36
+ | `opencode_wait_for_task` | Long-poll one or more delegated tasks until they finish (`mode: "all"` or `"any"`) or the timeout elapses |
37
+
38
+ ## Prompts
39
+
40
+ | Prompt | Description |
41
+ | --- | --- |
42
+ | `delegate_task` | Guides the host through delegating one or more tasks to OpenCode agents (start/wait/result workflow) |
43
+
44
+ ## Configuration
45
+
46
+ ### `MCP_TOOL_TIMEOUT`
47
+
48
+ `opencode_wait_for_task` accepts a `timeout_ms` input, but it's clamped to a server-side maximum so a single call can't block the MCP connection indefinitely. That maximum defaults to **300000 ms (5 minutes)** and is configurable via `MCP_TOOL_TIMEOUT`.
49
+
50
+ `MCP_TOOL_TIMEOUT` can be set two ways:
51
+
52
+ - **Environment variable** — set it in the MCP server config:
53
+
54
+ ```json
55
+ {
56
+ "mcpServers": {
57
+ "opencode": {
58
+ "command": "node",
59
+ "args": ["/path/to/opencode-mcp/build/src/index.js"],
60
+ "env": { "MCP_TOOL_TIMEOUT": "1200000" }
61
+ }
62
+ }
63
+ }
64
+ ```
65
+
66
+ - **CLI argument** — pass `MCP_TOOL_TIMEOUT=<ms>` as an extra arg to the server process:
67
+
68
+ ```json
69
+ {
70
+ "mcpServers": {
71
+ "opencode": {
72
+ "command": "node",
73
+ "args": ["/path/to/opencode-mcp/build/src/index.js", "MCP_TOOL_TIMEOUT=1200000"]
74
+ }
75
+ }
76
+ }
77
+ ```
78
+
79
+ If both are present, the **environment variable takes precedence** over the CLI argument. Invalid or non-numeric values fall back to the 300000 ms default.
80
+
81
+ Note that raising this value only raises the server-side clamp — the MCP *client's* own tool-call timeout (e.g. Claude Code's) must also be set to a value **greater than or equal to** this max, or the client will abort the call before `opencode_wait_for_task` has a chance to return.
82
+
83
+ ## Project structure
84
+
85
+ ```
86
+ src/
87
+ ├── index.ts # MCP server entrypoint (stdio transport, shutdown handlers)
88
+ └── modules/
89
+ ├── tools/ # One file per MCP tool, registered in index.ts
90
+ ├── prompts/ # One file per MCP prompt, registered in index.ts
91
+ └── shared/ # Cross-tool infrastructure
92
+ ├── server-registry.ts # Tracks running OpenCode servers; killAllServers() on shutdown
93
+ ├── task-registry.ts # Maps task_id → OpenCode server + session
94
+ ├── opencode-client.ts # Builds SDK clients from the registries
95
+ ├── config.ts # MCP_TOOL_TIMEOUT resolution (env var / CLI arg)
96
+ └── mcp-result.ts # jsonResult / jsonError MCP output helpers
97
+ ```
98
+
99
+ Each module ships with a colocated `*.test.ts` Vitest suite.
100
+
101
+ ## Getting started
102
+
103
+ ```bash
104
+ pnpm install
105
+ pnpm dev # runs the server through the MCP Inspector (tsx, no build needed)
106
+ ```
107
+
108
+ Other scripts:
109
+
110
+ ```bash
111
+ pnpm test # vitest run
112
+ pnpm test:coverage # vitest run --coverage
113
+ pnpm lint # biome check
114
+ pnpm lint:write # biome check --write
115
+ pnpm build # clean tsc build to ./build (also the typecheck)
116
+ ```
117
+
118
+ To use it from an MCP host, build and point the host at the executable entrypoint:
119
+
120
+ ```json
121
+ {
122
+ "mcpServers": {
123
+ "opencode": {
124
+ "command": "node",
125
+ "args": ["/path/to/opencode-mcp/build/src/index.js"]
126
+ }
127
+ }
128
+ }
129
+ ```
@@ -0,0 +1,3 @@
1
+ #!/usr/bin/env node
2
+ export {};
3
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":""}
@@ -0,0 +1,35 @@
1
+ #!/usr/bin/env node
2
+ import { McpServer } from "@modelcontextprotocol/sdk/server/mcp.js";
3
+ import { StdioServerTransport } from "@modelcontextprotocol/sdk/server/stdio.js";
4
+ import { registerPrompts } from "./modules/prompts/index.js";
5
+ import { killAllServers } from "./modules/shared/server-registry.js";
6
+ import { registerTools } from "./modules/tools/index.js";
7
+ // Create server instance
8
+ const server = new McpServer({
9
+ name: "opencode-mcp",
10
+ version: "1.0.0",
11
+ });
12
+ function shutdown(signal) {
13
+ console.error(`Received ${signal}, stopping tracked OpenCode servers...`);
14
+ killAllServers();
15
+ process.exit(0);
16
+ }
17
+ // Terminal closed (SIGHUP), Ctrl+C (SIGINT), or a normal kill (SIGTERM):
18
+ // make sure no `opencode serve` child keeps running after we die.
19
+ process.on("SIGHUP", shutdown);
20
+ process.on("SIGINT", shutdown);
21
+ process.on("SIGTERM", shutdown);
22
+ // Safety net for any other exit path (uncaught exception, process.exit elsewhere).
23
+ process.on("exit", killAllServers);
24
+ async function main() {
25
+ registerTools(server);
26
+ registerPrompts(server);
27
+ const transport = new StdioServerTransport();
28
+ await server.connect(transport);
29
+ console.error("OpenCode MCP Server running on stdio");
30
+ }
31
+ main().catch((error) => {
32
+ console.error("Fatal error in main():", error);
33
+ process.exit(1);
34
+ });
35
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":";AACA,OAAO,EAAE,SAAS,EAAE,MAAM,yCAAyC,CAAC;AACpE,OAAO,EAAE,oBAAoB,EAAE,MAAM,2CAA2C,CAAC;AACjF,OAAO,EAAE,eAAe,EAAE,MAAM,4BAA4B,CAAC;AAC7D,OAAO,EAAE,cAAc,EAAE,MAAM,qCAAqC,CAAC;AACrE,OAAO,EAAE,aAAa,EAAE,MAAM,0BAA0B,CAAC;AAEzD,yBAAyB;AACzB,MAAM,MAAM,GAAG,IAAI,SAAS,CAAC;IAC3B,IAAI,EAAE,cAAc;IACpB,OAAO,EAAE,OAAO;CACjB,CAAC,CAAC;AAEH,SAAS,QAAQ,CAAC,MAAsB;IACtC,OAAO,CAAC,KAAK,CAAC,YAAY,MAAM,wCAAwC,CAAC,CAAC;IAC1E,cAAc,EAAE,CAAC;IACjB,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;AAClB,CAAC;AAED,yEAAyE;AACzE,kEAAkE;AAClE,OAAO,CAAC,EAAE,CAAC,QAAQ,EAAE,QAAQ,CAAC,CAAC;AAC/B,OAAO,CAAC,EAAE,CAAC,QAAQ,EAAE,QAAQ,CAAC,CAAC;AAC/B,OAAO,CAAC,EAAE,CAAC,SAAS,EAAE,QAAQ,CAAC,CAAC;AAChC,mFAAmF;AACnF,OAAO,CAAC,EAAE,CAAC,MAAM,EAAE,cAAc,CAAC,CAAC;AAEnC,KAAK,UAAU,IAAI;IACjB,aAAa,CAAC,MAAM,CAAC,CAAC;IACtB,eAAe,CAAC,MAAM,CAAC,CAAC;IACxB,MAAM,SAAS,GAAG,IAAI,oBAAoB,EAAE,CAAC;IAC7C,MAAM,MAAM,CAAC,OAAO,CAAC,SAAS,CAAC,CAAC;IAChC,OAAO,CAAC,KAAK,CAAC,sCAAsC,CAAC,CAAC;AACxD,CAAC;AAED,IAAI,EAAE,CAAC,KAAK,CAAC,CAAC,KAAK,EAAE,EAAE;IACrB,OAAO,CAAC,KAAK,CAAC,wBAAwB,EAAE,KAAK,CAAC,CAAC;IAC/C,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;AAClB,CAAC,CAAC,CAAC"}
@@ -0,0 +1,3 @@
1
+ import type { McpServer } from "@modelcontextprotocol/sdk/server/mcp.js";
2
+ export declare function registerDelegateTaskPrompt(server: McpServer): void;
3
+ //# sourceMappingURL=delegate_task.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"delegate_task.d.ts","sourceRoot":"","sources":["../../../../src/modules/prompts/delegate_task.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,yCAAyC,CAAC;AAmBzE,wBAAgB,0BAA0B,CAAC,MAAM,EAAE,SAAS,QAoB3D"}
@@ -0,0 +1,33 @@
1
+ const DELEGATE_TASK_INSTRUCTIONS = `You have access to the opencode-mcp server, which lets you delegate work to OpenCode agents. Follow this workflow whenever you delegate tasks:
2
+
3
+ Recommended models: run delegated tasks with Fable 5, Opus 4.8, or GPT 5.6 Sol. When overriding an agent's model via opencode_start_task, prefer one of these.
4
+
5
+ Workflow:
6
+ 1. Ensure an OpenCode server is running. If you don't already have a server_id from a previous opencode_start_server call, call opencode_start_server first.
7
+ 2. Call opencode_list_agents with the server_id to discover the available agents (native and custom) and models. Agents may have a pre-assigned model ("provider/model"); you can still override it per task.
8
+ 3. For each task, call opencode_start_task with the server_id and the task's prompt. Optionally pass an agent name and/or a model override. Collect the returned task_id for every call.
9
+ 4. Wait for completion with opencode_wait_for_task:
10
+ - Single task: mode "all" with the single task_id.
11
+ - Multiple tasks, incremental results: call it repeatedly with mode "any", removing completed task_ids each time.
12
+ - Multiple tasks, all at once: call it once with mode "all" and every task_id.
13
+ 5. Once a task is reported finished, call opencode_get_task_result for that task_id to retrieve its output.
14
+ 6. Use opencode_get_task_status only for quick, non-blocking checks on a task's progress (e.g. to report status to the user) — it does not replace opencode_wait_for_task or opencode_get_task_result.
15
+
16
+ Do not call opencode_get_task_result before the task has finished, and prefer opencode_wait_for_task over polling opencode_get_task_status in a loop.`;
17
+ export function registerDelegateTaskPrompt(server) {
18
+ server.registerPrompt("delegate_task", {
19
+ title: "Delegate task to OpenCode",
20
+ description: "Instructions for the correct workflow to delegate tasks to OpenCode agents via this MCP server",
21
+ }, () => ({
22
+ messages: [
23
+ {
24
+ role: "user",
25
+ content: {
26
+ type: "text",
27
+ text: DELEGATE_TASK_INSTRUCTIONS,
28
+ },
29
+ },
30
+ ],
31
+ }));
32
+ }
33
+ //# sourceMappingURL=delegate_task.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"delegate_task.js","sourceRoot":"","sources":["../../../../src/modules/prompts/delegate_task.ts"],"names":[],"mappings":"AAEA,MAAM,0BAA0B,GAAG;;;;;;;;;;;;;;;sJAemH,CAAC;AAEvJ,MAAM,UAAU,0BAA0B,CAAC,MAAiB;IAC1D,MAAM,CAAC,cAAc,CACnB,eAAe,EACf;QACE,KAAK,EAAE,2BAA2B;QAClC,WAAW,EACT,gGAAgG;KACnG,EACD,GAAG,EAAE,CAAC,CAAC;QACL,QAAQ,EAAE;YACR;gBACE,IAAI,EAAE,MAAM;gBACZ,OAAO,EAAE;oBACP,IAAI,EAAE,MAAM;oBACZ,IAAI,EAAE,0BAA0B;iBACjC;aACF;SACF;KACF,CAAC,CACH,CAAC;AACJ,CAAC"}
@@ -0,0 +1,3 @@
1
+ import type { McpServer } from "@modelcontextprotocol/sdk/server/mcp.js";
2
+ export declare function registerPrompts(server: McpServer): void;
3
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../../src/modules/prompts/index.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,yCAAyC,CAAC;AAGzE,wBAAgB,eAAe,CAAC,MAAM,EAAE,SAAS,QAEhD"}
@@ -0,0 +1,5 @@
1
+ import { registerDelegateTaskPrompt } from "./delegate_task.js";
2
+ export function registerPrompts(server) {
3
+ registerDelegateTaskPrompt(server);
4
+ }
5
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../../../src/modules/prompts/index.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,0BAA0B,EAAE,MAAM,oBAAoB,CAAC;AAEhE,MAAM,UAAU,eAAe,CAAC,MAAiB;IAC/C,0BAA0B,CAAC,MAAM,CAAC,CAAC;AACrC,CAAC"}
@@ -0,0 +1,12 @@
1
+ /**
2
+ * Resolve the configurable max clamp (ms) for tool wait timeouts.
3
+ *
4
+ * Precedence: the `MCP_TOOL_TIMEOUT` environment variable wins over an
5
+ * `MCP_TOOL_TIMEOUT=<ms>` CLI arg, which wins over the built-in default of
6
+ * 300000ms (5 min). Invalid/non-numeric values fall back to the default.
7
+ *
8
+ * Reads `process.env` / `process.argv` lazily on each call so tests can vary
9
+ * them between invocations without module re-import tricks.
10
+ */
11
+ export declare function getMaxToolTimeoutMs(): number;
12
+ //# sourceMappingURL=config.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"config.d.ts","sourceRoot":"","sources":["../../../../src/modules/shared/config.ts"],"names":[],"mappings":"AAEA;;;;;;;;;GASG;AACH,wBAAgB,mBAAmB,IAAI,MAAM,CAY5C"}
@@ -0,0 +1,33 @@
1
+ const DEFAULT_MAX_TIMEOUT_MS = 300_000;
2
+ /**
3
+ * Resolve the configurable max clamp (ms) for tool wait timeouts.
4
+ *
5
+ * Precedence: the `MCP_TOOL_TIMEOUT` environment variable wins over an
6
+ * `MCP_TOOL_TIMEOUT=<ms>` CLI arg, which wins over the built-in default of
7
+ * 300000ms (5 min). Invalid/non-numeric values fall back to the default.
8
+ *
9
+ * Reads `process.env` / `process.argv` lazily on each call so tests can vary
10
+ * them between invocations without module re-import tricks.
11
+ */
12
+ export function getMaxToolTimeoutMs() {
13
+ const fromEnv = parsePositiveInt(process.env.MCP_TOOL_TIMEOUT);
14
+ if (fromEnv !== undefined)
15
+ return fromEnv;
16
+ const argPrefix = "MCP_TOOL_TIMEOUT=";
17
+ const argEntry = process.argv.find((arg) => arg.startsWith(argPrefix));
18
+ if (argEntry !== undefined) {
19
+ const fromArg = parsePositiveInt(argEntry.slice(argPrefix.length));
20
+ if (fromArg !== undefined)
21
+ return fromArg;
22
+ }
23
+ return DEFAULT_MAX_TIMEOUT_MS;
24
+ }
25
+ function parsePositiveInt(value) {
26
+ if (value === undefined || value.trim() === "")
27
+ return undefined;
28
+ const parsed = Number(value);
29
+ if (!Number.isFinite(parsed) || parsed <= 0)
30
+ return undefined;
31
+ return parsed;
32
+ }
33
+ //# sourceMappingURL=config.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"config.js","sourceRoot":"","sources":["../../../../src/modules/shared/config.ts"],"names":[],"mappings":"AAAA,MAAM,sBAAsB,GAAG,OAAO,CAAC;AAEvC;;;;;;;;;GASG;AACH,MAAM,UAAU,mBAAmB;IACjC,MAAM,OAAO,GAAG,gBAAgB,CAAC,OAAO,CAAC,GAAG,CAAC,gBAAgB,CAAC,CAAC;IAC/D,IAAI,OAAO,KAAK,SAAS;QAAE,OAAO,OAAO,CAAC;IAE1C,MAAM,SAAS,GAAG,mBAAmB,CAAC;IACtC,MAAM,QAAQ,GAAG,OAAO,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,GAAG,EAAE,EAAE,CAAC,GAAG,CAAC,UAAU,CAAC,SAAS,CAAC,CAAC,CAAC;IACvE,IAAI,QAAQ,KAAK,SAAS,EAAE,CAAC;QAC3B,MAAM,OAAO,GAAG,gBAAgB,CAAC,QAAQ,CAAC,KAAK,CAAC,SAAS,CAAC,MAAM,CAAC,CAAC,CAAC;QACnE,IAAI,OAAO,KAAK,SAAS;YAAE,OAAO,OAAO,CAAC;IAC5C,CAAC;IAED,OAAO,sBAAsB,CAAC;AAChC,CAAC;AAED,SAAS,gBAAgB,CAAC,KAAyB;IACjD,IAAI,KAAK,KAAK,SAAS,IAAI,KAAK,CAAC,IAAI,EAAE,KAAK,EAAE;QAAE,OAAO,SAAS,CAAC;IACjE,MAAM,MAAM,GAAG,MAAM,CAAC,KAAK,CAAC,CAAC;IAC7B,IAAI,CAAC,MAAM,CAAC,QAAQ,CAAC,MAAM,CAAC,IAAI,MAAM,IAAI,CAAC;QAAE,OAAO,SAAS,CAAC;IAC9D,OAAO,MAAM,CAAC;AAChB,CAAC"}
@@ -0,0 +1,16 @@
1
+ /** Serialize a payload as an MCP text tool result. */
2
+ export declare function jsonResult(payload: unknown): {
3
+ content: {
4
+ type: "text";
5
+ text: string;
6
+ }[];
7
+ };
8
+ /** Serialize a payload as an MCP text tool result flagged as an error. */
9
+ export declare function jsonError(payload: unknown): {
10
+ isError: boolean;
11
+ content: {
12
+ type: "text";
13
+ text: string;
14
+ }[];
15
+ };
16
+ //# sourceMappingURL=mcp-result.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"mcp-result.d.ts","sourceRoot":"","sources":["../../../../src/modules/shared/mcp-result.ts"],"names":[],"mappings":"AAAA,sDAAsD;AACtD,wBAAgB,UAAU,CAAC,OAAO,EAAE,OAAO;;cAErB,MAAM;;;EAE3B;AAED,0EAA0E;AAC1E,wBAAgB,SAAS,CAAC,OAAO,EAAE,OAAO;;;cAGpB,MAAM;;;EAE3B"}
@@ -0,0 +1,14 @@
1
+ /** Serialize a payload as an MCP text tool result. */
2
+ export function jsonResult(payload) {
3
+ return {
4
+ content: [{ type: "text", text: JSON.stringify(payload) }],
5
+ };
6
+ }
7
+ /** Serialize a payload as an MCP text tool result flagged as an error. */
8
+ export function jsonError(payload) {
9
+ return {
10
+ isError: true,
11
+ content: [{ type: "text", text: JSON.stringify(payload) }],
12
+ };
13
+ }
14
+ //# sourceMappingURL=mcp-result.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"mcp-result.js","sourceRoot":"","sources":["../../../../src/modules/shared/mcp-result.ts"],"names":[],"mappings":"AAAA,sDAAsD;AACtD,MAAM,UAAU,UAAU,CAAC,OAAgB;IACzC,OAAO;QACL,OAAO,EAAE,CAAC,EAAE,IAAI,EAAE,MAAe,EAAE,IAAI,EAAE,IAAI,CAAC,SAAS,CAAC,OAAO,CAAC,EAAE,CAAC;KACpE,CAAC;AACJ,CAAC;AAED,0EAA0E;AAC1E,MAAM,UAAU,SAAS,CAAC,OAAgB;IACxC,OAAO;QACL,OAAO,EAAE,IAAI;QACb,OAAO,EAAE,CAAC,EAAE,IAAI,EAAE,MAAe,EAAE,IAAI,EAAE,IAAI,CAAC,SAAS,CAAC,OAAO,CAAC,EAAE,CAAC;KACpE,CAAC;AACJ,CAAC"}
@@ -0,0 +1,27 @@
1
+ import { type AssistantMessage, type OpencodeClient, type Part } from "@opencode-ai/sdk";
2
+ /** Build an HTTP client for a tracked server, or undefined if the id is unknown. */
3
+ export declare function clientForServer(serverId: string): OpencodeClient | undefined;
4
+ /** Resolve a task to its server client and session id, or undefined if unknown. */
5
+ export declare function clientForTask(taskId: string): {
6
+ client: OpencodeClient;
7
+ sessionId: string;
8
+ } | undefined;
9
+ export interface AssistantEntry {
10
+ info: AssistantMessage;
11
+ parts: Part[];
12
+ }
13
+ /** Fetch the most recent assistant message (with its parts) for a session. */
14
+ export declare function lastAssistantEntry(client: OpencodeClient, sessionId: string): Promise<AssistantEntry | undefined>;
15
+ export type TaskStatus = "pending" | "running" | "completed" | "failed";
16
+ export interface TaskStatusResult {
17
+ task_id: string;
18
+ status: TaskStatus;
19
+ error?: string;
20
+ }
21
+ /**
22
+ * Derive the current status of a task by inspecting session busy state and
23
+ * the last assistant message. Shared by opencode_get_task_status and
24
+ * opencode_wait_for_task so both use identical status derivation.
25
+ */
26
+ export declare function deriveTaskStatus(client: OpencodeClient, sessionId: string, taskId: string): Promise<TaskStatusResult>;
27
+ //# sourceMappingURL=opencode-client.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"opencode-client.d.ts","sourceRoot":"","sources":["../../../../src/modules/shared/opencode-client.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,KAAK,gBAAgB,EAErB,KAAK,cAAc,EACnB,KAAK,IAAI,EACV,MAAM,kBAAkB,CAAC;AAI1B,oFAAoF;AACpF,wBAAgB,eAAe,CAAC,QAAQ,EAAE,MAAM,GAAG,cAAc,GAAG,SAAS,CAI5E;AAED,mFAAmF;AACnF,wBAAgB,aAAa,CAC3B,MAAM,EAAE,MAAM,GACb;IAAE,MAAM,EAAE,cAAc,CAAC;IAAC,SAAS,EAAE,MAAM,CAAA;CAAE,GAAG,SAAS,CAM3D;AAED,MAAM,WAAW,cAAc;IAC7B,IAAI,EAAE,gBAAgB,CAAC;IACvB,KAAK,EAAE,IAAI,EAAE,CAAC;CACf;AAED,8EAA8E;AAC9E,wBAAsB,kBAAkB,CACtC,MAAM,EAAE,cAAc,EACtB,SAAS,EAAE,MAAM,GAChB,OAAO,CAAC,cAAc,GAAG,SAAS,CAAC,CAUrC;AAED,MAAM,MAAM,UAAU,GAAG,SAAS,GAAG,SAAS,GAAG,WAAW,GAAG,QAAQ,CAAC;AAExE,MAAM,WAAW,gBAAgB;IAC/B,OAAO,EAAE,MAAM,CAAC;IAChB,MAAM,EAAE,UAAU,CAAC;IACnB,KAAK,CAAC,EAAE,MAAM,CAAC;CAChB;AAED;;;;GAIG;AACH,wBAAsB,gBAAgB,CACpC,MAAM,EAAE,cAAc,EACtB,SAAS,EAAE,MAAM,EACjB,MAAM,EAAE,MAAM,GACb,OAAO,CAAC,gBAAgB,CAAC,CAoB3B"}
@@ -0,0 +1,58 @@
1
+ import { createOpencodeClient, } from "@opencode-ai/sdk";
2
+ import { getServer } from "./server-registry.js";
3
+ import { getTask } from "./task-registry.js";
4
+ /** Build an HTTP client for a tracked server, or undefined if the id is unknown. */
5
+ export function clientForServer(serverId) {
6
+ const server = getServer(serverId);
7
+ if (!server)
8
+ return undefined;
9
+ return createOpencodeClient({ baseUrl: server.baseUrl });
10
+ }
11
+ /** Resolve a task to its server client and session id, or undefined if unknown. */
12
+ export function clientForTask(taskId) {
13
+ const task = getTask(taskId);
14
+ if (!task)
15
+ return undefined;
16
+ const client = clientForServer(task.serverId);
17
+ if (!client)
18
+ return undefined;
19
+ return { client, sessionId: task.sessionId };
20
+ }
21
+ /** Fetch the most recent assistant message (with its parts) for a session. */
22
+ export async function lastAssistantEntry(client, sessionId) {
23
+ const res = await client.session.messages({ path: { id: sessionId } });
24
+ const messages = res.data ?? [];
25
+ for (let i = messages.length - 1; i >= 0; i--) {
26
+ const entry = messages[i];
27
+ if (entry.info.role === "assistant") {
28
+ return { info: entry.info, parts: entry.parts };
29
+ }
30
+ }
31
+ return undefined;
32
+ }
33
+ /**
34
+ * Derive the current status of a task by inspecting session busy state and
35
+ * the last assistant message. Shared by opencode_get_task_status and
36
+ * opencode_wait_for_task so both use identical status derivation.
37
+ */
38
+ export async function deriveTaskStatus(client, sessionId, taskId) {
39
+ // The status map only lists sessions that are actively working.
40
+ const statusRes = await client.session.status();
41
+ const sessionStatus = statusRes.data?.[sessionId];
42
+ if (sessionStatus?.type === "busy" || sessionStatus?.type === "retry") {
43
+ return { task_id: taskId, status: "running" };
44
+ }
45
+ // Not busy: inspect the last assistant message to tell pending from done.
46
+ const entry = await lastAssistantEntry(client, sessionId);
47
+ if (!entry) {
48
+ return { task_id: taskId, status: "pending" };
49
+ }
50
+ if (entry.info.error) {
51
+ return { task_id: taskId, status: "failed", error: entry.info.error.name };
52
+ }
53
+ if (entry.info.time.completed) {
54
+ return { task_id: taskId, status: "completed" };
55
+ }
56
+ return { task_id: taskId, status: "running" };
57
+ }
58
+ //# sourceMappingURL=opencode-client.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"opencode-client.js","sourceRoot":"","sources":["../../../../src/modules/shared/opencode-client.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,10 @@
1
+ export interface OpencodeServerInstance {
2
+ serverId: string;
3
+ baseUrl: string;
4
+ close: () => void;
5
+ }
6
+ export declare function registerServer(instance: OpencodeServerInstance): void;
7
+ export declare function getServer(serverId: string): OpencodeServerInstance | undefined;
8
+ export declare function removeServer(serverId: string): void;
9
+ export declare function killAllServers(): void;
10
+ //# sourceMappingURL=server-registry.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"server-registry.d.ts","sourceRoot":"","sources":["../../../../src/modules/shared/server-registry.ts"],"names":[],"mappings":"AAAA,MAAM,WAAW,sBAAsB;IACrC,QAAQ,EAAE,MAAM,CAAC;IACjB,OAAO,EAAE,MAAM,CAAC;IAChB,KAAK,EAAE,MAAM,IAAI,CAAC;CACnB;AAID,wBAAgB,cAAc,CAAC,QAAQ,EAAE,sBAAsB,QAE9D;AAED,wBAAgB,SAAS,CAAC,QAAQ,EAAE,MAAM,GAAG,sBAAsB,GAAG,SAAS,CAE9E;AAED,wBAAgB,YAAY,CAAC,QAAQ,EAAE,MAAM,QAE5C;AAED,wBAAgB,cAAc,SAK7B"}
@@ -0,0 +1,17 @@
1
+ const servers = new Map();
2
+ export function registerServer(instance) {
3
+ servers.set(instance.serverId, instance);
4
+ }
5
+ export function getServer(serverId) {
6
+ return servers.get(serverId);
7
+ }
8
+ export function removeServer(serverId) {
9
+ servers.delete(serverId);
10
+ }
11
+ export function killAllServers() {
12
+ for (const instance of servers.values()) {
13
+ instance.close();
14
+ }
15
+ servers.clear();
16
+ }
17
+ //# sourceMappingURL=server-registry.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"server-registry.js","sourceRoot":"","sources":["../../../../src/modules/shared/server-registry.ts"],"names":[],"mappings":"AAMA,MAAM,OAAO,GAAG,IAAI,GAAG,EAAkC,CAAC;AAE1D,MAAM,UAAU,cAAc,CAAC,QAAgC;IAC7D,OAAO,CAAC,GAAG,CAAC,QAAQ,CAAC,QAAQ,EAAE,QAAQ,CAAC,CAAC;AAC3C,CAAC;AAED,MAAM,UAAU,SAAS,CAAC,QAAgB;IACxC,OAAO,OAAO,CAAC,GAAG,CAAC,QAAQ,CAAC,CAAC;AAC/B,CAAC;AAED,MAAM,UAAU,YAAY,CAAC,QAAgB;IAC3C,OAAO,CAAC,MAAM,CAAC,QAAQ,CAAC,CAAC;AAC3B,CAAC;AAED,MAAM,UAAU,cAAc;IAC5B,KAAK,MAAM,QAAQ,IAAI,OAAO,CAAC,MAAM,EAAE,EAAE,CAAC;QACxC,QAAQ,CAAC,KAAK,EAAE,CAAC;IACnB,CAAC;IACD,OAAO,CAAC,KAAK,EAAE,CAAC;AAClB,CAAC"}
@@ -0,0 +1,9 @@
1
+ export interface TaskRecord {
2
+ taskId: string;
3
+ serverId: string;
4
+ sessionId: string;
5
+ }
6
+ export declare function registerTask(task: TaskRecord): void;
7
+ export declare function getTask(taskId: string): TaskRecord | undefined;
8
+ export declare function removeTask(taskId: string): void;
9
+ //# sourceMappingURL=task-registry.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"task-registry.d.ts","sourceRoot":"","sources":["../../../../src/modules/shared/task-registry.ts"],"names":[],"mappings":"AAAA,MAAM,WAAW,UAAU;IACzB,MAAM,EAAE,MAAM,CAAC;IACf,QAAQ,EAAE,MAAM,CAAC;IACjB,SAAS,EAAE,MAAM,CAAC;CACnB;AAID,wBAAgB,YAAY,CAAC,IAAI,EAAE,UAAU,QAE5C;AAED,wBAAgB,OAAO,CAAC,MAAM,EAAE,MAAM,GAAG,UAAU,GAAG,SAAS,CAE9D;AAED,wBAAgB,UAAU,CAAC,MAAM,EAAE,MAAM,QAExC"}
@@ -0,0 +1,11 @@
1
+ const tasks = new Map();
2
+ export function registerTask(task) {
3
+ tasks.set(task.taskId, task);
4
+ }
5
+ export function getTask(taskId) {
6
+ return tasks.get(taskId);
7
+ }
8
+ export function removeTask(taskId) {
9
+ tasks.delete(taskId);
10
+ }
11
+ //# sourceMappingURL=task-registry.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"task-registry.js","sourceRoot":"","sources":["../../../../src/modules/shared/task-registry.ts"],"names":[],"mappings":"AAMA,MAAM,KAAK,GAAG,IAAI,GAAG,EAAsB,CAAC;AAE5C,MAAM,UAAU,YAAY,CAAC,IAAgB;IAC3C,KAAK,CAAC,GAAG,CAAC,IAAI,CAAC,MAAM,EAAE,IAAI,CAAC,CAAC;AAC/B,CAAC;AAED,MAAM,UAAU,OAAO,CAAC,MAAc;IACpC,OAAO,KAAK,CAAC,GAAG,CAAC,MAAM,CAAC,CAAC;AAC3B,CAAC;AAED,MAAM,UAAU,UAAU,CAAC,MAAc;IACvC,KAAK,CAAC,MAAM,CAAC,MAAM,CAAC,CAAC;AACvB,CAAC"}
@@ -0,0 +1,3 @@
1
+ import type { McpServer } from "@modelcontextprotocol/sdk/server/mcp.js";
2
+ export declare function registerOpencodeGetTaskResult(server: McpServer): void;
3
+ //# sourceMappingURL=get_task_result.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"get_task_result.d.ts","sourceRoot":"","sources":["../../../../src/modules/tools/get_task_result.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,yCAAyC,CAAC;AAKzE,wBAAgB,6BAA6B,CAAC,MAAM,EAAE,SAAS,QAgD9D"}
@@ -0,0 +1,47 @@
1
+ import { z } from "zod";
2
+ import { jsonError, jsonResult } from "../shared/mcp-result.js";
3
+ import { clientForTask, lastAssistantEntry } from "../shared/opencode-client.js";
4
+ export function registerOpencodeGetTaskResult(server) {
5
+ server.registerTool("opencode_get_task_result", {
6
+ description: "Get the final result of a completed task",
7
+ inputSchema: {
8
+ task_id: z.string().describe("Id of the task to fetch the result for"),
9
+ },
10
+ }, async ({ task_id }) => {
11
+ const resolved = clientForTask(task_id);
12
+ if (!resolved) {
13
+ return jsonError({ task_id, status: "not_found" });
14
+ }
15
+ const { client, sessionId } = resolved;
16
+ try {
17
+ const entry = await lastAssistantEntry(client, sessionId);
18
+ if (!entry) {
19
+ return jsonResult({ task_id, status: "pending", result: null });
20
+ }
21
+ if (entry.info.error) {
22
+ return jsonResult({
23
+ task_id,
24
+ status: "failed",
25
+ error: entry.info.error.name,
26
+ result: null,
27
+ });
28
+ }
29
+ if (!entry.info.time.completed) {
30
+ return jsonResult({ task_id, status: "running", result: null });
31
+ }
32
+ const text = entry.parts
33
+ .filter((part) => part.type === "text")
34
+ .map((part) => part.text)
35
+ .join("");
36
+ return jsonResult({ task_id, status: "completed", result: text });
37
+ }
38
+ catch (error) {
39
+ return jsonError({
40
+ task_id,
41
+ status: "error",
42
+ message: error instanceof Error ? error.message : String(error),
43
+ });
44
+ }
45
+ });
46
+ }
47
+ //# sourceMappingURL=get_task_result.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"get_task_result.js","sourceRoot":"","sources":["../../../../src/modules/tools/get_task_result.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AACxB,OAAO,EAAE,SAAS,EAAE,UAAU,EAAE,MAAM,yBAAyB,CAAC;AAChE,OAAO,EAAE,aAAa,EAAE,kBAAkB,EAAE,MAAM,8BAA8B,CAAC;AAEjF,MAAM,UAAU,6BAA6B,CAAC,MAAiB;IAC7D,MAAM,CAAC,YAAY,CACjB,0BAA0B,EAC1B;QACE,WAAW,EAAE,0CAA0C;QACvD,WAAW,EAAE;YACX,OAAO,EAAE,CAAC,CAAC,MAAM,EAAE,CAAC,QAAQ,CAAC,wCAAwC,CAAC;SACvE;KACF,EACD,KAAK,EAAE,EAAE,OAAO,EAAE,EAAE,EAAE;QACpB,MAAM,QAAQ,GAAG,aAAa,CAAC,OAAO,CAAC,CAAC;QACxC,IAAI,CAAC,QAAQ,EAAE,CAAC;YACd,OAAO,SAAS,CAAC,EAAE,OAAO,EAAE,MAAM,EAAE,WAAW,EAAE,CAAC,CAAC;QACrD,CAAC;QACD,MAAM,EAAE,MAAM,EAAE,SAAS,EAAE,GAAG,QAAQ,CAAC;QAEvC,IAAI,CAAC;YACH,MAAM,KAAK,GAAG,MAAM,kBAAkB,CAAC,MAAM,EAAE,SAAS,CAAC,CAAC;YAC1D,IAAI,CAAC,KAAK,EAAE,CAAC;gBACX,OAAO,UAAU,CAAC,EAAE,OAAO,EAAE,MAAM,EAAE,SAAS,EAAE,MAAM,EAAE,IAAI,EAAE,CAAC,CAAC;YAClE,CAAC;YACD,IAAI,KAAK,CAAC,IAAI,CAAC,KAAK,EAAE,CAAC;gBACrB,OAAO,UAAU,CAAC;oBAChB,OAAO;oBACP,MAAM,EAAE,QAAQ;oBAChB,KAAK,EAAE,KAAK,CAAC,IAAI,CAAC,KAAK,CAAC,IAAI;oBAC5B,MAAM,EAAE,IAAI;iBACb,CAAC,CAAC;YACL,CAAC;YACD,IAAI,CAAC,KAAK,CAAC,IAAI,CAAC,IAAI,CAAC,SAAS,EAAE,CAAC;gBAC/B,OAAO,UAAU,CAAC,EAAE,OAAO,EAAE,MAAM,EAAE,SAAS,EAAE,MAAM,EAAE,IAAI,EAAE,CAAC,CAAC;YAClE,CAAC;YAED,MAAM,IAAI,GAAG,KAAK,CAAC,KAAK;iBACrB,MAAM,CAAC,CAAC,IAAI,EAAkD,EAAE,CAAC,IAAI,CAAC,IAAI,KAAK,MAAM,CAAC;iBACtF,GAAG,CAAC,CAAC,IAAI,EAAE,EAAE,CAAC,IAAI,CAAC,IAAI,CAAC;iBACxB,IAAI,CAAC,EAAE,CAAC,CAAC;YAEZ,OAAO,UAAU,CAAC,EAAE,OAAO,EAAE,MAAM,EAAE,WAAW,EAAE,MAAM,EAAE,IAAI,EAAE,CAAC,CAAC;QACpE,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACf,OAAO,SAAS,CAAC;gBACf,OAAO;gBACP,MAAM,EAAE,OAAO;gBACf,OAAO,EAAE,KAAK,YAAY,KAAK,CAAC,CAAC,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC,CAAC,MAAM,CAAC,KAAK,CAAC;aAChE,CAAC,CAAC;QACL,CAAC;IACH,CAAC,CACF,CAAC;AACJ,CAAC"}
@@ -0,0 +1,3 @@
1
+ import type { McpServer } from "@modelcontextprotocol/sdk/server/mcp.js";
2
+ export declare function registerOpencodeGetTaskStatus(server: McpServer): void;
3
+ //# sourceMappingURL=get_task_status.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"get_task_status.d.ts","sourceRoot":"","sources":["../../../../src/modules/tools/get_task_status.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,yCAAyC,CAAC;AAKzE,wBAAgB,6BAA6B,CAAC,MAAM,EAAE,SAAS,QA4B9D"}
@@ -0,0 +1,29 @@
1
+ import { z } from "zod";
2
+ import { jsonError, jsonResult } from "../shared/mcp-result.js";
3
+ import { clientForTask, deriveTaskStatus } from "../shared/opencode-client.js";
4
+ export function registerOpencodeGetTaskStatus(server) {
5
+ server.registerTool("opencode_get_task_status", {
6
+ description: "Get the current status of a delegated task",
7
+ inputSchema: {
8
+ task_id: z.string().describe("Id of the task to check"),
9
+ },
10
+ }, async ({ task_id }) => {
11
+ const resolved = clientForTask(task_id);
12
+ if (!resolved) {
13
+ return jsonError({ task_id, status: "not_found" });
14
+ }
15
+ const { client, sessionId } = resolved;
16
+ try {
17
+ const result = await deriveTaskStatus(client, sessionId, task_id);
18
+ return jsonResult(result);
19
+ }
20
+ catch (error) {
21
+ return jsonError({
22
+ task_id,
23
+ status: "error",
24
+ message: error instanceof Error ? error.message : String(error),
25
+ });
26
+ }
27
+ });
28
+ }
29
+ //# sourceMappingURL=get_task_status.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"get_task_status.js","sourceRoot":"","sources":["../../../../src/modules/tools/get_task_status.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AACxB,OAAO,EAAE,SAAS,EAAE,UAAU,EAAE,MAAM,yBAAyB,CAAC;AAChE,OAAO,EAAE,aAAa,EAAE,gBAAgB,EAAE,MAAM,8BAA8B,CAAC;AAE/E,MAAM,UAAU,6BAA6B,CAAC,MAAiB;IAC7D,MAAM,CAAC,YAAY,CACjB,0BAA0B,EAC1B;QACE,WAAW,EAAE,4CAA4C;QACzD,WAAW,EAAE;YACX,OAAO,EAAE,CAAC,CAAC,MAAM,EAAE,CAAC,QAAQ,CAAC,yBAAyB,CAAC;SACxD;KACF,EACD,KAAK,EAAE,EAAE,OAAO,EAAE,EAAE,EAAE;QACpB,MAAM,QAAQ,GAAG,aAAa,CAAC,OAAO,CAAC,CAAC;QACxC,IAAI,CAAC,QAAQ,EAAE,CAAC;YACd,OAAO,SAAS,CAAC,EAAE,OAAO,EAAE,MAAM,EAAE,WAAW,EAAE,CAAC,CAAC;QACrD,CAAC;QACD,MAAM,EAAE,MAAM,EAAE,SAAS,EAAE,GAAG,QAAQ,CAAC;QAEvC,IAAI,CAAC;YACH,MAAM,MAAM,GAAG,MAAM,gBAAgB,CAAC,MAAM,EAAE,SAAS,EAAE,OAAO,CAAC,CAAC;YAClE,OAAO,UAAU,CAAC,MAAM,CAAC,CAAC;QAC5B,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACf,OAAO,SAAS,CAAC;gBACf,OAAO;gBACP,MAAM,EAAE,OAAO;gBACf,OAAO,EAAE,KAAK,YAAY,KAAK,CAAC,CAAC,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC,CAAC,MAAM,CAAC,KAAK,CAAC;aAChE,CAAC,CAAC;QACL,CAAC;IACH,CAAC,CACF,CAAC;AACJ,CAAC"}
@@ -0,0 +1,3 @@
1
+ import type { McpServer } from "@modelcontextprotocol/sdk/server/mcp.js";
2
+ export declare function registerTools(server: McpServer): void;
3
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../../src/modules/tools/index.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,yCAAyC,CAAC;AAUzE,wBAAgB,aAAa,CAAC,MAAM,EAAE,SAAS,QAQ9C"}