@nextfreelatech/xpec-mcp 1.0.1
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/LICENSE +201 -0
- package/README.md +450 -0
- package/dist/cli.js +242 -0
- package/dist/cli.js.map +1 -0
- package/dist/client.js +269 -0
- package/dist/client.js.map +1 -0
- package/dist/config.js +159 -0
- package/dist/config.js.map +1 -0
- package/dist/errors.js +100 -0
- package/dist/errors.js.map +1 -0
- package/dist/http.js +147 -0
- package/dist/http.js.map +1 -0
- package/dist/index.js +9 -0
- package/dist/index.js.map +1 -0
- package/dist/logger.js +29 -0
- package/dist/logger.js.map +1 -0
- package/dist/resources.js +181 -0
- package/dist/resources.js.map +1 -0
- package/dist/server.js +84 -0
- package/dist/server.js.map +1 -0
- package/dist/tools.js +398 -0
- package/dist/tools.js.map +1 -0
- package/package.json +43 -0
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"resources.js","sourceRoot":"","sources":["../src/resources.ts"],"names":[],"mappings":"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"}
|
package/dist/server.js
ADDED
|
@@ -0,0 +1,84 @@
|
|
|
1
|
+
// Build the MCP server, register tools/resources, and connect a stdio
|
|
2
|
+
// transport. Kept distinct from the CLI so tests can construct the server
|
|
3
|
+
// without spawning a child process.
|
|
4
|
+
import { McpServer } from "@modelcontextprotocol/sdk/server/mcp.js";
|
|
5
|
+
import { StdioServerTransport } from "@modelcontextprotocol/sdk/server/stdio.js";
|
|
6
|
+
import { XpecClient } from "./client.js";
|
|
7
|
+
import { McpToolError } from "./errors.js";
|
|
8
|
+
import { logger } from "./logger.js";
|
|
9
|
+
import { registerReadTools, registerWriteTools } from "./tools.js";
|
|
10
|
+
import { registerResources } from "./resources.js";
|
|
11
|
+
const SERVER_NAME = "@nextfreelatech/xpec-mcp";
|
|
12
|
+
const SERVER_VERSION = "1.0.1";
|
|
13
|
+
export function buildServer(options) {
|
|
14
|
+
const { config } = options;
|
|
15
|
+
if (!config.token) {
|
|
16
|
+
throw new Error("XPEC_API_TOKEN is required. Generate one at /settings/developer.");
|
|
17
|
+
}
|
|
18
|
+
const server = new McpServer({ name: SERVER_NAME, version: SERVER_VERSION }, {
|
|
19
|
+
capabilities: {
|
|
20
|
+
tools: {},
|
|
21
|
+
resources: {},
|
|
22
|
+
logging: {},
|
|
23
|
+
},
|
|
24
|
+
});
|
|
25
|
+
const client = options.client ??
|
|
26
|
+
new XpecClient({ apiUrl: config.apiUrl, token: config.token });
|
|
27
|
+
registerReadTools(server, { client, config });
|
|
28
|
+
registerWriteTools(server, { client, config });
|
|
29
|
+
registerResources(server, { client, config });
|
|
30
|
+
return server;
|
|
31
|
+
}
|
|
32
|
+
/**
|
|
33
|
+
* Resolves only when the transport's `onclose` fires. Used to keep the
|
|
34
|
+
* stdio process alive after `server.connect()` returns — without this, the
|
|
35
|
+
* CLI exits before the agent can send `initialize`.
|
|
36
|
+
*/
|
|
37
|
+
export function waitForTransportClose(transport) {
|
|
38
|
+
return new Promise((resolve) => {
|
|
39
|
+
const prev = transport.onclose;
|
|
40
|
+
transport.onclose = () => {
|
|
41
|
+
prev?.();
|
|
42
|
+
resolve();
|
|
43
|
+
};
|
|
44
|
+
});
|
|
45
|
+
}
|
|
46
|
+
export async function runStdio(config) {
|
|
47
|
+
const server = buildServer({ config });
|
|
48
|
+
const transport = new StdioServerTransport();
|
|
49
|
+
await server.connect(transport);
|
|
50
|
+
logger.info("mcp server connected", {
|
|
51
|
+
transport: "stdio",
|
|
52
|
+
apiUrl: config.apiUrl,
|
|
53
|
+
apiUrlSource: config.apiUrlSource,
|
|
54
|
+
bindingMode: config.bindingMode,
|
|
55
|
+
workspaceId: config.workspaceId ?? undefined,
|
|
56
|
+
workspaceSource: config.workspaceSource,
|
|
57
|
+
productId: config.productId ?? undefined,
|
|
58
|
+
productSource: config.productSource,
|
|
59
|
+
});
|
|
60
|
+
await waitForTransportClose(transport);
|
|
61
|
+
}
|
|
62
|
+
/**
|
|
63
|
+
* Phase 4 startup probe: detect the legacy `.xpec.json` shape
|
|
64
|
+
* (`{"workspaceId": "<old id>"}` whose value is now a Product id, not a
|
|
65
|
+
* Workspace id) and emit `LEGACY_BINDING_DETECTED` with an exact remediation
|
|
66
|
+
* (per mcp-workspace-tools.md §5). Returns `null` when the binding looks
|
|
67
|
+
* fine; returns an `McpToolError` the CLI can print and exit on.
|
|
68
|
+
*
|
|
69
|
+
* Triggers when:
|
|
70
|
+
* * `workspaceId` is set on the binding, AND
|
|
71
|
+
* * the API confirms it resolves to a Product (not a Workspace).
|
|
72
|
+
*
|
|
73
|
+
* Best-effort: API errors other than 404 propagate so transient connectivity
|
|
74
|
+
* problems don't masquerade as the legacy shape.
|
|
75
|
+
*/
|
|
76
|
+
export async function detectLegacyBinding(config, client) {
|
|
77
|
+
if (!config.workspaceId)
|
|
78
|
+
return null;
|
|
79
|
+
const shape = await client.resolveIdShape(config.workspaceId);
|
|
80
|
+
if (shape !== "product")
|
|
81
|
+
return null;
|
|
82
|
+
return new McpToolError("LEGACY_BINDING_DETECTED", `The "workspaceId" in .xpec.json (${config.workspaceId}) refers to a Product under the new model.`, 'Edit .xpec.json: rename "workspaceId" to "productId" to keep current behaviour. To bind a Workspace, create one and set both ids.');
|
|
83
|
+
}
|
|
84
|
+
//# sourceMappingURL=server.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"server.js","sourceRoot":"","sources":["../src/server.ts"],"names":[],"mappings":"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"}
|
package/dist/tools.js
ADDED
|
@@ -0,0 +1,398 @@
|
|
|
1
|
+
// Tool registration for the MCP server (per Xpec spec "mcp-server" §6
|
|
2
|
+
// "Tool naming"). Read-only surface for MVP — write tools land with
|
|
3
|
+
// feature #4 (MCP Specification Version Tools).
|
|
4
|
+
import { z } from "zod";
|
|
5
|
+
import { McpToolError, buildClientFailure, } from "./errors.js";
|
|
6
|
+
import { logger } from "./logger.js";
|
|
7
|
+
/**
|
|
8
|
+
* Resolves the effective product id — explicit argument wins, then the
|
|
9
|
+
* config's `productId` (file or env). Throws PRODUCT_NOT_BOUND when
|
|
10
|
+
* neither is present.
|
|
11
|
+
*/
|
|
12
|
+
function requireProductId(config, explicit) {
|
|
13
|
+
if (explicit && explicit.length > 0)
|
|
14
|
+
return explicit;
|
|
15
|
+
if (config.productId)
|
|
16
|
+
return config.productId;
|
|
17
|
+
throw new McpToolError("PRODUCT_NOT_BOUND", "No product is bound to this MCP session.", "Call list_products, pick one, then add it to .xpec.json or set XPEC_PRODUCT_ID.");
|
|
18
|
+
}
|
|
19
|
+
/**
|
|
20
|
+
* Phase 4: Workspace counterpart. Throws WORKSPACE_NOT_BOUND when the
|
|
21
|
+
* binding doesn't include a Workspace id.
|
|
22
|
+
*/
|
|
23
|
+
function requireWorkspaceId(config, explicit) {
|
|
24
|
+
if (explicit && explicit.length > 0)
|
|
25
|
+
return explicit;
|
|
26
|
+
if (config.workspaceId)
|
|
27
|
+
return config.workspaceId;
|
|
28
|
+
throw new McpToolError("WORKSPACE_NOT_BOUND", "No workspace is bound to this MCP session.", "Call list_workspaces, pick one, then add it to .xpec.json as `workspaceId` or set XPEC_WORKSPACE_ID.");
|
|
29
|
+
}
|
|
30
|
+
/**
|
|
31
|
+
* Phase 4 default-scope resolution for `list_specifications`:
|
|
32
|
+
* * Both binding ids set → Product's specs
|
|
33
|
+
* * workspaceId only → Workspace's own specs
|
|
34
|
+
* * productId only → Product's specs
|
|
35
|
+
* * Explicit `scope` arg → honoured (with the matching id
|
|
36
|
+
* from args or the binding)
|
|
37
|
+
*/
|
|
38
|
+
function resolveListSpecificationsTarget(config, args) {
|
|
39
|
+
// Explicit scope wins — but the corresponding id must resolve.
|
|
40
|
+
if (args.scope === "workspace") {
|
|
41
|
+
return { scope: "workspace", id: requireWorkspaceId(config, args.workspaceId) };
|
|
42
|
+
}
|
|
43
|
+
if (args.scope === "product") {
|
|
44
|
+
return { scope: "product", id: requireProductId(config, args.productId) };
|
|
45
|
+
}
|
|
46
|
+
// Explicit ids without a scope arg also win.
|
|
47
|
+
if (args.productId) {
|
|
48
|
+
return { scope: "product", id: args.productId };
|
|
49
|
+
}
|
|
50
|
+
if (args.workspaceId) {
|
|
51
|
+
return { scope: "workspace", id: args.workspaceId };
|
|
52
|
+
}
|
|
53
|
+
// Fall back to the binding-mode default per spec §3.
|
|
54
|
+
if (config.productId)
|
|
55
|
+
return { scope: "product", id: config.productId };
|
|
56
|
+
if (config.workspaceId)
|
|
57
|
+
return { scope: "workspace", id: config.workspaceId };
|
|
58
|
+
throw new McpToolError("PRODUCT_NOT_BOUND", "No product or workspace is bound to this MCP session.", "Call list_products or list_workspaces to discover ids, then bind in .xpec.json.");
|
|
59
|
+
}
|
|
60
|
+
/**
|
|
61
|
+
* Search defaults to the Workspace cross-scope endpoint when bound to a
|
|
62
|
+
* Workspace; that endpoint searches both Workspace specs and every member
|
|
63
|
+
* Product. With only a Product binding it falls through to the
|
|
64
|
+
* Product-scoped search.
|
|
65
|
+
*/
|
|
66
|
+
function resolveSearchSpecificationsTarget(config, args) {
|
|
67
|
+
if (args.scope === "workspace") {
|
|
68
|
+
return { scope: "workspace", id: requireWorkspaceId(config, args.workspaceId) };
|
|
69
|
+
}
|
|
70
|
+
if (args.scope === "product") {
|
|
71
|
+
return { scope: "product", id: requireProductId(config, args.productId) };
|
|
72
|
+
}
|
|
73
|
+
if (args.workspaceId) {
|
|
74
|
+
return { scope: "workspace", id: args.workspaceId };
|
|
75
|
+
}
|
|
76
|
+
if (args.productId) {
|
|
77
|
+
return { scope: "product", id: args.productId };
|
|
78
|
+
}
|
|
79
|
+
if (config.workspaceId) {
|
|
80
|
+
return { scope: "workspace", id: config.workspaceId };
|
|
81
|
+
}
|
|
82
|
+
if (config.productId) {
|
|
83
|
+
return { scope: "product", id: config.productId };
|
|
84
|
+
}
|
|
85
|
+
throw new McpToolError("PRODUCT_NOT_BOUND", "No product or workspace is bound to this MCP session.", "Call list_products or list_workspaces to discover ids, then bind in .xpec.json.");
|
|
86
|
+
}
|
|
87
|
+
function ok(data) {
|
|
88
|
+
return {
|
|
89
|
+
content: [{ type: "text", text: JSON.stringify(data, null, 2) }],
|
|
90
|
+
structuredContent: typeof data === "object" && data !== null
|
|
91
|
+
? data
|
|
92
|
+
: { value: data },
|
|
93
|
+
};
|
|
94
|
+
}
|
|
95
|
+
function fail(failure) {
|
|
96
|
+
return {
|
|
97
|
+
content: [
|
|
98
|
+
{
|
|
99
|
+
type: "text",
|
|
100
|
+
text: `${failure.code}: ${failure.message}\n\n${failure.remediation}`,
|
|
101
|
+
},
|
|
102
|
+
],
|
|
103
|
+
isError: true,
|
|
104
|
+
structuredContent: failure,
|
|
105
|
+
};
|
|
106
|
+
}
|
|
107
|
+
/**
|
|
108
|
+
* Wrap an async tool body so any thrown McpToolError translates to a
|
|
109
|
+
* structured tool failure. Anything else maps to INTERNAL_ERROR — agents
|
|
110
|
+
* can decide whether to retry. Tool calls also emit a debug log line
|
|
111
|
+
* matching the spec's `tool / productId / specId / durationMs / errorCode`
|
|
112
|
+
* shape.
|
|
113
|
+
*/
|
|
114
|
+
async function runTool(name, context, body) {
|
|
115
|
+
const startedAt = Date.now();
|
|
116
|
+
try {
|
|
117
|
+
const result = await body();
|
|
118
|
+
logger.debug("tool", {
|
|
119
|
+
tool: name,
|
|
120
|
+
durationMs: Date.now() - startedAt,
|
|
121
|
+
...context,
|
|
122
|
+
});
|
|
123
|
+
return result;
|
|
124
|
+
}
|
|
125
|
+
catch (err) {
|
|
126
|
+
const durationMs = Date.now() - startedAt;
|
|
127
|
+
if (err instanceof McpToolError) {
|
|
128
|
+
logger.warn("tool failed", {
|
|
129
|
+
tool: name,
|
|
130
|
+
durationMs,
|
|
131
|
+
errorCode: err.code,
|
|
132
|
+
...context,
|
|
133
|
+
});
|
|
134
|
+
return fail(err.toFailure());
|
|
135
|
+
}
|
|
136
|
+
logger.error("tool crashed", {
|
|
137
|
+
tool: name,
|
|
138
|
+
durationMs,
|
|
139
|
+
errorCode: "INTERNAL_ERROR",
|
|
140
|
+
err: err.message,
|
|
141
|
+
...context,
|
|
142
|
+
});
|
|
143
|
+
return fail(buildClientFailure("INTERNAL_ERROR", err.message ?? "Unexpected MCP server error."));
|
|
144
|
+
}
|
|
145
|
+
}
|
|
146
|
+
export function registerReadTools(server, deps) {
|
|
147
|
+
const { client, config } = deps;
|
|
148
|
+
server.registerTool("list_products", {
|
|
149
|
+
title: "List products",
|
|
150
|
+
description: "List Products visible to this token. With a Workspace binding, returns the Workspace's member Products; without, returns orphan Products (Products not attached to any Workspace). Read-only. Use this to discover a productId to bind.",
|
|
151
|
+
inputSchema: {
|
|
152
|
+
workspaceId: z.string().optional(),
|
|
153
|
+
},
|
|
154
|
+
}, async (args) => runTool("list_products", { workspaceId: args.workspaceId }, async () => {
|
|
155
|
+
// Default: when bound to a Workspace, list its member Products.
|
|
156
|
+
// Otherwise list orphan Products so the agent can pick one to bind.
|
|
157
|
+
const explicit = args.workspaceId;
|
|
158
|
+
const wsId = explicit ?? config.workspaceId ?? undefined;
|
|
159
|
+
const res = await client.listProducts(wsId ? { workspaceId: wsId } : { orphan: true });
|
|
160
|
+
return ok(res.body);
|
|
161
|
+
}));
|
|
162
|
+
server.registerTool("list_workspaces", {
|
|
163
|
+
title: "List workspaces",
|
|
164
|
+
description: "List Workspaces visible to this token. Read-only. Use this when discovering which Workspace to bind in .xpec.json.",
|
|
165
|
+
inputSchema: {},
|
|
166
|
+
}, async () => runTool("list_workspaces", {}, async () => {
|
|
167
|
+
const res = await client.listWorkspaces();
|
|
168
|
+
return ok(res.body);
|
|
169
|
+
}));
|
|
170
|
+
server.registerTool("read_product", {
|
|
171
|
+
title: "Read a product",
|
|
172
|
+
description: "Read a Product's metadata: name, description, specificationManagementType, and member-of Workspace (when set). Read-only.",
|
|
173
|
+
inputSchema: {
|
|
174
|
+
productId: z.string().optional(),
|
|
175
|
+
},
|
|
176
|
+
}, async (args) => runTool("read_product", { productId: args.productId }, async () => {
|
|
177
|
+
const productId = requireProductId(config, args.productId);
|
|
178
|
+
const res = await client.readProduct(productId);
|
|
179
|
+
return ok(res.body);
|
|
180
|
+
}));
|
|
181
|
+
server.registerTool("read_workspace", {
|
|
182
|
+
title: "Read a workspace",
|
|
183
|
+
description: "Read a Workspace's metadata: name, description, specificationManagementType, archived state. Read-only.",
|
|
184
|
+
inputSchema: {
|
|
185
|
+
workspaceId: z.string().optional(),
|
|
186
|
+
},
|
|
187
|
+
}, async (args) => runTool("read_workspace", { workspaceId: args.workspaceId }, async () => {
|
|
188
|
+
const wsId = requireWorkspaceId(config, args.workspaceId);
|
|
189
|
+
const res = await client.readWorkspace(wsId);
|
|
190
|
+
return ok(res.body);
|
|
191
|
+
}));
|
|
192
|
+
server.registerTool("list_specifications", {
|
|
193
|
+
title: "List specifications",
|
|
194
|
+
description: "List specifications in scope. Read-only. Default scope follows the binding: when both workspaceId and productId are bound, lists the Product's specs; with only workspaceId, lists the Workspace's own specs; with only productId, lists the Product's specs. Pass `scope` and/or `productId`/`workspaceId` to override. Filters are type-aware: Free scopes accept folder/tag; Web Application Products accept the BUSINESS/UX/DESIGN_SYSTEM type filter.",
|
|
195
|
+
inputSchema: {
|
|
196
|
+
scope: z.enum(["workspace", "product"]).optional(),
|
|
197
|
+
productId: z.string().optional(),
|
|
198
|
+
workspaceId: z.string().optional(),
|
|
199
|
+
type: z
|
|
200
|
+
.enum(["BUSINESS", "UX", "DESIGN_SYSTEM", "DOCUMENT"])
|
|
201
|
+
.optional(),
|
|
202
|
+
status: z
|
|
203
|
+
.enum(["DRAFT", "GENERATING", "NEEDS_REVIEW", "REVIEWED"])
|
|
204
|
+
.optional(),
|
|
205
|
+
folder: z.string().optional(),
|
|
206
|
+
tags: z.array(z.string()).optional(),
|
|
207
|
+
query: z.string().optional(),
|
|
208
|
+
cursor: z.string().optional(),
|
|
209
|
+
limit: z.number().int().min(1).max(100).optional(),
|
|
210
|
+
},
|
|
211
|
+
}, async (args) => runTool("list_specifications", {
|
|
212
|
+
scope: args.scope,
|
|
213
|
+
productId: args.productId,
|
|
214
|
+
workspaceId: args.workspaceId,
|
|
215
|
+
}, async () => {
|
|
216
|
+
const target = resolveListSpecificationsTarget(config, args);
|
|
217
|
+
const query = {
|
|
218
|
+
type: args.type,
|
|
219
|
+
status: args.status,
|
|
220
|
+
folder: args.folder,
|
|
221
|
+
tags: args.tags,
|
|
222
|
+
query: args.query,
|
|
223
|
+
cursor: args.cursor,
|
|
224
|
+
limit: args.limit,
|
|
225
|
+
};
|
|
226
|
+
const res = target.scope === "workspace"
|
|
227
|
+
? await client.listSpecificationsForWorkspace(target.id, query)
|
|
228
|
+
: await client.listSpecifications(target.id, query);
|
|
229
|
+
return ok(res.body);
|
|
230
|
+
}));
|
|
231
|
+
server.registerTool("search_specifications", {
|
|
232
|
+
title: "Search specifications",
|
|
233
|
+
description: "Lexical full-text search across spec titles and content. Read-only. With a Workspace binding, searches both the Workspace's specs and every member Product; results carry a `scope` discriminator. With only a Product binding, searches that Product's specs.",
|
|
234
|
+
inputSchema: {
|
|
235
|
+
scope: z.enum(["workspace", "product"]).optional(),
|
|
236
|
+
productId: z.string().optional(),
|
|
237
|
+
workspaceId: z.string().optional(),
|
|
238
|
+
query: z.string().min(1).max(200),
|
|
239
|
+
limit: z.number().int().min(1).max(50).optional(),
|
|
240
|
+
includeArchived: z.boolean().optional(),
|
|
241
|
+
},
|
|
242
|
+
}, async (args) => runTool("search_specifications", {
|
|
243
|
+
scope: args.scope,
|
|
244
|
+
productId: args.productId,
|
|
245
|
+
workspaceId: args.workspaceId,
|
|
246
|
+
}, async () => {
|
|
247
|
+
const target = resolveSearchSpecificationsTarget(config, args);
|
|
248
|
+
const query = {
|
|
249
|
+
query: args.query,
|
|
250
|
+
limit: args.limit,
|
|
251
|
+
includeArchived: args.includeArchived,
|
|
252
|
+
};
|
|
253
|
+
const res = target.scope === "workspace"
|
|
254
|
+
? await client.searchSpecificationsForWorkspace(target.id, query)
|
|
255
|
+
: await client.searchSpecifications(target.id, query);
|
|
256
|
+
return ok(res.body);
|
|
257
|
+
}));
|
|
258
|
+
server.registerTool("read_specification", {
|
|
259
|
+
title: "Read a specification",
|
|
260
|
+
description: 'Read the current Markdown content of a specification. Read-only. Returns the document plus status and version. Use format="rendered" when the agent should ignore open-question and assumption markers.',
|
|
261
|
+
inputSchema: {
|
|
262
|
+
specId: z.string().min(1),
|
|
263
|
+
format: z.enum(["raw", "rendered"]).optional(),
|
|
264
|
+
},
|
|
265
|
+
}, async (args) => runTool("read_specification", { specId: args.specId }, async () => {
|
|
266
|
+
const res = await client.readSpecification(args.specId, {
|
|
267
|
+
format: args.format,
|
|
268
|
+
});
|
|
269
|
+
if ("notModified" in res) {
|
|
270
|
+
// Not reachable from a tool call (no If-None-Match passed) but
|
|
271
|
+
// typed exhaustively for safety.
|
|
272
|
+
return ok({ notModified: true, etag: res.etag });
|
|
273
|
+
}
|
|
274
|
+
return ok(res.body);
|
|
275
|
+
}));
|
|
276
|
+
server.registerTool("list_specification_versions", {
|
|
277
|
+
title: "List approved versions",
|
|
278
|
+
description: "List the approved (user-marked Reviewed) snapshots for a specification, newest first. Read-only.",
|
|
279
|
+
inputSchema: {
|
|
280
|
+
specId: z.string().min(1),
|
|
281
|
+
},
|
|
282
|
+
}, async (args) => runTool("list_specification_versions", { specId: args.specId }, async () => {
|
|
283
|
+
const res = await client.listSpecificationVersions(args.specId);
|
|
284
|
+
return ok(res.body);
|
|
285
|
+
}));
|
|
286
|
+
server.registerTool("read_specification_version", {
|
|
287
|
+
title: "Read an approved version",
|
|
288
|
+
description: "Read the full Markdown of a specific approved revision. Read-only. Use this with list_specification_versions to compare past wording with current content.",
|
|
289
|
+
inputSchema: {
|
|
290
|
+
specId: z.string().min(1),
|
|
291
|
+
revisionId: z.string().min(1),
|
|
292
|
+
},
|
|
293
|
+
}, async (args) => runTool("read_specification_version", { specId: args.specId }, async () => {
|
|
294
|
+
const res = await client.readSpecificationVersion(args.specId, args.revisionId);
|
|
295
|
+
if ("notModified" in res) {
|
|
296
|
+
return ok({ notModified: true, etag: res.etag });
|
|
297
|
+
}
|
|
298
|
+
return ok(res.body);
|
|
299
|
+
}));
|
|
300
|
+
server.registerTool("list_open_questions", {
|
|
301
|
+
title: "List open questions",
|
|
302
|
+
description: "List the questions and assumptions attached to a specification. Read-only. Resolved or dismissed items are excluded by default; pass includeResolved=true to surface the full set.",
|
|
303
|
+
inputSchema: {
|
|
304
|
+
specId: z.string().min(1),
|
|
305
|
+
includeResolved: z.boolean().optional(),
|
|
306
|
+
},
|
|
307
|
+
}, async (args) => runTool("list_open_questions", { specId: args.specId }, async () => {
|
|
308
|
+
const res = await client.listOpenQuestions(args.specId, {
|
|
309
|
+
includeResolved: args.includeResolved,
|
|
310
|
+
});
|
|
311
|
+
return ok(res.body);
|
|
312
|
+
}));
|
|
313
|
+
}
|
|
314
|
+
export function registerWriteTools(server, deps) {
|
|
315
|
+
const { client, config } = deps;
|
|
316
|
+
server.registerTool("start_new_version", {
|
|
317
|
+
title: "Start a new draft",
|
|
318
|
+
description: "Open a new draft of a Reviewed specification. Side effect: status becomes Draft. Does not bump the user-visible version. Required before update_specification_content on a published spec. No-op when the spec is already in Draft (response carries hint=\"already_draft\").",
|
|
319
|
+
inputSchema: { specId: z.string().min(1) },
|
|
320
|
+
}, async (args) => runTool("start_new_version", { specId: args.specId }, async () => {
|
|
321
|
+
const res = await client.startNewVersion(args.specId);
|
|
322
|
+
return ok(res.body);
|
|
323
|
+
}));
|
|
324
|
+
server.registerTool("update_specification_content", {
|
|
325
|
+
title: "Replace a draft's full content",
|
|
326
|
+
description: "Replace the entire Markdown body of a Draft specification. Side effect: content + OCC version are updated. Pass `version` from the most recent read to detect concurrent edits. Returns 409 STALE_VERSION when another writer landed first — re-read and retry.",
|
|
327
|
+
inputSchema: {
|
|
328
|
+
specId: z.string().min(1),
|
|
329
|
+
content: z.string().max(1_000_000),
|
|
330
|
+
version: z.number().int().min(1),
|
|
331
|
+
},
|
|
332
|
+
}, async (args) => runTool("update_specification_content", { specId: args.specId }, async () => {
|
|
333
|
+
const res = await client.updateSpecificationContent(args.specId, {
|
|
334
|
+
content: args.content,
|
|
335
|
+
version: args.version,
|
|
336
|
+
});
|
|
337
|
+
return ok(res.body);
|
|
338
|
+
}));
|
|
339
|
+
server.registerTool("update_specification_section", {
|
|
340
|
+
title: "Replace a single section of a draft",
|
|
341
|
+
description: 'Replace one heading-bound section of a Draft specification (e.g. sectionPath="## Pricing"). Side effect: the section text is replaced atomically and a before-image revision is recorded. OCC-guarded — pass `version` from the most recent read.',
|
|
342
|
+
inputSchema: {
|
|
343
|
+
specId: z.string().min(1),
|
|
344
|
+
sectionPath: z.string().trim().min(1).max(200),
|
|
345
|
+
newSection: z.string().max(1_000_000),
|
|
346
|
+
version: z.number().int().min(1),
|
|
347
|
+
},
|
|
348
|
+
}, async (args) => runTool("update_specification_section", { specId: args.specId }, async () => {
|
|
349
|
+
const res = await client.updateSpecificationSection(args.specId, {
|
|
350
|
+
sectionPath: args.sectionPath,
|
|
351
|
+
newSection: args.newSection,
|
|
352
|
+
version: args.version,
|
|
353
|
+
});
|
|
354
|
+
return ok(res.body);
|
|
355
|
+
}));
|
|
356
|
+
server.registerTool("request_review", {
|
|
357
|
+
title: "Request review on a draft",
|
|
358
|
+
description: "Move a Draft specification to Needs Review so a human can mark it Reviewed in Xpec. Gated on the spec having no open questions — if questions remain, the response returns OPEN_QUESTIONS_PRESENT and the agent should surface them to the user.",
|
|
359
|
+
inputSchema: { specId: z.string().min(1) },
|
|
360
|
+
}, async (args) => runTool("request_review", { specId: args.specId }, async () => {
|
|
361
|
+
const res = await client.requestReview(args.specId);
|
|
362
|
+
return ok(res.body);
|
|
363
|
+
}));
|
|
364
|
+
server.registerTool("discard_draft", {
|
|
365
|
+
title: "Discard the current draft",
|
|
366
|
+
description: "Roll a Draft (or Needs Review) specification back to its last approved version. Side effect: content is restored from the latest approved revision and status returns to Reviewed. Rejected when the spec has never been approved.",
|
|
367
|
+
inputSchema: { specId: z.string().min(1) },
|
|
368
|
+
}, async (args) => runTool("discard_draft", { specId: args.specId }, async () => {
|
|
369
|
+
const res = await client.discardDraft(args.specId);
|
|
370
|
+
return ok(res.body);
|
|
371
|
+
}));
|
|
372
|
+
// Free-spec creation only makes sense when the bound product is Free.
|
|
373
|
+
// The API enforces this with PRODUCT_TYPE_MISMATCH, but the tool stays
|
|
374
|
+
// listed unconditionally so the agent can call it after binding to a
|
|
375
|
+
// Free product — the type check at call time matches the spec's
|
|
376
|
+
// documented behaviour better than an opaque "tool not found".
|
|
377
|
+
server.registerTool("create_free_specification", {
|
|
378
|
+
title: "Create a Free product specification",
|
|
379
|
+
description: "Create a new Markdown specification in the bound Free product. Side effect: a new spec row is created at status=Draft, approvedVersion=1. Path uniqueness is enforced. Rejected with PRODUCT_TYPE_MISMATCH when the product is Web Application — use start_new_version on an existing structured spec instead.",
|
|
380
|
+
inputSchema: {
|
|
381
|
+
productId: z.string().optional(),
|
|
382
|
+
title: z.string().min(1).max(200),
|
|
383
|
+
path: z.string().optional(),
|
|
384
|
+
tags: z.array(z.string()).optional(),
|
|
385
|
+
content: z.string().optional(),
|
|
386
|
+
},
|
|
387
|
+
}, async (args) => runTool("create_free_specification", { productId: args.productId }, async () => {
|
|
388
|
+
const wsId = requireProductId(config, args.productId);
|
|
389
|
+
const res = await client.createFreeSpecification(wsId, {
|
|
390
|
+
title: args.title,
|
|
391
|
+
path: args.path,
|
|
392
|
+
tags: args.tags,
|
|
393
|
+
content: args.content,
|
|
394
|
+
});
|
|
395
|
+
return ok(res.body);
|
|
396
|
+
}));
|
|
397
|
+
}
|
|
398
|
+
//# sourceMappingURL=tools.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"tools.js","sourceRoot":"","sources":["../src/tools.ts"],"names":[],"mappings":"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"}
|
package/package.json
ADDED
|
@@ -0,0 +1,43 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "@nextfreelatech/xpec-mcp",
|
|
3
|
+
"version": "1.0.1",
|
|
4
|
+
"description": "Model Context Protocol server for Xpec — exposes a workspace's specifications to local AI coding agents.",
|
|
5
|
+
"type": "module",
|
|
6
|
+
"license": "Apache-2.0",
|
|
7
|
+
"engines": {
|
|
8
|
+
"node": ">=22.22"
|
|
9
|
+
},
|
|
10
|
+
"bin": {
|
|
11
|
+
"xpec-mcp": "./dist/cli.js"
|
|
12
|
+
},
|
|
13
|
+
"main": "./dist/index.js",
|
|
14
|
+
"files": [
|
|
15
|
+
"dist",
|
|
16
|
+
"README.md"
|
|
17
|
+
],
|
|
18
|
+
"repository": {
|
|
19
|
+
"type": "git",
|
|
20
|
+
"url": "git+https://github.com/nextfreela/xpec-mcp.git",
|
|
21
|
+
"directory": "."
|
|
22
|
+
},
|
|
23
|
+
"publishConfig": {
|
|
24
|
+
"access": "public",
|
|
25
|
+
"provenance": true
|
|
26
|
+
},
|
|
27
|
+
"scripts": {
|
|
28
|
+
"build": "tsc -p tsconfig.json"
|
|
29
|
+
},
|
|
30
|
+
"dependencies": {
|
|
31
|
+
"@modelcontextprotocol/sdk": "^1.29.0",
|
|
32
|
+
"zod": "^4.3.6"
|
|
33
|
+
},
|
|
34
|
+
"devDependencies": {
|
|
35
|
+
"@types/node": "^20",
|
|
36
|
+
"dotenv": "^17.4.2",
|
|
37
|
+
"eslint": "^9",
|
|
38
|
+
"eslint-config-next": "16.2.4",
|
|
39
|
+
"tsx": "^4.21.0",
|
|
40
|
+
"typescript": "^5",
|
|
41
|
+
"vitest": "^4.1.5"
|
|
42
|
+
}
|
|
43
|
+
}
|