@miragon/design-iq-mcp 5.0.0 → 5.2.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 +2 -2
- package/dist/http.js +1 -1
- package/dist/server.js +1 -1
- package/dist/{tools-Df9L1Tf-.js → tools-8vgJc4aD.js} +28 -17
- package/package.json +7 -7
package/README.md
CHANGED
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
# @miragon/design-iq-mcp
|
|
2
2
|
|
|
3
3
|
designIQ's read-only MCP server: it exposes the models of a designIQ content repo — processes
|
|
4
|
-
(BPMN), decisions (DMN), Wardley
|
|
5
|
-
|
|
4
|
+
(BPMN), decisions (DMN), Wardley Maps, Team Topologies, Event Storming boards, Context Maps,
|
|
5
|
+
Value Chains and Markdown — to any MCP client (Claude Code, Claude Desktop, IDEs, ...). A
|
|
6
6
|
content repo is a root `designiq.yml` naming its models folder (`models:`, legacy alias
|
|
7
7
|
`processes:`; the legacy file name `bpmiq.yml` is still read); a model IS a file with a
|
|
8
8
|
registered notation extension there (a process its `.bpmn`). Views are **derived from the
|
package/dist/http.js
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
|
-
import { n as createMcpServer, r as todosConfigFromEnv, t as DEFAULT_ROOT } from "./tools-
|
|
2
|
+
import { n as createMcpServer, r as todosConfigFromEnv, t as DEFAULT_ROOT } from "./tools-8vgJc4aD.js";
|
|
3
3
|
import { createServer } from "node:http";
|
|
4
4
|
import { timingSafeEqual } from "node:crypto";
|
|
5
5
|
import { NodeStreamableHTTPServerTransport } from "@modelcontextprotocol/node";
|
package/dist/server.js
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
|
-
import { n as createMcpServer, r as todosConfigFromEnv, t as DEFAULT_ROOT } from "./tools-
|
|
2
|
+
import { n as createMcpServer, r as todosConfigFromEnv, t as DEFAULT_ROOT } from "./tools-8vgJc4aD.js";
|
|
3
3
|
import { existsSync } from "node:fs";
|
|
4
4
|
import { resolve } from "node:path";
|
|
5
5
|
import { StdioServerTransport } from "@modelcontextprotocol/server/stdio";
|
|
@@ -93,8 +93,8 @@ const NOTATIONS = [
|
|
|
93
93
|
id: "wardley",
|
|
94
94
|
label: "Wardley Map",
|
|
95
95
|
noun: {
|
|
96
|
-
singular: "
|
|
97
|
-
plural: "
|
|
96
|
+
singular: "Wardley Map",
|
|
97
|
+
plural: "Wardley Maps"
|
|
98
98
|
},
|
|
99
99
|
extensions: [".owm", ".wmap"],
|
|
100
100
|
mediaKind: "dsl",
|
|
@@ -109,8 +109,8 @@ const NOTATIONS = [
|
|
|
109
109
|
id: "team-topology",
|
|
110
110
|
label: "Team Topology",
|
|
111
111
|
noun: {
|
|
112
|
-
singular: "
|
|
113
|
-
plural: "
|
|
112
|
+
singular: "Team Topology",
|
|
113
|
+
plural: "Team Topologies"
|
|
114
114
|
},
|
|
115
115
|
extensions: [".tt", ".ttm.json"],
|
|
116
116
|
mediaKind: "json",
|
|
@@ -121,8 +121,8 @@ const NOTATIONS = [
|
|
|
121
121
|
id: "event-storming",
|
|
122
122
|
label: "Event Storming",
|
|
123
123
|
noun: {
|
|
124
|
-
singular: "
|
|
125
|
-
plural: "
|
|
124
|
+
singular: "Event Storming board",
|
|
125
|
+
plural: "Event Storming boards"
|
|
126
126
|
},
|
|
127
127
|
extensions: [".storm"],
|
|
128
128
|
mediaKind: "dsl",
|
|
@@ -137,8 +137,8 @@ const NOTATIONS = [
|
|
|
137
137
|
id: "context-map",
|
|
138
138
|
label: "Context Map",
|
|
139
139
|
noun: {
|
|
140
|
-
singular: "
|
|
141
|
-
plural: "
|
|
140
|
+
singular: "Context Map",
|
|
141
|
+
plural: "Context Maps"
|
|
142
142
|
},
|
|
143
143
|
extensions: [".cm.json"],
|
|
144
144
|
mediaKind: "json",
|
|
@@ -159,8 +159,8 @@ const NOTATIONS = [
|
|
|
159
159
|
id: "value-chain",
|
|
160
160
|
label: "Value Chain",
|
|
161
161
|
noun: {
|
|
162
|
-
singular: "
|
|
163
|
-
plural: "
|
|
162
|
+
singular: "Value Chain",
|
|
163
|
+
plural: "Value Chains"
|
|
164
164
|
},
|
|
165
165
|
extensions: [".vc.json"],
|
|
166
166
|
mediaKind: "json",
|
|
@@ -1342,7 +1342,7 @@ const DERIVERS = {
|
|
|
1342
1342
|
return {
|
|
1343
1343
|
notation: "wardley",
|
|
1344
1344
|
name: null,
|
|
1345
|
-
summary: `Wardley
|
|
1345
|
+
summary: `Wardley Map with ${counted(stats)}`,
|
|
1346
1346
|
stats
|
|
1347
1347
|
};
|
|
1348
1348
|
},
|
|
@@ -1354,7 +1354,7 @@ const DERIVERS = {
|
|
|
1354
1354
|
return {
|
|
1355
1355
|
notation: "team-topology",
|
|
1356
1356
|
name: null,
|
|
1357
|
-
summary: `Team
|
|
1357
|
+
summary: `Team Topology with ${counted(stats)}`,
|
|
1358
1358
|
stats
|
|
1359
1359
|
};
|
|
1360
1360
|
},
|
|
@@ -1378,7 +1378,7 @@ const DERIVERS = {
|
|
|
1378
1378
|
return {
|
|
1379
1379
|
notation: "event-storming",
|
|
1380
1380
|
name: typeof title === "string" ? title : null,
|
|
1381
|
-
summary: `Event
|
|
1381
|
+
summary: `Event Storming board with ${Object.keys(present).length > 0 ? counted(present) : "no elements"}`,
|
|
1382
1382
|
stats,
|
|
1383
1383
|
detail: {
|
|
1384
1384
|
level: graph.meta?.level ?? null,
|
|
@@ -1401,7 +1401,7 @@ const DERIVERS = {
|
|
|
1401
1401
|
return {
|
|
1402
1402
|
notation: "context-map",
|
|
1403
1403
|
name: typeof title === "string" ? title : null,
|
|
1404
|
-
summary: `Context
|
|
1404
|
+
summary: `Context Map with ${counted({ contexts: stats.contexts })}${breakdown(CM_SUBDOMAIN_TYPES)}, ${counted({ relationships: stats.relationships })}${breakdown(CM_RELATIONSHIP_PATTERNS)}`,
|
|
1405
1405
|
stats,
|
|
1406
1406
|
detail: {
|
|
1407
1407
|
contexts: graph.nodes.map((n) => ({
|
|
@@ -1432,7 +1432,7 @@ const DERIVERS = {
|
|
|
1432
1432
|
return {
|
|
1433
1433
|
notation: "value-chain",
|
|
1434
1434
|
name: null,
|
|
1435
|
-
summary: `Value
|
|
1435
|
+
summary: `Value Chain with ${counted(stats)}`,
|
|
1436
1436
|
stats
|
|
1437
1437
|
};
|
|
1438
1438
|
}
|
|
@@ -1628,17 +1628,18 @@ function createMcpServer(root = DEFAULT_ROOT, todos, contributions = []) {
|
|
|
1628
1628
|
return graph;
|
|
1629
1629
|
};
|
|
1630
1630
|
const isGraph = (g) => !("content" in g);
|
|
1631
|
-
/** the registry nouns for user-facing copy ("
|
|
1631
|
+
/** the registry nouns for user-facing copy ("Wardley Map" / "Team Topologies") */
|
|
1632
1632
|
const nounOf = (notation) => byId(notation)?.noun.singular ?? notation;
|
|
1633
1633
|
const pluralOf = (notation) => byId(notation)?.noun.plural ?? notation;
|
|
1634
1634
|
const notAContentRepo = () => fail(`No usable designiq.yml (or legacy bpmiq.yml) at the content root — not a content repo. Expected a root designiq.yml naming the models folder.`);
|
|
1635
1635
|
const unknownProcess = async (id) => fail(`Unknown process '${id}'. Available: ${(await processes()).map((p) => p.id).join(", ") || "(none)"}.`);
|
|
1636
1636
|
const server = new McpServer({
|
|
1637
1637
|
name: "designiq-mcp",
|
|
1638
|
-
title: "designIQ
|
|
1638
|
+
title: "designIQ model repository (read-only)",
|
|
1639
1639
|
version: "0.2.0"
|
|
1640
1640
|
}, { instructions: readOnlyInstructions({ todos: todos !== void 0 }) });
|
|
1641
1641
|
server.registerTool("list_models", {
|
|
1642
|
+
title: "List models",
|
|
1642
1643
|
description: `List EVERY model file of the repository, grouped by notation (${NOTATIONS.map((n) => n.id).join(", ")}) — the starting point for any question. Each row: id (file stem), path, and — for notations with a registered deriver — the model's own name, summary and stats. Use to see which notations a repo contains before reaching for the notation-specific tools; list_processes is the BPMN-only listing.`,
|
|
1643
1644
|
annotations: READ_ONLY
|
|
1644
1645
|
}, safe(async () => {
|
|
@@ -1669,6 +1670,7 @@ function createMcpServer(root = DEFAULT_ROOT, todos, contributions = []) {
|
|
|
1669
1670
|
return ok({ models: grouped });
|
|
1670
1671
|
}));
|
|
1671
1672
|
server.registerTool("list_processes", {
|
|
1673
|
+
title: "List BPMN processes",
|
|
1672
1674
|
description: "BPMN only: list the processes — every .bpmn file under the repo's designiq.yml models folder. Each row: id (file name without extension), derived name, the file path, and a count of steps/events/gateways/roles. Use for a process overview or to find a process id before calling get_process, get_model, who_owns or enumerate_paths; list_models covers every notation.",
|
|
1673
1675
|
annotations: READ_ONLY
|
|
1674
1676
|
}, safe(async () => {
|
|
@@ -1692,6 +1694,7 @@ function createMcpServer(root = DEFAULT_ROOT, todos, contributions = []) {
|
|
|
1692
1694
|
}));
|
|
1693
1695
|
}));
|
|
1694
1696
|
server.registerTool("get_process", {
|
|
1697
|
+
title: "Get BPMN process view",
|
|
1695
1698
|
description: "BPMN only: get one process in full — the process view DERIVED from its BPMN: name, roles (BPMN lanes = owning teams), steps (activities with their role), events, gateways, the sequence/message flow, and the sub-processes it calls (callActivity → calledElement). Use for walkthroughs and any deep question about a single process; get_view covers every notation.",
|
|
1696
1699
|
inputSchema: z.object({ id: z.string().describe("Process id = the .bpmn file name without extension, e.g. order-to-cash") }),
|
|
1697
1700
|
annotations: READ_ONLY
|
|
@@ -1708,6 +1711,7 @@ function createMcpServer(root = DEFAULT_ROOT, todos, contributions = []) {
|
|
|
1708
1711
|
});
|
|
1709
1712
|
}));
|
|
1710
1713
|
server.registerTool("get_model", {
|
|
1714
|
+
title: "Get model graph",
|
|
1711
1715
|
description: "Parse ANY model file into its generic graph: nodes (id, type, name), edges and meta — BPMN flows and lanes, DMN requirements, Wardley components/dependencies, … Use to see the raw structure, or to ground any 'how does X work' answer in the actual model.",
|
|
1712
1716
|
inputSchema: z.object({
|
|
1713
1717
|
id: z.string().describe("Model id = file stem (from list_models), e.g. order-to-cash"),
|
|
@@ -1726,6 +1730,7 @@ function createMcpServer(root = DEFAULT_ROOT, todos, contributions = []) {
|
|
|
1726
1730
|
}) : graph;
|
|
1727
1731
|
}));
|
|
1728
1732
|
server.registerTool("get_view", {
|
|
1733
|
+
title: "Get model view",
|
|
1729
1734
|
description: `The derived view of ANY model — its own name, a one-line summary, stats, and the rich notation payload in \`detail\` where one exists (the process view for BPMN, the decision tables for DMN). Works for every notation with extract+derive capabilities (${NOTATIONS.filter((n) => hasDeriver(n.id)).map((n) => n.id).join(", ")}).`,
|
|
1730
1735
|
inputSchema: z.object({
|
|
1731
1736
|
id: z.string().describe("Model id = file stem (from list_models), e.g. tea-shop"),
|
|
@@ -1747,6 +1752,7 @@ function createMcpServer(root = DEFAULT_ROOT, todos, contributions = []) {
|
|
|
1747
1752
|
});
|
|
1748
1753
|
}));
|
|
1749
1754
|
server.registerTool("enumerate_paths", {
|
|
1755
|
+
title: "Enumerate flow paths",
|
|
1750
1756
|
description: "Enumerate the possible start→end paths through a model's flow (cycle-safe, capped) — BPMN sequence flows, Wardley dependencies, … per the notation's graph hints. Each path is the ordered list of element names. Use for walkthroughs ('what are the ways an order can go?'), test-case derivation, and spotting unexpected shortcuts or dead branches.",
|
|
1751
1757
|
inputSchema: z.object({
|
|
1752
1758
|
id: z.string().describe("Model id = file stem, e.g. order-to-cash"),
|
|
@@ -1772,6 +1778,7 @@ function createMcpServer(root = DEFAULT_ROOT, todos, contributions = []) {
|
|
|
1772
1778
|
});
|
|
1773
1779
|
}));
|
|
1774
1780
|
server.registerTool("find_cycles", {
|
|
1781
|
+
title: "Find flow cycles",
|
|
1775
1782
|
description: "Detect cycles (loops) in a model's flow — BPMN rework/retry loops, circular Wardley dependencies, circular DMN requirements — per the notation's graph hints. Returns each cycle as the ordered list of element names. Use when analyzing complexity, rework cost, or 'why does this case never finish'.",
|
|
1776
1783
|
inputSchema: z.object({
|
|
1777
1784
|
id: z.string().describe("Model id = file stem, e.g. order-to-cash"),
|
|
@@ -1793,6 +1800,7 @@ function createMcpServer(root = DEFAULT_ROOT, todos, contributions = []) {
|
|
|
1793
1800
|
});
|
|
1794
1801
|
}));
|
|
1795
1802
|
server.registerTool("who_owns", {
|
|
1803
|
+
title: "Find who owns a BPMN process",
|
|
1796
1804
|
description: "BPMN only: resolve ownership of a process from its lanes — the roles/teams that own its steps (each lane, with the steps it contains) plus the pools (participants). Use for 'who owns X', 'who does what in X', or handoff questions. Note: on the slim contract ownership is whatever the model's lanes say; a process with no lanes has no modeled owner.",
|
|
1797
1805
|
inputSchema: z.object({ id: z.string().describe("Process id, e.g. order-to-cash") }),
|
|
1798
1806
|
annotations: READ_ONLY
|
|
@@ -1815,6 +1823,7 @@ function createMcpServer(root = DEFAULT_ROOT, todos, contributions = []) {
|
|
|
1815
1823
|
});
|
|
1816
1824
|
}));
|
|
1817
1825
|
server.registerTool("which_processes_use", {
|
|
1826
|
+
title: "Search BPMN processes",
|
|
1818
1827
|
description: "BPMN only: find processes whose id, derived name, role/lane names, step names, or sub-process calls (calledElement) match a query — case-insensitive substring. Use for 'what calls invoice-handling', 'which processes have a Billing lane', 'what touches the credit check'. which_models_use follows references across every notation.",
|
|
1819
1828
|
inputSchema: z.object({ query: z.string().describe("Case-insensitive substring, e.g. 'invoice-handling', 'Billing', 'credit'") }),
|
|
1820
1829
|
annotations: READ_ONLY
|
|
@@ -1849,6 +1858,7 @@ function createMcpServer(root = DEFAULT_ROOT, todos, contributions = []) {
|
|
|
1849
1858
|
return ok(hits);
|
|
1850
1859
|
}));
|
|
1851
1860
|
server.registerTool("which_models_use", {
|
|
1861
|
+
title: "Find models that reference a model",
|
|
1852
1862
|
description: "Reference-level impact analysis across EVERY notation: all models whose typed cross-model references (callActivity calls, businessRuleTask decides, …) point at the given model id (file stem, exact match) — the repo-wide reference index behind it also flags dangling references. Use for 'what breaks if I change or delete this model?'.",
|
|
1853
1863
|
inputSchema: z.object({ id: z.string().describe("Target model id = file stem (from list_models), e.g. 'credit-check'") }),
|
|
1854
1864
|
annotations: READ_ONLY
|
|
@@ -1873,6 +1883,7 @@ function createMcpServer(root = DEFAULT_ROOT, todos, contributions = []) {
|
|
|
1873
1883
|
const { repo: todosRepo, token: todosToken } = todos;
|
|
1874
1884
|
const api = (todos.apiUrl ?? "https://api.github.com").replace(/\/$/, "");
|
|
1875
1885
|
server.registerTool("list_todos", {
|
|
1886
|
+
title: "List open todos",
|
|
1876
1887
|
description: "List the OPEN model-anchored todos of this content repo — work items filed from the live model into the repo's issue tracker (label 'todo'). Each row carries the tracker id and URL, title, assignees, createdAt and the parsed anchor (process, model file, anchored BPMN elements). Optional filter on one process. Use for 'what is open on process X' or to cross-check a model answer against known open discrepancies.",
|
|
1877
1888
|
inputSchema: z.object({ process: z.string().optional().describe("Only todos anchored to this process id, e.g. order-to-cash") }),
|
|
1878
1889
|
annotations: {
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@miragon/design-iq-mcp",
|
|
3
|
-
"version": "5.
|
|
4
|
-
"description": "Read-only MCP server exposing a designIQ content repo's models — BPMN processes, DMN decisions, Wardley
|
|
3
|
+
"version": "5.2.0",
|
|
4
|
+
"description": "Read-only MCP server exposing a designIQ content repo's models — BPMN processes, DMN decisions, Wardley Maps, Team Topologies, Event Storming boards, Context Maps and more — to any MCP client. Discovered from designiq.yml, views derived from the models.",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"license": "MIT",
|
|
7
7
|
"repository": {
|
|
@@ -40,19 +40,19 @@
|
|
|
40
40
|
"access": "public"
|
|
41
41
|
},
|
|
42
42
|
"dependencies": {
|
|
43
|
-
"@modelcontextprotocol/node": "2.1.
|
|
44
|
-
"@modelcontextprotocol/server": "2.
|
|
45
|
-
"fast-xml-parser": "5.11.
|
|
43
|
+
"@modelcontextprotocol/node": "2.1.1",
|
|
44
|
+
"@modelcontextprotocol/server": "2.3.0",
|
|
45
|
+
"fast-xml-parser": "5.11.2",
|
|
46
46
|
"yaml": "2.9.1",
|
|
47
47
|
"zod": "4.6.5"
|
|
48
48
|
},
|
|
49
49
|
"devDependencies": {
|
|
50
|
-
"@modelcontextprotocol/client": "2.
|
|
50
|
+
"@modelcontextprotocol/client": "2.3.0",
|
|
51
51
|
"tsdown": "0.23.0",
|
|
52
52
|
"@designiq/contracts": "0.1.0",
|
|
53
53
|
"@designiq/github-app": "0.1.0",
|
|
54
|
-
"@designiq/mcp-kit": "0.1.0",
|
|
55
54
|
"@designiq/http-kit": "0.1.0",
|
|
55
|
+
"@designiq/mcp-kit": "0.1.0",
|
|
56
56
|
"@designiq/notations": "0.1.0"
|
|
57
57
|
},
|
|
58
58
|
"scripts": {
|