@roadmapperai/mcp 0.2.0 → 0.3.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/package.json +1 -1
- package/server.mjs +54 -2
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@roadmapperai/mcp",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.3.0",
|
|
4
4
|
"description": "Roadmapper AI MCP server — exposes a planning surface (themes, capabilities, tasks, sprints, PRs) to coding agents via stdio JSON-RPC. Pairs with the Roadmapper AI workspace at dashboard.roadmapperai.com.",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"mcp",
|
package/server.mjs
CHANGED
|
@@ -111,6 +111,47 @@ function readAgentsMd() {
|
|
|
111
111
|
}
|
|
112
112
|
}
|
|
113
113
|
|
|
114
|
+
/**
|
|
115
|
+
* Fetch a workspace-scoped rubric override via the mcp-broker.
|
|
116
|
+
*
|
|
117
|
+
* Returns the workspace's custom rubric content if they've authored
|
|
118
|
+
* one in the dashboard's Settings → Workspace customization tab,
|
|
119
|
+
* null if the workspace is on the default, or null on any error
|
|
120
|
+
* (we fall back to the bundled AGENTS.md rather than refuse to
|
|
121
|
+
* serve get_agents_md).
|
|
122
|
+
*
|
|
123
|
+
* Only called when ROADMAPPER_API_KEY is set — i.e. the customer
|
|
124
|
+
* install path. Operator path (SUPABASE_SERVICE_ROLE_KEY) skips
|
|
125
|
+
* this and always serves the bundled rubric.
|
|
126
|
+
*/
|
|
127
|
+
async function fetchWorkspaceRubric() {
|
|
128
|
+
const { apiKey, brokerUrl } = supabaseConfig();
|
|
129
|
+
if (!apiKey || !brokerUrl) return null;
|
|
130
|
+
try {
|
|
131
|
+
const res = await fetch(brokerUrl, {
|
|
132
|
+
method: "POST",
|
|
133
|
+
headers: {
|
|
134
|
+
Authorization: `Bearer ${apiKey}`,
|
|
135
|
+
"content-type": "application/json",
|
|
136
|
+
Accept: "application/json",
|
|
137
|
+
},
|
|
138
|
+
body: JSON.stringify({ rpc: "get_workspace_rubric", body: {} }),
|
|
139
|
+
});
|
|
140
|
+
if (!res.ok) return null;
|
|
141
|
+
const parsed = await res.json();
|
|
142
|
+
if (typeof parsed === "string" && parsed.length > 0) return parsed;
|
|
143
|
+
return null;
|
|
144
|
+
} catch {
|
|
145
|
+
return null;
|
|
146
|
+
}
|
|
147
|
+
}
|
|
148
|
+
|
|
149
|
+
async function readAgentsMdForWorkspace() {
|
|
150
|
+
const custom = await fetchWorkspaceRubric();
|
|
151
|
+
if (custom) return custom;
|
|
152
|
+
return readAgentsMd();
|
|
153
|
+
}
|
|
154
|
+
|
|
114
155
|
/**
|
|
115
156
|
* The read key used to fetch the workspace row. Accepts the new
|
|
116
157
|
* publishable key (`sb_publishable_…`) or the legacy `anon`/JWT key.
|
|
@@ -1651,7 +1692,11 @@ async function callTool(name, args) {
|
|
|
1651
1692
|
const fresh = session.rubricFetchedAt === null;
|
|
1652
1693
|
session.rubricFetchedAt = Date.now();
|
|
1653
1694
|
if (fresh) recordTelemetry("rubric_fetched", { via: "tool" }, wsId);
|
|
1654
|
-
|
|
1695
|
+
// Customer path (ROADMAPPER_API_KEY set): ask the broker for
|
|
1696
|
+
// a workspace-scoped rubric. Falls back to the bundled
|
|
1697
|
+
// AGENTS.md when the workspace hasn't customized one.
|
|
1698
|
+
const rubric = await readAgentsMdForWorkspace();
|
|
1699
|
+
return textResult(rubric, {
|
|
1655
1700
|
_meta: {
|
|
1656
1701
|
roadmapper: {
|
|
1657
1702
|
reminder:
|
|
@@ -2865,7 +2910,14 @@ async function readResource(uri) {
|
|
|
2865
2910
|
}
|
|
2866
2911
|
return {
|
|
2867
2912
|
contents: [
|
|
2868
|
-
{
|
|
2913
|
+
{
|
|
2914
|
+
uri,
|
|
2915
|
+
mimeType: "text/markdown",
|
|
2916
|
+
// Resource handler is also async, so the workspace
|
|
2917
|
+
// rubric override applies here too — same fallback chain
|
|
2918
|
+
// as the get_agents_md tool.
|
|
2919
|
+
text: await readAgentsMdForWorkspace(),
|
|
2920
|
+
},
|
|
2869
2921
|
],
|
|
2870
2922
|
};
|
|
2871
2923
|
}
|