@nimara-app/mcp 0.5.0 → 0.6.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 +1 -0
- package/dist/index.js +94 -62
- package/dist/index.js.map +4 -4
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -50,6 +50,7 @@ remove existing data, as opposed to only adding.
|
|
|
50
50
|
| `remove_item_from_milestone` | **Write ⚠** | Remove a work item's association with a milestone (idempotent — a no-op if it wasn't associated).. |
|
|
51
51
|
| `remove_label_from_work_item` | **Write ⚠** | Remove a label from a work item (idempotent — a no-op if it wasn't attached).. |
|
|
52
52
|
| `search_work_items` | Read | Find work items in a project by title — the cheap way to check whether something is already tracked. |
|
|
53
|
+
| `watch_work_item` | Write | Put the token owner on (or off) an item's watch list: they are told when it changes status, gets a comment or reviewer, is archived or moved. |
|
|
53
54
|
| `update_document` | **Write ⚠** | Update an existing document's markdown content and/or title. |
|
|
54
55
|
| `update_work_item` | **Write ⚠** | Update an existing work item: title, description, status, priority, parent, or review flags. |
|
|
55
56
|
|
package/dist/index.js
CHANGED
|
@@ -9,7 +9,7 @@ import { McpServer } from "@modelcontextprotocol/sdk/server/mcp.js";
|
|
|
9
9
|
// package.json
|
|
10
10
|
var package_default = {
|
|
11
11
|
name: "@nimara-app/mcp",
|
|
12
|
-
version: "0.
|
|
12
|
+
version: "0.6.0",
|
|
13
13
|
private: false,
|
|
14
14
|
mcpName: "io.github.langskip-studios/nimara",
|
|
15
15
|
description: "Nimara MCP server \u2014 AI tool integration for Claude, Codex, and others",
|
|
@@ -833,18 +833,49 @@ function registerHeartbeatWorkItem(server) {
|
|
|
833
833
|
);
|
|
834
834
|
}
|
|
835
835
|
|
|
836
|
-
// src/tools/
|
|
836
|
+
// src/tools/watch-work-item.ts
|
|
837
837
|
import { z as z19 } from "zod";
|
|
838
|
+
function registerWatchWorkItem(server) {
|
|
839
|
+
server.registerTool(
|
|
840
|
+
"watch_work_item",
|
|
841
|
+
{
|
|
842
|
+
description: "Put the token owner on (or take them off) an item's watch list. A watcher is notified when the item changes status, gets a comment, gets a reviewer, is archived or moved \u2014 not on title or description edits. The item's assignee and reviewer already hear about it. Use this when you start work the person will want to follow, or when they ask to keep an eye on something.",
|
|
843
|
+
inputSchema: {
|
|
844
|
+
workItemId: z19.string().describe("workItemId of the item"),
|
|
845
|
+
watching: z19.boolean().default(true).describe("true to watch, false to stop")
|
|
846
|
+
},
|
|
847
|
+
annotations: {
|
|
848
|
+
readOnlyHint: false,
|
|
849
|
+
destructiveHint: false,
|
|
850
|
+
idempotentHint: true,
|
|
851
|
+
openWorldHint: false
|
|
852
|
+
}
|
|
853
|
+
},
|
|
854
|
+
async ({ workItemId, watching }) => {
|
|
855
|
+
const result = await getConvexClient().action(api.mcp.watchWorkItem, {
|
|
856
|
+
token: getToken(),
|
|
857
|
+
workItemId,
|
|
858
|
+
watching
|
|
859
|
+
});
|
|
860
|
+
return {
|
|
861
|
+
content: [{ type: "text", text: JSON.stringify(result, null, 2) }]
|
|
862
|
+
};
|
|
863
|
+
}
|
|
864
|
+
);
|
|
865
|
+
}
|
|
866
|
+
|
|
867
|
+
// src/tools/add-work-item-image.ts
|
|
868
|
+
import { z as z20 } from "zod";
|
|
838
869
|
function registerAddWorkItemImage(server) {
|
|
839
870
|
server.registerTool(
|
|
840
871
|
"add_work_item_image",
|
|
841
872
|
{
|
|
842
873
|
description: "Attach an externally hosted image URL to a work item. Use this when an MCP client has a screenshot, mockup, or generated image URL to preserve with the task.",
|
|
843
874
|
inputSchema: {
|
|
844
|
-
workItemId:
|
|
845
|
-
imageUrl:
|
|
846
|
-
filename:
|
|
847
|
-
altText:
|
|
875
|
+
workItemId: z20.string().describe("workItemId from list_work_items"),
|
|
876
|
+
imageUrl: z20.string().url().describe("Public or otherwise fetchable http(s) image URL"),
|
|
877
|
+
filename: z20.string().optional().describe("Optional display filename"),
|
|
878
|
+
altText: z20.string().optional().describe("Optional description/caption for the image")
|
|
848
879
|
},
|
|
849
880
|
annotations: {
|
|
850
881
|
readOnlyHint: false,
|
|
@@ -866,14 +897,14 @@ function registerAddWorkItemImage(server) {
|
|
|
866
897
|
}
|
|
867
898
|
|
|
868
899
|
// src/tools/list-work-item-images.ts
|
|
869
|
-
import { z as
|
|
900
|
+
import { z as z21 } from "zod";
|
|
870
901
|
function registerListWorkItemImages(server) {
|
|
871
902
|
server.registerTool(
|
|
872
903
|
"list_work_item_images",
|
|
873
904
|
{
|
|
874
905
|
description: "List image attachments for a work item, including uploaded images and externally attached MCP images. Call list_work_items first to find the workItemId.",
|
|
875
906
|
inputSchema: {
|
|
876
|
-
workItemId:
|
|
907
|
+
workItemId: z21.string().describe("workItemId from list_work_items")
|
|
877
908
|
},
|
|
878
909
|
annotations: {
|
|
879
910
|
readOnlyHint: true,
|
|
@@ -896,18 +927,18 @@ function registerListWorkItemImages(server) {
|
|
|
896
927
|
}
|
|
897
928
|
|
|
898
929
|
// src/tools/add-work-item-comment.ts
|
|
899
|
-
import { z as
|
|
930
|
+
import { z as z22 } from "zod";
|
|
900
931
|
function registerAddWorkItemComment(server) {
|
|
901
932
|
server.registerTool(
|
|
902
933
|
"add_work_item_comment",
|
|
903
934
|
{
|
|
904
935
|
description: "Add a timestamped comment to a work item. Use this to record notes, updates, or an 'AI touched' entry instead of editing the description. Comments are stamped with the current time automatically and never overwrite each other.",
|
|
905
936
|
inputSchema: {
|
|
906
|
-
workItemId:
|
|
907
|
-
body:
|
|
937
|
+
workItemId: z22.string().describe("workItemId from list_work_items"),
|
|
938
|
+
body: z22.string().min(1).describe(
|
|
908
939
|
"Comment text (markdown supported). To pull a person into the thread, mention them as [@Name](user:<userId>) \u2014 they are notified and the app renders it as a chip. userIds come from an item's assigneeId/reviewerId; there is no member lookup tool yet, so only mention ids you have seen."
|
|
909
940
|
),
|
|
910
|
-
source:
|
|
941
|
+
source: z22.enum(["user", "ai"]).optional().describe('Who authored it; defaults to "ai" for MCP callers')
|
|
911
942
|
},
|
|
912
943
|
annotations: {
|
|
913
944
|
readOnlyHint: false,
|
|
@@ -933,14 +964,14 @@ function registerAddWorkItemComment(server) {
|
|
|
933
964
|
}
|
|
934
965
|
|
|
935
966
|
// src/tools/list-work-item-comments.ts
|
|
936
|
-
import { z as
|
|
967
|
+
import { z as z23 } from "zod";
|
|
937
968
|
function registerListWorkItemComments(server) {
|
|
938
969
|
server.registerTool(
|
|
939
970
|
"list_work_item_comments",
|
|
940
971
|
{
|
|
941
972
|
description: "List the timestamped comments on a work item, oldest first. Use this to check whether the item was already touched/commented before adding a new comment.",
|
|
942
973
|
inputSchema: {
|
|
943
|
-
workItemId:
|
|
974
|
+
workItemId: z23.string().describe("workItemId from list_work_items")
|
|
944
975
|
},
|
|
945
976
|
annotations: {
|
|
946
977
|
readOnlyHint: true,
|
|
@@ -963,14 +994,14 @@ function registerListWorkItemComments(server) {
|
|
|
963
994
|
}
|
|
964
995
|
|
|
965
996
|
// src/tools/list-validations.ts
|
|
966
|
-
import { z as
|
|
997
|
+
import { z as z24 } from "zod";
|
|
967
998
|
function registerListValidations(server) {
|
|
968
999
|
server.registerTool(
|
|
969
1000
|
"list_validations",
|
|
970
1001
|
{
|
|
971
1002
|
description: "List a project's validation graph: core systems and validation/test tasks with their DERIVED state (passing, failing, stale, unvalidated). A task is 'stale' when a system it covers changed since it was last validated, or an upstream dependency is no longer passing. Call list_projects first to find the projectId.",
|
|
972
1003
|
inputSchema: {
|
|
973
|
-
projectId:
|
|
1004
|
+
projectId: z24.string().describe("projectId from list_projects")
|
|
974
1005
|
},
|
|
975
1006
|
annotations: {
|
|
976
1007
|
readOnlyHint: true,
|
|
@@ -991,15 +1022,15 @@ function registerListValidations(server) {
|
|
|
991
1022
|
}
|
|
992
1023
|
|
|
993
1024
|
// src/tools/record-validation.ts
|
|
994
|
-
import { z as
|
|
1025
|
+
import { z as z25 } from "zod";
|
|
995
1026
|
function registerRecordValidation(server) {
|
|
996
1027
|
server.registerTool(
|
|
997
1028
|
"record_validation",
|
|
998
1029
|
{
|
|
999
1030
|
description: "Check off a validation task by recording a pass or fail. Stamps the task as validated 'now', clearing any stale flag until a covered system changes or an upstream dependency moves again. Get validationTaskId from list_validations.",
|
|
1000
1031
|
inputSchema: {
|
|
1001
|
-
validationTaskId:
|
|
1002
|
-
result:
|
|
1032
|
+
validationTaskId: z25.string().describe("validationTaskId from list_validations"),
|
|
1033
|
+
result: z25.enum(["pass", "fail"]).describe("Outcome of running the test")
|
|
1003
1034
|
},
|
|
1004
1035
|
annotations: {
|
|
1005
1036
|
readOnlyHint: false,
|
|
@@ -1023,14 +1054,14 @@ function registerRecordValidation(server) {
|
|
|
1023
1054
|
}
|
|
1024
1055
|
|
|
1025
1056
|
// src/tools/mark-system-changed.ts
|
|
1026
|
-
import { z as
|
|
1057
|
+
import { z as z26 } from "zod";
|
|
1027
1058
|
function registerMarkSystemChanged(server) {
|
|
1028
1059
|
server.registerTool(
|
|
1029
1060
|
"mark_system_changed",
|
|
1030
1061
|
{
|
|
1031
1062
|
description: "Mark a core system as changed. This is the single action that invalidates testing: every validation task that covers this system (and everything transitively depending on those tasks) immediately becomes 'stale' and needs revalidation. Get systemId from list_validations.",
|
|
1032
1063
|
inputSchema: {
|
|
1033
|
-
systemId:
|
|
1064
|
+
systemId: z26.string().describe("systemId from list_validations")
|
|
1034
1065
|
},
|
|
1035
1066
|
annotations: {
|
|
1036
1067
|
readOnlyHint: false,
|
|
@@ -1053,16 +1084,16 @@ function registerMarkSystemChanged(server) {
|
|
|
1053
1084
|
}
|
|
1054
1085
|
|
|
1055
1086
|
// src/tools/create-system.ts
|
|
1056
|
-
import { z as
|
|
1087
|
+
import { z as z27 } from "zod";
|
|
1057
1088
|
function registerCreateSystem(server) {
|
|
1058
1089
|
server.registerTool(
|
|
1059
1090
|
"create_system",
|
|
1060
1091
|
{
|
|
1061
1092
|
description: "Create a core system in a project \u2014 a subsystem (e.g. Auth, Payments, Sync) whose change should invalidate the validation tasks that cover it. Returns the new systemId.",
|
|
1062
1093
|
inputSchema: {
|
|
1063
|
-
projectId:
|
|
1064
|
-
name:
|
|
1065
|
-
description:
|
|
1094
|
+
projectId: z27.string().describe("projectId from list_projects"),
|
|
1095
|
+
name: z27.string().min(1).describe("Short system name, e.g. 'Auth'"),
|
|
1096
|
+
description: z27.string().optional().describe("Optional details")
|
|
1066
1097
|
},
|
|
1067
1098
|
annotations: {
|
|
1068
1099
|
readOnlyHint: false,
|
|
@@ -1085,20 +1116,20 @@ function registerCreateSystem(server) {
|
|
|
1085
1116
|
}
|
|
1086
1117
|
|
|
1087
1118
|
// src/tools/create-validation-task.ts
|
|
1088
|
-
import { z as
|
|
1119
|
+
import { z as z28 } from "zod";
|
|
1089
1120
|
function registerCreateValidationTask(server) {
|
|
1090
1121
|
server.registerTool(
|
|
1091
1122
|
"create_validation_task",
|
|
1092
1123
|
{
|
|
1093
1124
|
description: "Create a validation/test task in a project. After creating it, use add_system_to_task to declare which systems it exercises (so it goes stale when they change) and add_validation_dependency to order it after other tasks. Returns the new validationTaskId.",
|
|
1094
1125
|
inputSchema: {
|
|
1095
|
-
projectId:
|
|
1096
|
-
title:
|
|
1097
|
-
description:
|
|
1098
|
-
kind:
|
|
1126
|
+
projectId: z28.string().describe("projectId from list_projects"),
|
|
1127
|
+
title: z28.string().min(1).describe("What this test validates"),
|
|
1128
|
+
description: z28.string().optional().describe("Optional steps / details"),
|
|
1129
|
+
kind: z28.enum(["auto", "manual"]).optional().describe(
|
|
1099
1130
|
"'auto' if runnable by a test runner, 'manual' if a human checks it. Defaults to manual."
|
|
1100
1131
|
),
|
|
1101
|
-
workItemId:
|
|
1132
|
+
workItemId: z28.string().optional().describe(
|
|
1102
1133
|
"Optional workItemId to link this test to a feature for traceability"
|
|
1103
1134
|
)
|
|
1104
1135
|
},
|
|
@@ -1123,15 +1154,15 @@ function registerCreateValidationTask(server) {
|
|
|
1123
1154
|
}
|
|
1124
1155
|
|
|
1125
1156
|
// src/tools/add-system-to-task.ts
|
|
1126
|
-
import { z as
|
|
1157
|
+
import { z as z29 } from "zod";
|
|
1127
1158
|
function registerAddSystemToTask(server) {
|
|
1128
1159
|
server.registerTool(
|
|
1129
1160
|
"add_system_to_task",
|
|
1130
1161
|
{
|
|
1131
1162
|
description: "Declare that a validation task COVERS (exercises) a system. Once linked, the task becomes 'stale' whenever that system is marked changed. Idempotent. Both IDs come from list_validations and must be in the same project.",
|
|
1132
1163
|
inputSchema: {
|
|
1133
|
-
validationTaskId:
|
|
1134
|
-
systemId:
|
|
1164
|
+
validationTaskId: z29.string().describe("validationTaskId from list_validations"),
|
|
1165
|
+
systemId: z29.string().describe("systemId from list_validations")
|
|
1135
1166
|
},
|
|
1136
1167
|
annotations: {
|
|
1137
1168
|
readOnlyHint: false,
|
|
@@ -1155,15 +1186,15 @@ function registerAddSystemToTask(server) {
|
|
|
1155
1186
|
}
|
|
1156
1187
|
|
|
1157
1188
|
// src/tools/add-validation-dependency.ts
|
|
1158
|
-
import { z as
|
|
1189
|
+
import { z as z30 } from "zod";
|
|
1159
1190
|
function registerAddValidationDependency(server) {
|
|
1160
1191
|
server.registerTool(
|
|
1161
1192
|
"add_validation_dependency",
|
|
1162
1193
|
{
|
|
1163
1194
|
description: "Make one validation task depend on another (validationTaskId depends on dependsOnTaskId). The dependent goes 'stale' whenever the upstream task is not passing or gets revalidated. Cycles and self-dependencies are rejected. Idempotent. Both IDs come from list_validations and must be in the same project.",
|
|
1164
1195
|
inputSchema: {
|
|
1165
|
-
validationTaskId:
|
|
1166
|
-
dependsOnTaskId:
|
|
1196
|
+
validationTaskId: z30.string().describe("The dependent (downstream) task"),
|
|
1197
|
+
dependsOnTaskId: z30.string().describe("The dependency (upstream) task it relies on")
|
|
1167
1198
|
},
|
|
1168
1199
|
annotations: {
|
|
1169
1200
|
readOnlyHint: false,
|
|
@@ -1187,14 +1218,14 @@ function registerAddValidationDependency(server) {
|
|
|
1187
1218
|
}
|
|
1188
1219
|
|
|
1189
1220
|
// src/tools/list-labels.ts
|
|
1190
|
-
import { z as
|
|
1221
|
+
import { z as z31 } from "zod";
|
|
1191
1222
|
function registerListLabels(server) {
|
|
1192
1223
|
server.registerTool(
|
|
1193
1224
|
"list_labels",
|
|
1194
1225
|
{
|
|
1195
1226
|
description: "List all labels defined in a project. Returns each label's id, name, and color. Use the labelId with add_label_to_work_item / remove_label_from_work_item.",
|
|
1196
1227
|
inputSchema: {
|
|
1197
|
-
projectId:
|
|
1228
|
+
projectId: z31.string().describe("projectId from list_projects")
|
|
1198
1229
|
},
|
|
1199
1230
|
annotations: {
|
|
1200
1231
|
readOnlyHint: true,
|
|
@@ -1214,16 +1245,16 @@ function registerListLabels(server) {
|
|
|
1214
1245
|
}
|
|
1215
1246
|
|
|
1216
1247
|
// src/tools/create-label.ts
|
|
1217
|
-
import { z as
|
|
1248
|
+
import { z as z32 } from "zod";
|
|
1218
1249
|
function registerCreateLabel(server) {
|
|
1219
1250
|
server.registerTool(
|
|
1220
1251
|
"create_label",
|
|
1221
1252
|
{
|
|
1222
1253
|
description: "Apply-or-seed a label. Returns the existing label if the name is already taken (idempotent), and otherwise creates it ONLY if the name is one of the curated ones. Any other new name is REFUSED \u2014 the reply carries `refused: true`, the reason, and `available`, the project's existing labels. Agents apply labels; they do not invent them, because a near-duplicate of an existing label splits the vocabulary silently. Prefer list_labels first. Colors are ignored for curated names so the vocabulary looks the same in every project.",
|
|
1223
1254
|
inputSchema: {
|
|
1224
|
-
projectId:
|
|
1225
|
-
name:
|
|
1226
|
-
color:
|
|
1255
|
+
projectId: z32.string().describe("projectId from list_projects"),
|
|
1256
|
+
name: z32.string().min(1).describe("Label name, unique within the project"),
|
|
1257
|
+
color: z32.string().regex(/^#[0-9a-fA-F]{6}$/).optional().describe("Hex color like #2563eb. Defaults to a neutral slate.")
|
|
1227
1258
|
},
|
|
1228
1259
|
annotations: {
|
|
1229
1260
|
readOnlyHint: false,
|
|
@@ -1245,15 +1276,15 @@ function registerCreateLabel(server) {
|
|
|
1245
1276
|
}
|
|
1246
1277
|
|
|
1247
1278
|
// src/tools/add-label-to-work-item.ts
|
|
1248
|
-
import { z as
|
|
1279
|
+
import { z as z33 } from "zod";
|
|
1249
1280
|
function registerAddLabelToWorkItem(server) {
|
|
1250
1281
|
server.registerTool(
|
|
1251
1282
|
"add_label_to_work_item",
|
|
1252
1283
|
{
|
|
1253
1284
|
description: "Attach a label to a work item (idempotent). The label and work item must be in the same project. Get labelIds from list_labels / create_label.",
|
|
1254
1285
|
inputSchema: {
|
|
1255
|
-
workItemId:
|
|
1256
|
-
labelId:
|
|
1286
|
+
workItemId: z33.string().describe("workItemId from list_work_items"),
|
|
1287
|
+
labelId: z33.string().describe("labelId from list_labels or create_label")
|
|
1257
1288
|
},
|
|
1258
1289
|
annotations: {
|
|
1259
1290
|
readOnlyHint: false,
|
|
@@ -1276,15 +1307,15 @@ function registerAddLabelToWorkItem(server) {
|
|
|
1276
1307
|
}
|
|
1277
1308
|
|
|
1278
1309
|
// src/tools/remove-label-from-work-item.ts
|
|
1279
|
-
import { z as
|
|
1310
|
+
import { z as z34 } from "zod";
|
|
1280
1311
|
function registerRemoveLabelFromWorkItem(server) {
|
|
1281
1312
|
server.registerTool(
|
|
1282
1313
|
"remove_label_from_work_item",
|
|
1283
1314
|
{
|
|
1284
1315
|
description: "Remove a label from a work item (idempotent \u2014 a no-op if it wasn't attached).",
|
|
1285
1316
|
inputSchema: {
|
|
1286
|
-
workItemId:
|
|
1287
|
-
labelId:
|
|
1317
|
+
workItemId: z34.string().describe("workItemId from list_work_items"),
|
|
1318
|
+
labelId: z34.string().describe("labelId from list_labels")
|
|
1288
1319
|
},
|
|
1289
1320
|
annotations: {
|
|
1290
1321
|
readOnlyHint: false,
|
|
@@ -1307,14 +1338,14 @@ function registerRemoveLabelFromWorkItem(server) {
|
|
|
1307
1338
|
}
|
|
1308
1339
|
|
|
1309
1340
|
// src/tools/list-milestones.ts
|
|
1310
|
-
import { z as
|
|
1341
|
+
import { z as z35 } from "zod";
|
|
1311
1342
|
function registerListMilestones(server) {
|
|
1312
1343
|
server.registerTool(
|
|
1313
1344
|
"list_milestones",
|
|
1314
1345
|
{
|
|
1315
1346
|
description: "List all milestones in a project. Returns each milestone's id, name, description, dueDate (unix ms), and status. Use the milestoneId with add_item_to_milestone / remove_item_from_milestone.",
|
|
1316
1347
|
inputSchema: {
|
|
1317
|
-
projectId:
|
|
1348
|
+
projectId: z35.string().describe("projectId from list_projects")
|
|
1318
1349
|
},
|
|
1319
1350
|
annotations: {
|
|
1320
1351
|
readOnlyHint: true,
|
|
@@ -1334,17 +1365,17 @@ function registerListMilestones(server) {
|
|
|
1334
1365
|
}
|
|
1335
1366
|
|
|
1336
1367
|
// src/tools/create-milestone.ts
|
|
1337
|
-
import { z as
|
|
1368
|
+
import { z as z36 } from "zod";
|
|
1338
1369
|
function registerCreateMilestone(server) {
|
|
1339
1370
|
server.registerTool(
|
|
1340
1371
|
"create_milestone",
|
|
1341
1372
|
{
|
|
1342
1373
|
description: "Create a milestone in a project. Returns the milestoneId. Good for grouping work into phases (e.g. 'Phase 1 \u2014 Web', 'Phase 2 \u2014 Native').",
|
|
1343
1374
|
inputSchema: {
|
|
1344
|
-
projectId:
|
|
1345
|
-
name:
|
|
1346
|
-
description:
|
|
1347
|
-
dueDate:
|
|
1375
|
+
projectId: z36.string().describe("projectId from list_projects"),
|
|
1376
|
+
name: z36.string().min(1).describe("Milestone name"),
|
|
1377
|
+
description: z36.string().optional().describe("Optional markdown description"),
|
|
1378
|
+
dueDate: z36.number().optional().describe("Optional due date as a unix timestamp in milliseconds")
|
|
1348
1379
|
},
|
|
1349
1380
|
annotations: {
|
|
1350
1381
|
readOnlyHint: false,
|
|
@@ -1366,15 +1397,15 @@ function registerCreateMilestone(server) {
|
|
|
1366
1397
|
}
|
|
1367
1398
|
|
|
1368
1399
|
// src/tools/add-item-to-milestone.ts
|
|
1369
|
-
import { z as
|
|
1400
|
+
import { z as z37 } from "zod";
|
|
1370
1401
|
function registerAddItemToMilestone(server) {
|
|
1371
1402
|
server.registerTool(
|
|
1372
1403
|
"add_item_to_milestone",
|
|
1373
1404
|
{
|
|
1374
1405
|
description: "Associate a work item with a milestone (idempotent). Both must be in the same project.",
|
|
1375
1406
|
inputSchema: {
|
|
1376
|
-
milestoneId:
|
|
1377
|
-
workItemId:
|
|
1407
|
+
milestoneId: z37.string().describe("milestoneId from list_milestones or create_milestone"),
|
|
1408
|
+
workItemId: z37.string().describe("workItemId from list_work_items")
|
|
1378
1409
|
},
|
|
1379
1410
|
annotations: {
|
|
1380
1411
|
readOnlyHint: false,
|
|
@@ -1400,15 +1431,15 @@ function registerAddItemToMilestone(server) {
|
|
|
1400
1431
|
}
|
|
1401
1432
|
|
|
1402
1433
|
// src/tools/remove-item-from-milestone.ts
|
|
1403
|
-
import { z as
|
|
1434
|
+
import { z as z38 } from "zod";
|
|
1404
1435
|
function registerRemoveItemFromMilestone(server) {
|
|
1405
1436
|
server.registerTool(
|
|
1406
1437
|
"remove_item_from_milestone",
|
|
1407
1438
|
{
|
|
1408
1439
|
description: "Remove a work item's association with a milestone (idempotent \u2014 a no-op if it wasn't associated).",
|
|
1409
1440
|
inputSchema: {
|
|
1410
|
-
milestoneId:
|
|
1411
|
-
workItemId:
|
|
1441
|
+
milestoneId: z38.string().describe("milestoneId from list_milestones"),
|
|
1442
|
+
workItemId: z38.string().describe("workItemId from list_work_items")
|
|
1412
1443
|
},
|
|
1413
1444
|
annotations: {
|
|
1414
1445
|
readOnlyHint: false,
|
|
@@ -1463,6 +1494,7 @@ function createServer() {
|
|
|
1463
1494
|
registerListScratchNotes(server);
|
|
1464
1495
|
registerResolveScratchNote(server);
|
|
1465
1496
|
registerHeartbeatWorkItem(server);
|
|
1497
|
+
registerWatchWorkItem(server);
|
|
1466
1498
|
registerAddWorkItemImage(server);
|
|
1467
1499
|
registerListWorkItemImages(server);
|
|
1468
1500
|
registerAddWorkItemComment(server);
|
package/dist/index.js.map
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"version": 3,
|
|
3
|
-
"sources": ["../src/index.ts", "../src/server.ts", "../package.json", "../src/instructions.ts", "../src/convex.ts", "../../convex/convex/_generated/api.js", "../src/tools/list-orgs.ts", "../src/tools/list-projects.ts", "../src/tools/list-work-items.ts", "../src/tools/get-work-items.ts", "../src/tools/search-work-items.ts", "../src/tools/list-ai-review-queue.ts", "../src/tools/get-active-block.ts", "../src/tools/create-work-item.ts", "../src/tools/titleGuidance.ts", "../src/tools/statusGuidance.ts", "../../convex/convex/lib/descriptionLimits.ts", "../src/tools/descriptionGuidance.ts", "../src/tools/create-project.ts", "../src/tools/update-work-item.ts", "../src/tools/researchFormat.ts", "../src/tools/move-work-item.ts", "../src/tools/create-document.ts", "../src/tools/update-document.ts", "../src/tools/list-documents.ts", "../src/tools/create-project-link.ts", "../src/tools/list-project-links.ts", "../src/tools/list-scratch-notes.ts", "../src/tools/resolve-scratch-note.ts", "../src/tools/heartbeat-work-item.ts", "../src/tools/add-work-item-image.ts", "../src/tools/list-work-item-images.ts", "../src/tools/add-work-item-comment.ts", "../src/tools/list-work-item-comments.ts", "../src/tools/list-validations.ts", "../src/tools/record-validation.ts", "../src/tools/mark-system-changed.ts", "../src/tools/create-system.ts", "../src/tools/create-validation-task.ts", "../src/tools/add-system-to-task.ts", "../src/tools/add-validation-dependency.ts", "../src/tools/list-labels.ts", "../src/tools/create-label.ts", "../src/tools/add-label-to-work-item.ts", "../src/tools/remove-label-from-work-item.ts", "../src/tools/list-milestones.ts", "../src/tools/create-milestone.ts", "../src/tools/add-item-to-milestone.ts", "../src/tools/remove-item-from-milestone.ts"],
|
|
4
|
-
"sourcesContent": ["#!/usr/bin/env node\n// MCP stdio transport reserves stdout for JSON-RPC frames. Any library that\n// writes to stdout (e.g. the Convex client's `[CONVEX A(uth)]` info logs)\n// corrupts the stream. Redirect console.* to stderr before anything else loads.\nfor (const m of [\"log\", \"info\", \"warn\", \"debug\"] as const) {\n console[m] = (...args: unknown[]) => console.error(...args);\n}\n\nimport { StdioServerTransport } from \"@modelcontextprotocol/sdk/server/stdio.js\";\nimport { createServer } from \"./server.js\";\n\nasync function main() {\n const server = createServer();\n const transport = new StdioServerTransport();\n await server.connect(transport);\n // Server runs until stdin closes; nothing else to do here.\n}\n\nmain().catch((err) => {\n console.error(\"nimara-mcp: fatal error\", err);\n process.exit(1);\n});\n", "import { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport pkg from \"../package.json\" with { type: \"json\" };\nimport { INSTRUCTIONS } from \"./instructions.js\";\nimport { setClientInfo } from \"./convex.js\";\nimport { registerListOrgs } from \"./tools/list-orgs.js\";\nimport { registerListProjects } from \"./tools/list-projects.js\";\nimport { registerListWorkItems } from \"./tools/list-work-items.js\";\nimport { registerGetWorkItems } from \"./tools/get-work-items.js\";\nimport { registerSearchWorkItems } from \"./tools/search-work-items.js\";\nimport { registerListAiReviewQueue } from \"./tools/list-ai-review-queue.js\";\nimport { registerGetActiveBlock } from \"./tools/get-active-block.js\";\nimport { registerCreateWorkItem } from \"./tools/create-work-item.js\";\nimport { registerCreateProject } from \"./tools/create-project.js\";\nimport { registerUpdateWorkItem } from \"./tools/update-work-item.js\";\nimport { registerMoveWorkItem } from \"./tools/move-work-item.js\";\nimport { registerCreateDocument } from \"./tools/create-document.js\";\nimport { registerUpdateDocument } from \"./tools/update-document.js\";\nimport { registerListDocuments } from \"./tools/list-documents.js\";\nimport { registerCreateProjectLink } from \"./tools/create-project-link.js\";\nimport { registerListProjectLinks } from \"./tools/list-project-links.js\";\nimport { registerListScratchNotes } from \"./tools/list-scratch-notes.js\";\nimport { registerResolveScratchNote } from \"./tools/resolve-scratch-note.js\";\nimport { registerHeartbeatWorkItem } from \"./tools/heartbeat-work-item.js\";\nimport { registerAddWorkItemImage } from \"./tools/add-work-item-image.js\";\nimport { registerListWorkItemImages } from \"./tools/list-work-item-images.js\";\nimport { registerAddWorkItemComment } from \"./tools/add-work-item-comment.js\";\nimport { registerListWorkItemComments } from \"./tools/list-work-item-comments.js\";\nimport { registerListValidations } from \"./tools/list-validations.js\";\nimport { registerRecordValidation } from \"./tools/record-validation.js\";\nimport { registerMarkSystemChanged } from \"./tools/mark-system-changed.js\";\nimport { registerCreateSystem } from \"./tools/create-system.js\";\nimport { registerCreateValidationTask } from \"./tools/create-validation-task.js\";\nimport { registerAddSystemToTask } from \"./tools/add-system-to-task.js\";\nimport { registerAddValidationDependency } from \"./tools/add-validation-dependency.js\";\nimport { registerListLabels } from \"./tools/list-labels.js\";\nimport { registerCreateLabel } from \"./tools/create-label.js\";\nimport { registerAddLabelToWorkItem } from \"./tools/add-label-to-work-item.js\";\nimport { registerRemoveLabelFromWorkItem } from \"./tools/remove-label-from-work-item.js\";\nimport { registerListMilestones } from \"./tools/list-milestones.js\";\nimport { registerCreateMilestone } from \"./tools/create-milestone.js\";\nimport { registerAddItemToMilestone } from \"./tools/add-item-to-milestone.js\";\nimport { registerRemoveItemFromMilestone } from \"./tools/remove-item-from-milestone.js\";\n\nexport function createServer(): McpServer {\n const server = new McpServer(\n {\n name: \"nimara\",\n version: pkg.version,\n },\n // Sent at connect time, before any tool is read (NIM-T189).\n { instructions: INSTRUCTIONS },\n );\n // The client's name arrives with initialize; keep it for every later write.\n server.server.oninitialized = () => setClientInfo(server.server.getClientVersion());\n\n registerListOrgs(server);\n registerListProjects(server);\n registerListWorkItems(server);\n registerGetWorkItems(server);\n registerSearchWorkItems(server);\n registerListAiReviewQueue(server);\n registerGetActiveBlock(server);\n registerCreateProject(server);\n registerCreateWorkItem(server);\n registerUpdateWorkItem(server);\n registerMoveWorkItem(server);\n registerCreateDocument(server);\n registerUpdateDocument(server);\n registerListDocuments(server);\n registerCreateProjectLink(server);\n registerListProjectLinks(server);\n registerListScratchNotes(server);\n registerResolveScratchNote(server);\n registerHeartbeatWorkItem(server);\n registerAddWorkItemImage(server);\n registerListWorkItemImages(server);\n registerAddWorkItemComment(server);\n registerListWorkItemComments(server);\n\n // Validation / test-dependency framework\n registerListValidations(server);\n registerRecordValidation(server);\n registerMarkSystemChanged(server);\n registerCreateSystem(server);\n registerCreateValidationTask(server);\n registerAddSystemToTask(server);\n registerAddValidationDependency(server);\n\n // Labels & milestones\n registerListLabels(server);\n registerCreateLabel(server);\n registerAddLabelToWorkItem(server);\n registerRemoveLabelFromWorkItem(server);\n registerListMilestones(server);\n registerCreateMilestone(server);\n registerAddItemToMilestone(server);\n registerRemoveItemFromMilestone(server);\n\n return server;\n}\n", "{\n \"name\": \"@nimara-app/mcp\",\n \"version\": \"0.5.0\",\n \"private\": false,\n \"mcpName\": \"io.github.langskip-studios/nimara\",\n \"description\": \"Nimara MCP server \u2014 AI tool integration for Claude, Codex, and others\",\n \"license\": \"MIT\",\n \"type\": \"module\",\n \"main\": \"dist/index.js\",\n \"bin\": {\n \"nimara-mcp\": \"dist/index.js\"\n },\n \"files\": [\n \"dist\",\n \"README.md\"\n ],\n \"keywords\": [\n \"mcp\",\n \"model-context-protocol\",\n \"nimara\",\n \"claude\",\n \"ai\",\n \"convex\"\n ],\n \"repository\": {\n \"type\": \"git\",\n \"url\": \"git+https://github.com/Langskip-Studios/Nimara.git\",\n \"directory\": \"packages/mcp\"\n },\n \"homepage\": \"https://github.com/Langskip-Studios/Nimara/tree/master/packages/mcp#readme\",\n \"publishConfig\": {\n \"access\": \"public\"\n },\n \"scripts\": {\n \"build\": \"node build.mjs\",\n \"dev\": \"node build.mjs\",\n \"start\": \"node dist/index.js\",\n \"typecheck\": \"tsc --noEmit\",\n \"prepublishOnly\": \"npm run typecheck && npm run build\"\n },\n \"dependencies\": {\n \"@modelcontextprotocol/sdk\": \"^1.0.0\",\n \"convex\": \"^1.18.0\",\n \"zod\": \"^3.23.0\"\n },\n \"devDependencies\": {\n \"@nimara/convex\": \"workspace:*\",\n \"@types/node\": \"^20.0.0\",\n \"esbuild\": \"^0.23.0\",\n \"typescript\": \"^5.0.0\"\n },\n \"engines\": {\n \"node\": \">=20\"\n }\n}\n", "/**\n * What every MCP client is told at connect time, before any tool is read.\n *\n * The rules that span tools \u2014 titles, statuses, the lease, mentions \u2014 each\n * live in one tool's parameter description, so a model that never loads that\n * tool never hears them. This is the map; the tool descriptions stay the\n * detailed reference. Kept short on purpose: it sits in the model's context\n * for the whole session.\n */\nexport const INSTRUCTIONS = `Nimara is the team's work tracker. Work items have a type (epic > feature > task > subtask), a status from the project's own workflow, and a displayId like NIM-T42 that people read and type.\n\nStart with list_orgs \u2192 list_projects \u2192 get_active_block (the committed work; position 0 is next) and list_ai_review_queue (what a person has asked an agent to do; read \\`answer\\` first). Use get_work_items / search_work_items for items you already know of; list_work_items only to survey.\n\nTitles are plain language a teammate understands at a glance: what is wrong or what changes for a person, not the file, function or mechanism. No em dashes, no \"Area: thing, thing\" shapes. Descriptions carry the why, acceptance criteria and file paths; a spec, design or long report goes in a document (create_document) linked from the item.\n\nA status must be one of the project's \\`statuses\\` from list_projects, spelled exactly; never invent one. Labels come from list_labels; do not invent those either.\n\nWhen you pick up an item: update_work_item { status: <in-progress status>, agentWorking: true, model: <the model you run as> }. That lights its row for 15 minutes and lets the app say whose agent, and which, is on it; any write or read of the item renews it, and on a long stretch with no Nimara calls, heartbeat_work_item every few minutes keeps it lit. Post a comment at real milestones. If you stop early, agentWorking: false. Moving to the last status clears it.\n\nMention a person in a comment as [@Name](user:<userId>) and they are notified. Append agent research to a description under the exact heading \"## Research (auto)\", never editing the human text above it. When you open a PR, put the displayId in its title.`;\n", "import { ConvexHttpClient } from \"convex/browser\";\n\nlet cachedClient: ConvexHttpClient | null = null;\n\nexport function getConvexClient(): ConvexHttpClient {\n if (cachedClient) return cachedClient;\n\n const url = process.env.NIMARA_CONVEX_URL;\n if (!url) {\n throw new Error(\n \"NIMARA_CONVEX_URL is not set. Add it to your MCP client config (e.g. Claude Desktop's mcpServers env block).\"\n );\n }\n\n cachedClient = new ConvexHttpClient(url);\n return cachedClient;\n}\n\nexport function getToken(): string {\n const token = process.env.NIMARA_TOKEN;\n if (!token) {\n throw new Error(\n \"NIMARA_TOKEN is not set. Generate a personal access token from Nimara \u2192 Settings \u2192 Personal Access Tokens, then add it to your MCP client config.\"\n );\n }\n return token;\n}\n\n/**\n * Who this server is talking to. Every MCP client names itself in the\n * `initialize` request (claude-code, codex, pi, \u2026); the server keeps it so\n * writes can say which agent made them, and the app can show \"Jordan's\n * Claude Code agent is working on this\" (NIM-F43). The model is not in the\n * protocol: an agent may pass it on the tools that take `model`.\n */\nlet clientInfo: { name: string; version?: string } | undefined;\n\nexport function setClientInfo(info: { name: string; version?: string } | undefined): void {\n clientInfo = info;\n}\n\n/** The `agent` argument for a Convex write, or undefined before initialize. */\nexport function agentArg(model?: string): { client: string; model?: string } | undefined {\n if (!clientInfo) return model ? { client: \"unknown\", model } : undefined;\n const client = clientInfo.version ? `${clientInfo.name} ${clientInfo.version}` : clientInfo.name;\n return model ? { client, model } : { client };\n}\n", "/* eslint-disable */\n/**\n * Generated `api` utility.\n *\n * THIS CODE IS AUTOMATICALLY GENERATED.\n *\n * To regenerate, run `npx convex dev`.\n * @module\n */\n\nimport { anyApi, componentsGeneric } from \"convex/server\";\n\n/**\n * A utility for referencing Convex functions in your app's API.\n *\n * Usage:\n * ```js\n * const myFunctionReference = api.myModule.myFunction;\n * ```\n */\nexport const api = anyApi;\nexport const internal = anyApi;\nexport const components = componentsGeneric();\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerListOrgs(server: McpServer): void {\n server.registerTool(\n \"list_orgs\",\n {\n description:\n \"List all organizations (and the personal workspace) the authenticated user belongs to. Use this first to discover org IDs needed by other tools.\",\n inputSchema: {},\n annotations: {\n readOnlyHint: true,\n openWorldHint: false,\n },\n },\n\n async () => {\n const client = getConvexClient();\n const orgs = await client.action(api.mcp.listOrgs, { token: getToken() });\n return {\n content: [{ type: \"text\", text: JSON.stringify(orgs, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerListProjects(server: McpServer): void {\n server.registerTool(\n \"list_projects\",\n {\n description:\n \"List projects in a given organization. Call list_orgs first to find \" +\n \"the orgId. Each project includes `statuses` \u2014 its workflow in board \" +\n \"order. Read that before setting a status on any item: those names are \" +\n \"the only accepted values, and anything else is rejected.\",\n inputSchema: { orgId: z.string().describe(\"orgId from list_orgs\") },\n annotations: {\n readOnlyHint: true,\n openWorldHint: false,\n },\n },\n\n async ({ orgId }) => {\n const client = getConvexClient();\n const projects = await client.action(api.mcp.listProjects, {\n token: getToken(),\n orgId,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(projects, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerListWorkItems(server: McpServer): void {\n server.registerTool(\n \"list_work_items\",\n {\n // The description is the only place a model learns paging exists, so it\n // states the shape of the response and what to do when hasMore is true.\n description:\n \"List non-archived work items in a project, oldest-created first. Returns \" +\n \"{ items, nextCursor, hasMore }. Long descriptions are previewed \u2014 an \" +\n \"item with descriptionTruncated: true has more text, readable via \" +\n \"fullDescriptions. When hasMore is true, call again with cursor set to \" +\n \"nextCursor to get the next page \u2014 the FIRST page is the OLDEST items, so \" +\n \"recently created ones are on the LAST page and you have not seen the \" +\n \"project until hasMore is false. Narrow with status/type/parentId/\" +\n \"needsReview rather than paging and filtering yourself. If you already \" +\n \"know which items you want, use get_work_items instead \u2014 it takes \" +\n \"displayIds like NIM-T75 and costs a fraction of a list. \" +\n \"Call list_projects first for the projectId.\",\n inputSchema: {\n projectId: z.string().describe(\"projectId from list_projects\"),\n status: z\n .union([z.string(), z.array(z.string())])\n .optional()\n .describe(\n \"Only items in these statuses. Names come from the project's \" +\n \"statusOrder (e.g. 'In Progress'). One name or a list.\",\n ),\n type: z\n .union([\n z.enum([\"epic\", \"feature\", \"task\", \"subtask\"]),\n z.array(z.enum([\"epic\", \"feature\", \"task\", \"subtask\"])),\n ])\n .optional()\n .describe(\"Only items of these types. One type or a list.\"),\n parentId: z\n .string()\n .optional()\n .describe(\n \"Only direct children of this workItemId. One level, not the whole subtree.\",\n ),\n needsReview: z\n .boolean()\n .optional()\n .describe(\n \"true returns only items flagged needsReview; false only unflagged ones. \" +\n \"Omit for both.\",\n ),\n limit: z\n .number()\n .int()\n .min(1)\n .max(200)\n .optional()\n .describe(\"Items per page (default 50, max 200).\"),\n cursor: z\n .number()\n .optional()\n .describe(\n \"nextCursor from the previous page. Omit for the first page.\",\n ),\n fullDescriptions: z\n .boolean()\n .optional()\n .describe(\n \"Return descriptions in full instead of previewed. Costly on large \" +\n \"projects \u2014 prefer paging, or read one item at a time.\",\n ),\n },\n annotations: {\n readOnlyHint: true,\n openWorldHint: false,\n },\n },\n async ({\n projectId,\n limit,\n cursor,\n fullDescriptions,\n status,\n type,\n parentId,\n needsReview,\n }) => {\n const page = await getConvexClient().action(api.mcp.listWorkItems, {\n token: getToken(),\n projectId,\n limit,\n cursor,\n fullDescriptions,\n // Accepting a bare string as well as a list is what keeps a model from\n // failing validation on the overwhelmingly common single-value case.\n status:\n status === undefined\n ? undefined\n : Array.isArray(status)\n ? status\n : [status],\n type:\n type === undefined ? undefined : Array.isArray(type) ? type : [type],\n parentId,\n needsReview,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(page, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerGetWorkItems(server: McpServer): void {\n server.registerTool(\n \"get_work_items\",\n {\n // Written to be chosen *over* list_work_items whenever the caller already\n // knows which items it wants \u2014 that is the whole point of the tool, and\n // the description is the only place a model learns it.\n description:\n \"Read specific work items by id \u2014 the cheap way to re-read items you \" +\n \"already know about. Prefer this over list_work_items whenever you have \" +\n \"a displayId (e.g. NIM-T75) or a workItemId: listing a project returns \" +\n \"every item and its description, which is orders of magnitude more data. \" +\n \"Accepts up to 50 ids per call and always returns descriptions in full. \" +\n \"Returns { items, notFound }; ids in notFound either do not exist or are \" +\n \"not readable by this token. displayIds require projectId (they are \" +\n \"unique per project, not globally); workItemIds do not.\",\n inputSchema: {\n displayIds: z\n .array(z.string())\n .optional()\n .describe(\n \"Human-facing ids like ['NIM-T75', 'NIM-F27']. Case-insensitive. \" +\n \"Requires projectId.\",\n ),\n workItemIds: z\n .array(z.string())\n .optional()\n .describe(\n \"Raw workItemIds, as returned by create_work_item or list_work_items.\",\n ),\n projectId: z\n .string()\n .optional()\n .describe(\n \"projectId from list_projects. Required only when passing displayIds.\",\n ),\n },\n annotations: {\n readOnlyHint: true,\n openWorldHint: false,\n },\n },\n async ({ displayIds, workItemIds, projectId }) => {\n const result = await getConvexClient().action(api.mcp.getWorkItems, {\n token: getToken(),\n displayIds,\n workItemIds,\n projectId,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerSearchWorkItems(server: McpServer): void {\n server.registerTool(\n \"search_work_items\",\n {\n // The point of this description is to stop a model reaching for\n // list_work_items when it is looking for something by name. Listing a\n // project to find one item is the expensive mistake this tool exists to\n // prevent.\n description:\n \"Find work items in a project by title. Use this to answer 'does an \" +\n \"item for X already exist?' \u2014 listing the whole project and filtering \" +\n \"yourself is far more expensive and, because the first page is the \" +\n \"OLDEST items, easy to get wrong. Matches TITLES only, not \" +\n \"descriptions. Returns { items, query } with descriptions previewed; \" +\n \"once you know which item you want, get_work_items returns it in full. \" +\n \"Capped at 25 results \u2014 narrow the query rather than paging. \" +\n \"Call list_projects first for the projectId.\",\n inputSchema: {\n projectId: z.string().describe(\"projectId from list_projects\"),\n q: z\n .string()\n .min(1)\n .describe(\n \"Words to match against item titles, e.g. 'mobile modal' or \" +\n \"'shortcut'. Matching is full-text, so word order does not matter.\",\n ),\n limit: z\n .number()\n .int()\n .min(1)\n .max(25)\n .optional()\n .describe(\"Maximum results (default and maximum 25).\"),\n },\n annotations: { readOnlyHint: true },\n },\n async ({ projectId, q, limit }) => {\n const result = await getConvexClient().action(api.mcp.searchWorkItems, {\n token: getToken(),\n projectId,\n q,\n limit,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerListAiReviewQueue(server: McpServer): void {\n server.registerTool(\n \"list_ai_review_queue\",\n {\n description:\n \"List work items in a project that a human has flagged for AI review \" +\n \"(aiReviewRequested). Descriptions come back in full here, since \" +\n \"enrichment needs the whole text. Each item also carries recentComments \" +\n \"(the last few, oldest first) and, when a person has written one, \" +\n \"`answer`: the newest human comment. READ `answer` FIRST. When you \" +\n \"flagged an item with a question and it is back in this queue, `answer` \" +\n \"is the person's reply to that question; act on it rather than asking \" +\n \"again. Returns { items, nextCursor, hasMore } \u2014 when hasMore is true, \" +\n \"call again with cursor set to nextCursor. Process each item, then clear \" +\n \"its flag by calling update_work_item with aiReviewRequested: false. \" +\n \"Call list_projects first to find the projectId.\",\n inputSchema: {\n projectId: z.string().describe(\"projectId from list_projects\"),\n limit: z\n .number()\n .int()\n .min(1)\n .max(200)\n .optional()\n .describe(\"Items per page (default 50, max 200).\"),\n cursor: z\n .number()\n .optional()\n .describe(\n \"nextCursor from the previous page. Omit for the first page.\",\n ),\n },\n annotations: {\n readOnlyHint: true,\n openWorldHint: false,\n },\n },\n async ({ projectId, limit, cursor }) => {\n const page = await getConvexClient().action(api.mcp.listAiReviewQueue, {\n token: getToken(),\n projectId,\n limit,\n cursor,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(page, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerGetActiveBlock(server: McpServer): void {\n server.registerTool(\n \"get_active_block\",\n {\n description:\n \"The project's ACTIVE BLOCK: the small, ordered set of work a person has \" +\n \"committed to right now. Call this BEFORE list_work_items when deciding what \" +\n \"to work on \u2014 position 0 is the next thing to do, and the wider backlog is \" +\n \"not on the table until the block is empty. Each item carries a lane: \" +\n \"'person' means a human owes it (flagged for review, or parked in a Review \" +\n \"status) and you should not touch it; 'agent' means a human asked an agent \" +\n \"to act on it, so it is yours first, and it carries recentComments and \" +\n \"`answer` (the newest human comment: read it before anything else); \" +\n \"'open' is uncommitted-to-anyone work in \" +\n \"priority order; 'done' is finished. Returns null when the project has no \" +\n \"active block, in which case fall back to list_work_items. Descriptions are \" +\n \"previewed; use get_work_items for the full text of an item you pick up. \" +\n \"Call list_projects first for the projectId.\",\n inputSchema: {\n projectId: z.string().describe(\"projectId from list_projects\"),\n },\n annotations: {\n readOnlyHint: true,\n openWorldHint: false,\n },\n },\n async ({ projectId }) => {\n const block = await getConvexClient().action(api.mcp.getActiveBlock, {\n token: getToken(),\n projectId,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(block, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\nimport { TITLE_GUIDANCE } from \"./titleGuidance.js\";\nimport { STATUS_GUIDANCE } from \"./statusGuidance.js\";\nimport { DESCRIPTION_GUIDANCE, DESCRIPTION_MAX } from \"./descriptionGuidance.js\";\n\nexport function registerCreateWorkItem(server: McpServer): void {\n server.registerTool(\n \"create_work_item\",\n {\n description:\n \"Create a new work item in a project. Hierarchy rules: epics live at the root; features go under epics; tasks go under epics or features (or root); subtasks must go under a task. Returns the new workItemId and its display ID (e.g. NIM-42).\",\n inputSchema: {\n projectId: z.string().describe(\"projectId from list_projects\"),\n type: z\n .enum([\"epic\", \"feature\", \"task\", \"subtask\"])\n .describe(\"Item type \u2014 drives hierarchy validation\"),\n title: z.string().min(1).describe(TITLE_GUIDANCE),\n description: z.string().max(DESCRIPTION_MAX).optional().describe(DESCRIPTION_GUIDANCE),\n parentId: z\n .string()\n .optional()\n .describe(\n \"workItemId of the parent. Required for subtask, optional otherwise.\",\n ),\n status: z\n .string()\n .optional()\n .describe(\n STATUS_GUIDANCE,\n ),\n priority: z\n .enum([\"p0\", \"p1\", \"p2\", \"p3\"])\n .optional()\n .describe(\"p0 highest, p3 lowest. Defaults to p2.\"),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: false,\n idempotentHint: false,\n openWorldHint: false,\n },\n },\n\n async (args) => {\n const client = getConvexClient();\n const result = await client.action(api.mcp.createWorkItem, {\n token: getToken(),\n ...args,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "/**\n * What a work-item title should read like, stated once.\n *\n * This exists because \"Short, descriptive title\" \u2014 the previous guidance on\n * `create_work_item` \u2014 is satisfied by \"Fix hasChildren computation in\n * list.tsx\". That is short and it does describe something, and it is unreadable\n * to anyone who has not just been in that file. Titles are what a board shows;\n * a board full of symbol names cannot be scanned.\n *\n * The em-dash and verbosity rules come from NIM-T117, which Jordan filed\n * before this and which asked for exactly that: \"Remove the em dash and\n * other verbose title that make it hard to read.\"\n *\n * Shared by `create_work_item` and `update_work_item` so the rule cannot hold\n * on one path and not the other \u2014 retitling is the same act as titling, and\n * `update_work_item` previously carried no guidance at all.\n */\nexport const TITLE_GUIDANCE =\n \"A title a teammate can understand at a glance, without opening the item or \" +\n \"knowing the codebase. Say what is wrong or what changes FOR A PERSON, in \" +\n \"plain words \u2014 not the mechanism, the file, or the symbol. \" +\n 'Good: \"Sorted list shows an expand arrow that does nothing\". ' +\n 'Bad: \"Fix hasChildren computation in list.tsx\". ' +\n 'Good: \"Long titles wrap to three lines and are hard to read\". ' +\n 'Bad: \"Adjust COLUMNS.title min-width constant\". ' +\n \"Prefer ordinary words over internal abbreviations, and only name a file, \" +\n \"function or identifier when it genuinely is the clearest way to say it \" +\n \"(a tool or endpoint the user calls by name, for instance). No ticket \" +\n \"prefixes or status markers \u2014 the board renders those already. Root cause, \" +\n \"file paths, and reproduction steps belong in the description, which has \" +\n \"room for them. \" +\n \"Keep it to one plain clause. Do NOT use an em dash, and do not use the \" +\n '\"Area: thing, other thing\" shape \u2014 both are ways of stapling a second ' +\n \"title on and they are what makes these hard to read. \" +\n 'Bad: \"Gantt: tighten row density, match app typography, stop the chart ' +\n 'falling short of its container\". ' +\n 'Good: \"Gantt chart looks nothing like the rest of the app\". ' +\n \"If the title needs a comma-spliced list to be accurate, that is a sign the \" +\n \"item is really several items, not a sign it needs a longer title.\";\n", "/**\n * How to choose a status, stated once.\n *\n * The rule the tools already stated \u2014 \"a status name from the project's\n * statusOrder\" \u2014 referred to data no tool returned. An agent could not read a\n * project's workflow, so it guessed a plausible-sounding name, and the guess\n * was frequently \"In Review\" on boards whose workflow only ever had \"Review\".\n * `list_projects` now returns `statuses`, which is what makes this instruction\n * followable rather than aspirational.\n *\n * The second half matters as much as the first. A status is POSITIONAL \u2014 it is\n * the board column \u2014 so inventing one is not a labelling choice, it reshapes\n * the board and every status chart that aggregates across projects. Anything\n * that describes an item without saying where it sits in the flow is a label:\n * `list_labels`, `create_label` and `add_label_to_work_item` exist for exactly\n * that, and cost nothing to add. This is NIM-T49's decision, held to.\n *\n * Shared by `create_work_item` and `update_work_item`. `update_work_item.status`\n * previously carried no guidance at all, which is the path most likely to move\n * an item to an invented status.\n */\nexport const STATUS_GUIDANCE =\n \"Must be one of the names in the project's `statuses`, returned by \" +\n \"list_projects. Read it rather than guessing \u2014 a status is the board \" +\n \"column, so a name the workflow does not have is rejected, and before that \" +\n \"check existed such items rendered in the first column while claiming \" +\n \"otherwise. Match the existing name exactly, including its wording: if the \" +\n \"workflow says \\\"Review\\\", do not write \\\"In Review\\\". \" +\n \"Do NOT invent a status to capture something about an item. Statuses are \" +\n \"shared across the whole project and aggregated on the dashboard, so each \" +\n \"new one is a permanent extra band there. Anything that describes an item \" +\n \"rather than locating it in the flow belongs in a LABEL \u2014 see create_label \" +\n \"and add_label_to_work_item. Defaults to the first status when omitted.\";\n", "/**\n * The two sizes a work item description is measured against. Kept free of\n * Convex imports so the web app and the MCP package can share the numbers.\n *\n * PREVIEW is what the row carries so lists never join the body\n * (lib/workItemBody.ts). MAX is a sanity cap, not a product decision: no\n * task written by hand comes near it, but an agent pasting a log or a whole\n * research report into a description would \u2014 and that belongs in a document.\n * Descriptions averaged 14 KB when the cap was chosen; 32 KB is roughly\n * 5,000 words, eight pages.\n */\nexport const DESCRIPTION_PREVIEW_CHARS = 500;\nexport const DESCRIPTION_MAX_CHARS = 32_000;\n\n/** Where a description's length stands, for an error or a counter. */\nexport const DESCRIPTION_TOO_LONG =\n `A description can be at most ${DESCRIPTION_MAX_CHARS.toLocaleString(\"en-US\")} characters. ` +\n \"Put specs, research and long reports in a document and link it to the item.\";\n", "import { DESCRIPTION_MAX_CHARS } from \"@nimara/convex/convex/lib/descriptionLimits.js\";\n\n/**\n * What a description is for, and how big it may be, stated once and shared\n * by `create_work_item` and `update_work_item` the way TITLE_GUIDANCE is.\n *\n * The cap is enforced server-side in writeDescription; the zod max here\n * only means an agent hears about it before the round-trip. The guidance is\n * the real lever: descriptions averaged 14 KB because agents used them as\n * the place to put everything, and the row split (lib/workItemBody.ts) made\n * that cheap but not right \u2014 a document is what other items can link to.\n */\nexport const DESCRIPTION_MAX = DESCRIPTION_MAX_CHARS;\n\nexport const DESCRIPTION_GUIDANCE =\n \"Markdown. The what and the why: the problem, acceptance criteria, \" +\n \"reproduction steps, file paths, root cause. Keep it to what someone \" +\n \"picking the item up needs. A spec, a design, research, or a long report \" +\n \"goes in a document (create_document) linked from here, not inline. \" +\n `At most ${DESCRIPTION_MAX_CHARS.toLocaleString(\"en-US\")} characters.`;\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerCreateProject(server: McpServer): void {\n server.registerTool(\n \"create_project\",\n {\n description:\n \"Create a new project in an org. Prefix must be unique within the org and is uppercased (e.g. 'NIM' yields work items NIM-1, NIM-2\u2026). Caller becomes the project admin. Returns the new projectId.\",\n inputSchema: {\n orgId: z.string().describe(\"orgId from list_orgs\"),\n name: z.string().min(1).describe(\"Project name\"),\n prefix: z\n .string()\n .min(1)\n .max(8)\n .describe(\n \"Short uppercase prefix for work item IDs (e.g. 'NIM'). Unique per org.\",\n ),\n description: z\n .string()\n .optional()\n .describe(\"Optional markdown description\"),\n isPrivate: z\n .boolean()\n .optional()\n .describe(\n \"If true, only explicitly added members see it. Defaults to false.\",\n ),\n workflowTemplate: z\n .enum([\"default\", \"simple\", \"kanban\", \"bug\"])\n .optional()\n .describe(\n \"Status workflow. Defaults to 'default' (Backlog/Todo/In Progress/Review/Done).\",\n ),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: false,\n idempotentHint: false,\n openWorldHint: false,\n },\n },\n\n async (args) => {\n const client = getConvexClient();\n const result = await client.action(api.mcp.createProject, {\n token: getToken(),\n ...args,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { agentArg, getConvexClient, getToken } from \"../convex.js\";\nimport { TITLE_GUIDANCE } from \"./titleGuidance.js\";\nimport { STATUS_GUIDANCE } from \"./statusGuidance.js\";\nimport { DESCRIPTION_GUIDANCE, DESCRIPTION_MAX } from \"./descriptionGuidance.js\";\nimport { RESEARCH_FORMAT } from \"./researchFormat.js\";\n\nexport function registerUpdateWorkItem(server: McpServer): void {\n server.registerTool(\n \"update_work_item\",\n {\n description:\n \"Update an existing work item: title, description, status, priority, parent, or review flags. Any update also stamps the item as AI-touched.\",\n inputSchema: {\n workItemId: z.string().describe(\"workItemId from list_work_items\"),\n title: z.string().min(1).optional().describe(TITLE_GUIDANCE),\n description: z\n .string()\n .max(DESCRIPTION_MAX)\n .optional()\n .describe(\n \"Full markdown body, replacing what is there. \" +\n DESCRIPTION_GUIDANCE +\n \" \" +\n RESEARCH_FORMAT,\n ),\n status: z.string().optional().describe(STATUS_GUIDANCE),\n priority: z.enum([\"p0\", \"p1\", \"p2\", \"p3\"]).optional(),\n parentId: z\n .string()\n .nullable()\n .optional()\n .describe(\"New parent workItemId, null to move to root.\"),\n needsReview: z\n .boolean()\n .optional()\n .describe(\n \"Flag the item for manual human review \u2014 set true when your enrichment was thin or uncertain.\",\n ),\n reviewReason: z\n .string()\n .optional()\n .describe(\n \"Short reason the item needs manual review (shown to the human).\",\n ),\n aiReviewRequested: z\n .boolean()\n .optional()\n .describe(\n \"The human\u2192AI review flag. Set false to clear it after you have reviewed/enriched an item from list_ai_review_queue.\",\n ),\n agentWorking: z\n .boolean()\n .optional()\n .describe(\n \"Set true when you start working on this item: the app lights its row so the person can see it is in flight. It is a 15-minute lease renewed by any later MCP write on the item (updates, comments), by reading it (get_work_items, list_work_item_comments), or by heartbeat_work_item \u2014 call that every few minutes on a long task with no other Nimara calls, or the row goes quiet while you are still at it. Set false when you stop without finishing; moving the item to the last status clears it for you.\",\n ),\n model: z\n .string()\n .optional()\n .describe(\"With agentWorking: the model you are running as, e.g. claude-opus-5, so the app can say which agent is on this. Your harness is reported automatically.\"),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: true,\n idempotentHint: true,\n openWorldHint: false,\n },\n },\n\n async ({ model, ...args }) => {\n const result = await getConvexClient().action(api.mcp.updateWorkItem, {\n token: getToken(),\n ...args,\n agent: agentArg(model),\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "/**\n * The shape of the automated research block an enrichment agent appends to a\n * work item's description.\n *\n * Two reasons this is stated here rather than left to each agent's own taste.\n *\n * The web app parses this block out of the description and renders it in its\n * own tab on the item (NIM-T125). The anchor heading is therefore a contract,\n * not a style choice: change its wording and the tab stops appearing, with the\n * text still sitting in the description and nothing failing loudly.\n *\n * And the existing blocks are decorated with emoji section markers \u2014 \uD83D\uDD0E, \uD83D\uDD17,\n * \uD83E\uDDED, \uD83C\uDF9A. They read as noise in a panel that is already labelled \"Research\",\n * they carry no information the heading does not, and they are the first thing\n * Jordan asked to remove. The parser accepts the old emoji heading so the 20\n * items already enriched keep working; nothing new should write one.\n *\n * Deliberately NOT permitted: raw HTML. The app renders this with\n * `react-markdown` and no `rehype-raw`, so HTML is stripped rather than shown \u2014\n * and turning that on would render agent-authored markup whose inputs include\n * untrusted work-item text. Mermaid fences cover the diagram case without\n * opening that door.\n */\nexport const RESEARCH_FORMAT = `When appending automated research to a description, use EXACTLY this format, \\\nafter the human-written text:\n\n---\n## Research (auto)\n\n### Findings\n- One bullet per verified fact, each naming what you checked.\n\n### Dependencies\n- Items this blocks or is blocked by, by displayId. Omit the section if none.\n\n### Duplicates\n- Existing items covering the same work, by displayId. Omit if none.\n\n### Suggested priority\nOne line. Say \"No change\" when it is already right.\n\nRules:\n- The \"## Research (auto)\" heading is EXACT and is what the app keys on to show \\\nthis in its own tab. Do not reword it, renumber its level, or translate it.\n- NO EMOJI anywhere in the block, in headings or in bullets. Older items carry \\\nemoji headings; do not copy them.\n- Omit a section rather than writing \"None found\" in it. An empty section is \\\nnoise the reader still has to read.\n- Never edit or delete the human-written text above the rule. Append only.\n- Markdown only. GFM tables are supported and are the right choice for \\\ncomparisons. Raw HTML is NOT rendered by the app and must not be used.\n- For a workflow, sequence or state machine, use a \\\\\\`\\\\\\`\\\\\\`mermaid fenced block. \\\nThat is the supported way to draw one.\n- Say what you verified and how. \"Confirmed X still returns Y (file:line)\" is \\\nworth more than a conclusion with no trail.`;\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerMoveWorkItem(server: McpServer): void {\n server.registerTool(\n \"move_work_item\",\n {\n // Everything a model needs to predict the damage has to be stated here \u2014\n // the description is the only channel it has. The consequences that are\n // NOT obvious from the name are the ones worth the tokens: the display ID\n // changes, and labels/milestones do not survive.\n description:\n \"Move a work item to a different project, taking its whole subtree \" +\n \"with it \u2014 children and grandchildren move too, and the hierarchy is \" +\n \"preserved. Both projects must be in the same organization, and you \" +\n \"need write access to both. \" +\n \"Not reversible by calling this again: the item is renumbered in the \" +\n \"destination, so NIM-T44 might become SKA-T18 and the old ID stops \" +\n \"resolving. Labels and milestone assignments are dropped, because both \" +\n \"belong to the project being left; a status the destination doesn't \" +\n \"define falls back to its first status. The response reports every \" +\n \"old \u2192 new ID plus everything that was dropped or remapped. \" +\n \"Comments, images, attached documents, PR links and history all follow \" +\n \"the item. Call list_projects first for the target projectId.\",\n inputSchema: {\n workItemId: z\n .string()\n .describe(\"workItemId from list_work_items \u2014 the item to move.\"),\n targetProjectId: z\n .string()\n .describe(\n \"projectId from list_projects \u2014 the destination. Must be in the \" +\n \"same org as the item's current project.\",\n ),\n },\n annotations: {\n readOnlyHint: false,\n // Renumbering display IDs and deleting label/milestone links are\n // overwrites, not additions \u2014 this belongs with the tools a client\n // should prompt on rather than auto-approve.\n destructiveHint: true,\n // Calling it twice does not land in the same place: the second call\n // either errors as already-there or moves the item on again.\n idempotentHint: false,\n openWorldHint: false,\n },\n },\n async ({ workItemId, targetProjectId }) => {\n const result = await getConvexClient().action(\n api.mcp.moveWorkItemToProject,\n { token: getToken(), workItemId, targetProjectId },\n );\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerCreateDocument(server: McpServer): void {\n server.registerTool(\n \"create_document\",\n {\n description:\n \"Create a markdown project document. Use type 'prd' for project docs or 'fd' for feature/work-item documents.\",\n inputSchema: {\n projectId: z.string().describe(\"projectId from list_projects\"),\n title: z.string().min(1),\n type: z\n .enum([\"prd\", \"fd\"])\n .describe(\n \"Document type. 'fd' is stored as the app's feature document type.\",\n ),\n workItemId: z\n .string()\n .optional()\n .describe(\"Required for fd documents; omitted for prd.\"),\n content: z\n .string()\n .optional()\n .describe(\"Optional initial markdown content.\"),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: false,\n idempotentHint: false,\n openWorldHint: false,\n },\n },\n\n async (args) => {\n const result = await getConvexClient().action(api.mcp.createDocument, {\n token: getToken(),\n ...args,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerUpdateDocument(server: McpServer): void {\n server.registerTool(\n \"update_document\",\n {\n description:\n \"Update an existing document's markdown content and/or title. Use this to fill in or revise a document created earlier (e.g. backfill content into an empty doc). documentId comes from list_documents. Provided content fully replaces the existing content.\",\n inputSchema: {\n documentId: z.string().describe(\"documentId from list_documents\"),\n content: z\n .string()\n .optional()\n .describe(\n \"New markdown content. Replaces the document's existing content.\",\n ),\n title: z.string().min(1).optional().describe(\"New title (optional).\"),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: true,\n idempotentHint: true,\n openWorldHint: false,\n },\n },\n\n async (args) => {\n const result = await getConvexClient().action(api.mcp.updateDocument, {\n token: getToken(),\n ...args,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerListDocuments(server: McpServer): void {\n server.registerTool(\n \"list_documents\",\n {\n description:\n \"List PRD/FD markdown documents for a project, optionally filtered to one work item.\",\n inputSchema: {\n projectId: z.string().describe(\"projectId from list_projects\"),\n workItemId: z\n .string()\n .optional()\n .describe(\"Optional workItemId to list linked FD documents.\"),\n },\n annotations: {\n readOnlyHint: true,\n openWorldHint: false,\n },\n },\n\n async (args) => {\n const result = await getConvexClient().action(api.mcp.listDocuments, {\n token: getToken(),\n ...args,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nconst projectLinkCategory = z.enum([\n \"api\",\n \"dashboard\",\n \"documentation\",\n \"repository\",\n \"service\",\n \"other\",\n]);\n\nexport function registerCreateProjectLink(server: McpServer): void {\n server.registerTool(\n \"create_project_link\",\n {\n description:\n \"Save a link on a project for resources like APIs, dashboards, documentation, repositories, or services.\",\n inputSchema: {\n projectId: z.string().describe(\"projectId from list_projects\"),\n title: z.string().min(1).max(120),\n url: z.string().url().describe(\"http(s) URL to save\"),\n description: z.string().max(500).optional(),\n category: projectLinkCategory.optional().describe(\"Defaults to other.\"),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: false,\n idempotentHint: false,\n openWorldHint: false,\n },\n },\n\n async (args) => {\n const result = await getConvexClient().action(api.mcp.createProjectLink, {\n token: getToken(),\n ...args,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerListProjectLinks(server: McpServer): void {\n server.registerTool(\n \"list_project_links\",\n {\n description:\n \"List saved links for a project, such as APIs, dashboards, docs, repositories, and services.\",\n inputSchema: {\n projectId: z.string().describe(\"projectId from list_projects\"),\n },\n annotations: {\n readOnlyHint: true,\n openWorldHint: false,\n },\n },\n\n async ({ projectId }) => {\n const result = await getConvexClient().action(api.mcp.listProjectLinks, {\n token: getToken(),\n projectId,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerListScratchNotes(server: McpServer): void {\n server.registerTool(\n \"list_scratch_notes\",\n {\n description:\n \"The token owner's OPEN scratch notes: thoughts and ideas they captured \" +\n \"in the app with the `s` shortcut before deciding what to do with them. \" +\n \"Returns the notes that belong with this project (tagged with it, or \" +\n \"tagged with nothing), oldest first, each with noteId, body, projectId \" +\n \"and createdAt. These are raw: a note may be one line or a paragraph, \" +\n \"may describe one task or three, and may not be a task at all. Read \" +\n \"each, decide what it should become (usually one or more work items \" +\n \"via create_work_item, sometimes a comment on an existing item, \" +\n \"sometimes nothing), do that, then call resolve_scratch_note with the \" +\n \"noteId and the workItemId it became so the person sees where their \" +\n \"note went. Ask in a comment rather than guess when a note is too \" +\n \"thin to act on. Call list_projects first for the projectId.\",\n inputSchema: {\n projectId: z.string().describe(\"projectId from list_projects\"),\n },\n annotations: {\n readOnlyHint: true,\n openWorldHint: false,\n },\n },\n async ({ projectId }) => {\n const notes = await getConvexClient().action(api.mcp.listScratchNotes, {\n token: getToken(),\n projectId,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(notes, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerResolveScratchNote(server: McpServer): void {\n server.registerTool(\n \"resolve_scratch_note\",\n {\n description:\n \"Mark a scratch note as used, recording the work item it became. Call \" +\n \"this after acting on a note from list_scratch_notes: pass the noteId \" +\n \"and the workItemId you created or updated from it (omit workItemId \" +\n \"only when the note needed no item). The note leaves the person's open \" +\n \"list and shows where it went. Only the token owner's own notes.\",\n inputSchema: {\n noteId: z.string().describe(\"noteId from list_scratch_notes\"),\n workItemId: z\n .string()\n .optional()\n .describe(\"The workItemId the note became, from create_work_item or list_work_items.\"),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: false,\n idempotentHint: true,\n openWorldHint: false,\n },\n },\n async ({ noteId, workItemId }) => {\n const result = await getConvexClient().action(api.mcp.resolveScratchNote, {\n token: getToken(),\n noteId,\n workItemId,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { agentArg, getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerHeartbeatWorkItem(server: McpServer): void {\n server.registerTool(\n \"heartbeat_work_item\",\n {\n description:\n \"Say you are still working on an item. Renews (or starts) its 15-minute \" +\n \"\\\"agent working\\\" lease and does nothing else: no comment, no activity \" +\n \"event, no change to the item. The app lights the row while the lease is \" +\n \"live, so on a long task call this every few minutes or every handful of \" +\n \"tool calls \u2014 otherwise the row goes quiet while you are still at it. \" +\n \"Reads of the item (get_work_items, list_work_item_comments) also renew a \" +\n \"live lease, and any update or comment does; this is for the stretches \" +\n \"where you do none of those. Cheap and idempotent.\",\n inputSchema: {\n workItemId: z.string().describe(\"workItemId of the item you are working on\"),\n model: z\n .string()\n .optional()\n .describe(\"The model you are running as, e.g. claude-opus-5 or gpt-5, so the app can say which agent is on this. Your harness is reported automatically.\"),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: false,\n idempotentHint: true,\n openWorldHint: false,\n },\n },\n async ({ workItemId, model }) => {\n const result = await getConvexClient().action(api.mcp.heartbeatWorkItem, {\n token: getToken(),\n workItemId,\n agent: agentArg(model),\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerAddWorkItemImage(server: McpServer): void {\n server.registerTool(\n \"add_work_item_image\",\n {\n description:\n \"Attach an externally hosted image URL to a work item. Use this when an MCP client has a screenshot, mockup, or generated image URL to preserve with the task.\",\n inputSchema: {\n workItemId: z.string().describe(\"workItemId from list_work_items\"),\n imageUrl: z\n .string()\n .url()\n .describe(\"Public or otherwise fetchable http(s) image URL\"),\n filename: z.string().optional().describe(\"Optional display filename\"),\n altText: z\n .string()\n .optional()\n .describe(\"Optional description/caption for the image\"),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: false,\n idempotentHint: false,\n openWorldHint: false,\n },\n },\n\n async (args) => {\n const result = await getConvexClient().action(api.mcp.addWorkItemImage, {\n token: getToken(),\n ...args,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerListWorkItemImages(server: McpServer): void {\n server.registerTool(\n \"list_work_item_images\",\n {\n description:\n \"List image attachments for a work item, including uploaded images and externally attached MCP images. Call list_work_items first to find the workItemId.\",\n inputSchema: {\n workItemId: z.string().describe(\"workItemId from list_work_items\"),\n },\n annotations: {\n readOnlyHint: true,\n openWorldHint: false,\n },\n },\n\n async ({ workItemId }) => {\n const result = await getConvexClient().action(\n api.mcp.listWorkItemImages,\n {\n token: getToken(),\n workItemId,\n },\n );\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { agentArg, getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerAddWorkItemComment(server: McpServer): void {\n server.registerTool(\n \"add_work_item_comment\",\n {\n description:\n \"Add a timestamped comment to a work item. Use this to record notes, updates, \" +\n \"or an 'AI touched' entry instead of editing the description. Comments are \" +\n \"stamped with the current time automatically and never overwrite each other.\",\n inputSchema: {\n workItemId: z.string().describe(\"workItemId from list_work_items\"),\n body: z\n .string()\n .min(1)\n .describe(\n \"Comment text (markdown supported). To pull a person into the thread, mention them as [@Name](user:<userId>) \u2014 they are notified and the app renders it as a chip. userIds come from an item's assigneeId/reviewerId; there is no member lookup tool yet, so only mention ids you have seen.\",\n ),\n source: z\n .enum([\"user\", \"ai\"])\n .optional()\n .describe('Who authored it; defaults to \"ai\" for MCP callers'),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: false,\n idempotentHint: false,\n openWorldHint: false,\n },\n },\n\n async (args) => {\n const result = await getConvexClient().action(\n api.mcp.addWorkItemComment,\n {\n token: getToken(),\n ...args,\n agent: agentArg(),\n },\n );\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerListWorkItemComments(server: McpServer): void {\n server.registerTool(\n \"list_work_item_comments\",\n {\n description:\n \"List the timestamped comments on a work item, oldest first. Use this to check \" +\n \"whether the item was already touched/commented before adding a new comment.\",\n inputSchema: {\n workItemId: z.string().describe(\"workItemId from list_work_items\"),\n },\n annotations: {\n readOnlyHint: true,\n openWorldHint: false,\n },\n },\n\n async (args) => {\n const result = await getConvexClient().action(\n api.mcp.listWorkItemComments,\n {\n token: getToken(),\n ...args,\n },\n );\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerListValidations(server: McpServer): void {\n server.registerTool(\n \"list_validations\",\n {\n description:\n \"List a project's validation graph: core systems and validation/test tasks with their DERIVED state (passing, failing, stale, unvalidated). A task is 'stale' when a system it covers changed since it was last validated, or an upstream dependency is no longer passing. Call list_projects first to find the projectId.\",\n inputSchema: {\n projectId: z.string().describe(\"projectId from list_projects\"),\n },\n annotations: {\n readOnlyHint: true,\n openWorldHint: false,\n },\n },\n\n async ({ projectId }) => {\n const client = getConvexClient();\n const graph = await client.action(api.mcp.listValidations, {\n token: getToken(),\n projectId,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(graph, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerRecordValidation(server: McpServer): void {\n server.registerTool(\n \"record_validation\",\n {\n description:\n \"Check off a validation task by recording a pass or fail. Stamps the task as validated 'now', clearing any stale flag until a covered system changes or an upstream dependency moves again. Get validationTaskId from list_validations.\",\n inputSchema: {\n validationTaskId: z\n .string()\n .describe(\"validationTaskId from list_validations\"),\n result: z\n .enum([\"pass\", \"fail\"])\n .describe(\"Outcome of running the test\"),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: true,\n idempotentHint: true,\n openWorldHint: false,\n },\n },\n\n async ({ validationTaskId, result }) => {\n const client = getConvexClient();\n const res = await client.action(api.mcp.recordValidation, {\n token: getToken(),\n validationTaskId,\n result,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(res, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerMarkSystemChanged(server: McpServer): void {\n server.registerTool(\n \"mark_system_changed\",\n {\n description:\n \"Mark a core system as changed. This is the single action that invalidates testing: every validation task that covers this system (and everything transitively depending on those tasks) immediately becomes 'stale' and needs revalidation. Get systemId from list_validations.\",\n inputSchema: {\n systemId: z.string().describe(\"systemId from list_validations\"),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: false,\n idempotentHint: false,\n openWorldHint: false,\n },\n },\n\n async ({ systemId }) => {\n const client = getConvexClient();\n const res = await client.action(api.mcp.markSystemChanged, {\n token: getToken(),\n systemId,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(res, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerCreateSystem(server: McpServer): void {\n server.registerTool(\n \"create_system\",\n {\n description:\n \"Create a core system in a project \u2014 a subsystem (e.g. Auth, Payments, Sync) whose change should invalidate the validation tasks that cover it. Returns the new systemId.\",\n inputSchema: {\n projectId: z.string().describe(\"projectId from list_projects\"),\n name: z.string().min(1).describe(\"Short system name, e.g. 'Auth'\"),\n description: z.string().optional().describe(\"Optional details\"),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: false,\n idempotentHint: false,\n openWorldHint: false,\n },\n },\n\n async (args) => {\n const client = getConvexClient();\n const res = await client.action(api.mcp.createSystem, {\n token: getToken(),\n ...args,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(res, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerCreateValidationTask(server: McpServer): void {\n server.registerTool(\n \"create_validation_task\",\n {\n description:\n \"Create a validation/test task in a project. After creating it, use add_system_to_task to declare which systems it exercises (so it goes stale when they change) and add_validation_dependency to order it after other tasks. Returns the new validationTaskId.\",\n inputSchema: {\n projectId: z.string().describe(\"projectId from list_projects\"),\n title: z.string().min(1).describe(\"What this test validates\"),\n description: z.string().optional().describe(\"Optional steps / details\"),\n kind: z\n .enum([\"auto\", \"manual\"])\n .optional()\n .describe(\n \"'auto' if runnable by a test runner, 'manual' if a human checks it. Defaults to manual.\",\n ),\n workItemId: z\n .string()\n .optional()\n .describe(\n \"Optional workItemId to link this test to a feature for traceability\",\n ),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: false,\n idempotentHint: false,\n openWorldHint: false,\n },\n },\n\n async (args) => {\n const client = getConvexClient();\n const res = await client.action(api.mcp.createValidationTask, {\n token: getToken(),\n ...args,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(res, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerAddSystemToTask(server: McpServer): void {\n server.registerTool(\n \"add_system_to_task\",\n {\n description:\n \"Declare that a validation task COVERS (exercises) a system. Once linked, the task becomes 'stale' whenever that system is marked changed. Idempotent. Both IDs come from list_validations and must be in the same project.\",\n inputSchema: {\n validationTaskId: z\n .string()\n .describe(\"validationTaskId from list_validations\"),\n systemId: z.string().describe(\"systemId from list_validations\"),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: false,\n idempotentHint: true,\n openWorldHint: false,\n },\n },\n\n async ({ validationTaskId, systemId }) => {\n const client = getConvexClient();\n const res = await client.action(api.mcp.addSystemToTask, {\n token: getToken(),\n validationTaskId,\n systemId,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(res, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerAddValidationDependency(server: McpServer): void {\n server.registerTool(\n \"add_validation_dependency\",\n {\n description:\n \"Make one validation task depend on another (validationTaskId depends on dependsOnTaskId). The dependent goes 'stale' whenever the upstream task is not passing or gets revalidated. Cycles and self-dependencies are rejected. Idempotent. Both IDs come from list_validations and must be in the same project.\",\n inputSchema: {\n validationTaskId: z\n .string()\n .describe(\"The dependent (downstream) task\"),\n dependsOnTaskId: z\n .string()\n .describe(\"The dependency (upstream) task it relies on\"),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: false,\n idempotentHint: true,\n openWorldHint: false,\n },\n },\n\n async ({ validationTaskId, dependsOnTaskId }) => {\n const client = getConvexClient();\n const res = await client.action(api.mcp.addValidationDependency, {\n token: getToken(),\n validationTaskId,\n dependsOnTaskId,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(res, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerListLabels(server: McpServer): void {\n server.registerTool(\n \"list_labels\",\n {\n description:\n \"List all labels defined in a project. Returns each label's id, name, and color. Use the labelId with add_label_to_work_item / remove_label_from_work_item.\",\n inputSchema: {\n projectId: z.string().describe(\"projectId from list_projects\"),\n },\n annotations: {\n readOnlyHint: true,\n openWorldHint: false,\n },\n },\n\n async (args) => {\n const result = await getConvexClient().action(api.mcp.listLabels, {\n token: getToken(),\n ...args,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerCreateLabel(server: McpServer): void {\n server.registerTool(\n \"create_label\",\n {\n description:\n \"Apply-or-seed a label. Returns the existing label if the name is \" +\n \"already taken (idempotent), and otherwise creates it ONLY if the name \" +\n \"is one of the curated ones. Any other new name is REFUSED \u2014 the reply \" +\n \"carries `refused: true`, the reason, and `available`, the project's \" +\n \"existing labels. Agents apply labels; they do not invent them, because \" +\n \"a near-duplicate of an existing label splits the vocabulary silently. \" +\n \"Prefer list_labels first. Colors are ignored for curated names so the \" +\n \"vocabulary looks the same in every project.\",\n inputSchema: {\n projectId: z.string().describe(\"projectId from list_projects\"),\n name: z\n .string()\n .min(1)\n .describe(\"Label name, unique within the project\"),\n color: z\n .string()\n .regex(/^#[0-9a-fA-F]{6}$/)\n .optional()\n .describe(\"Hex color like #2563eb. Defaults to a neutral slate.\"),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: false,\n idempotentHint: true,\n openWorldHint: false,\n },\n },\n\n async (args) => {\n const result = await getConvexClient().action(api.mcp.createLabel, {\n token: getToken(),\n ...args,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerAddLabelToWorkItem(server: McpServer): void {\n server.registerTool(\n \"add_label_to_work_item\",\n {\n description:\n \"Attach a label to a work item (idempotent). The label and work item must be in the same project. Get labelIds from list_labels / create_label.\",\n inputSchema: {\n workItemId: z.string().describe(\"workItemId from list_work_items\"),\n labelId: z\n .string()\n .describe(\"labelId from list_labels or create_label\"),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: false,\n idempotentHint: true,\n openWorldHint: false,\n },\n },\n\n async (args) => {\n const result = await getConvexClient().action(api.mcp.setWorkItemLabel, {\n token: getToken(),\n ...args,\n attached: true,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerRemoveLabelFromWorkItem(server: McpServer): void {\n server.registerTool(\n \"remove_label_from_work_item\",\n {\n description:\n \"Remove a label from a work item (idempotent \u2014 a no-op if it wasn't attached).\",\n inputSchema: {\n workItemId: z.string().describe(\"workItemId from list_work_items\"),\n labelId: z.string().describe(\"labelId from list_labels\"),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: true,\n idempotentHint: true,\n openWorldHint: false,\n },\n },\n\n async (args) => {\n const result = await getConvexClient().action(api.mcp.setWorkItemLabel, {\n token: getToken(),\n ...args,\n attached: false,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerListMilestones(server: McpServer): void {\n server.registerTool(\n \"list_milestones\",\n {\n description:\n \"List all milestones in a project. Returns each milestone's id, name, description, dueDate (unix ms), and status. Use the milestoneId with add_item_to_milestone / remove_item_from_milestone.\",\n inputSchema: {\n projectId: z.string().describe(\"projectId from list_projects\"),\n },\n annotations: {\n readOnlyHint: true,\n openWorldHint: false,\n },\n },\n\n async (args) => {\n const result = await getConvexClient().action(api.mcp.listMilestones, {\n token: getToken(),\n ...args,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerCreateMilestone(server: McpServer): void {\n server.registerTool(\n \"create_milestone\",\n {\n description:\n \"Create a milestone in a project. Returns the milestoneId. Good for grouping work into phases (e.g. 'Phase 1 \u2014 Web', 'Phase 2 \u2014 Native').\",\n inputSchema: {\n projectId: z.string().describe(\"projectId from list_projects\"),\n name: z.string().min(1).describe(\"Milestone name\"),\n description: z\n .string()\n .optional()\n .describe(\"Optional markdown description\"),\n dueDate: z\n .number()\n .optional()\n .describe(\"Optional due date as a unix timestamp in milliseconds\"),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: false,\n idempotentHint: false,\n openWorldHint: false,\n },\n },\n\n async (args) => {\n const result = await getConvexClient().action(api.mcp.createMilestone, {\n token: getToken(),\n ...args,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerAddItemToMilestone(server: McpServer): void {\n server.registerTool(\n \"add_item_to_milestone\",\n {\n description:\n \"Associate a work item with a milestone (idempotent). Both must be in the same project.\",\n inputSchema: {\n milestoneId: z\n .string()\n .describe(\"milestoneId from list_milestones or create_milestone\"),\n workItemId: z.string().describe(\"workItemId from list_work_items\"),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: false,\n idempotentHint: true,\n openWorldHint: false,\n },\n },\n\n async (args) => {\n const result = await getConvexClient().action(\n api.mcp.setWorkItemMilestone,\n {\n token: getToken(),\n ...args,\n attached: true,\n },\n );\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerRemoveItemFromMilestone(server: McpServer): void {\n server.registerTool(\n \"remove_item_from_milestone\",\n {\n description:\n \"Remove a work item's association with a milestone (idempotent \u2014 a no-op if it wasn't associated).\",\n inputSchema: {\n milestoneId: z.string().describe(\"milestoneId from list_milestones\"),\n workItemId: z.string().describe(\"workItemId from list_work_items\"),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: true,\n idempotentHint: true,\n openWorldHint: false,\n },\n },\n\n async (args) => {\n const result = await getConvexClient().action(\n api.mcp.setWorkItemMilestone,\n {\n token: getToken(),\n ...args,\n attached: false,\n },\n );\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n"],
|
|
5
|
-
"mappings": "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",
|
|
6
|
-
"names": ["z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z"]
|
|
3
|
+
"sources": ["../src/index.ts", "../src/server.ts", "../package.json", "../src/instructions.ts", "../src/convex.ts", "../../convex/convex/_generated/api.js", "../src/tools/list-orgs.ts", "../src/tools/list-projects.ts", "../src/tools/list-work-items.ts", "../src/tools/get-work-items.ts", "../src/tools/search-work-items.ts", "../src/tools/list-ai-review-queue.ts", "../src/tools/get-active-block.ts", "../src/tools/create-work-item.ts", "../src/tools/titleGuidance.ts", "../src/tools/statusGuidance.ts", "../../convex/convex/lib/descriptionLimits.ts", "../src/tools/descriptionGuidance.ts", "../src/tools/create-project.ts", "../src/tools/update-work-item.ts", "../src/tools/researchFormat.ts", "../src/tools/move-work-item.ts", "../src/tools/create-document.ts", "../src/tools/update-document.ts", "../src/tools/list-documents.ts", "../src/tools/create-project-link.ts", "../src/tools/list-project-links.ts", "../src/tools/list-scratch-notes.ts", "../src/tools/resolve-scratch-note.ts", "../src/tools/heartbeat-work-item.ts", "../src/tools/watch-work-item.ts", "../src/tools/add-work-item-image.ts", "../src/tools/list-work-item-images.ts", "../src/tools/add-work-item-comment.ts", "../src/tools/list-work-item-comments.ts", "../src/tools/list-validations.ts", "../src/tools/record-validation.ts", "../src/tools/mark-system-changed.ts", "../src/tools/create-system.ts", "../src/tools/create-validation-task.ts", "../src/tools/add-system-to-task.ts", "../src/tools/add-validation-dependency.ts", "../src/tools/list-labels.ts", "../src/tools/create-label.ts", "../src/tools/add-label-to-work-item.ts", "../src/tools/remove-label-from-work-item.ts", "../src/tools/list-milestones.ts", "../src/tools/create-milestone.ts", "../src/tools/add-item-to-milestone.ts", "../src/tools/remove-item-from-milestone.ts"],
|
|
4
|
+
"sourcesContent": ["#!/usr/bin/env node\n// MCP stdio transport reserves stdout for JSON-RPC frames. Any library that\n// writes to stdout (e.g. the Convex client's `[CONVEX A(uth)]` info logs)\n// corrupts the stream. Redirect console.* to stderr before anything else loads.\nfor (const m of [\"log\", \"info\", \"warn\", \"debug\"] as const) {\n console[m] = (...args: unknown[]) => console.error(...args);\n}\n\nimport { StdioServerTransport } from \"@modelcontextprotocol/sdk/server/stdio.js\";\nimport { createServer } from \"./server.js\";\n\nasync function main() {\n const server = createServer();\n const transport = new StdioServerTransport();\n await server.connect(transport);\n // Server runs until stdin closes; nothing else to do here.\n}\n\nmain().catch((err) => {\n console.error(\"nimara-mcp: fatal error\", err);\n process.exit(1);\n});\n", "import { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport pkg from \"../package.json\" with { type: \"json\" };\nimport { INSTRUCTIONS } from \"./instructions.js\";\nimport { setClientInfo } from \"./convex.js\";\nimport { registerListOrgs } from \"./tools/list-orgs.js\";\nimport { registerListProjects } from \"./tools/list-projects.js\";\nimport { registerListWorkItems } from \"./tools/list-work-items.js\";\nimport { registerGetWorkItems } from \"./tools/get-work-items.js\";\nimport { registerSearchWorkItems } from \"./tools/search-work-items.js\";\nimport { registerListAiReviewQueue } from \"./tools/list-ai-review-queue.js\";\nimport { registerGetActiveBlock } from \"./tools/get-active-block.js\";\nimport { registerCreateWorkItem } from \"./tools/create-work-item.js\";\nimport { registerCreateProject } from \"./tools/create-project.js\";\nimport { registerUpdateWorkItem } from \"./tools/update-work-item.js\";\nimport { registerMoveWorkItem } from \"./tools/move-work-item.js\";\nimport { registerCreateDocument } from \"./tools/create-document.js\";\nimport { registerUpdateDocument } from \"./tools/update-document.js\";\nimport { registerListDocuments } from \"./tools/list-documents.js\";\nimport { registerCreateProjectLink } from \"./tools/create-project-link.js\";\nimport { registerListProjectLinks } from \"./tools/list-project-links.js\";\nimport { registerListScratchNotes } from \"./tools/list-scratch-notes.js\";\nimport { registerResolveScratchNote } from \"./tools/resolve-scratch-note.js\";\nimport { registerHeartbeatWorkItem } from \"./tools/heartbeat-work-item.js\";\nimport { registerWatchWorkItem } from \"./tools/watch-work-item.js\";\nimport { registerAddWorkItemImage } from \"./tools/add-work-item-image.js\";\nimport { registerListWorkItemImages } from \"./tools/list-work-item-images.js\";\nimport { registerAddWorkItemComment } from \"./tools/add-work-item-comment.js\";\nimport { registerListWorkItemComments } from \"./tools/list-work-item-comments.js\";\nimport { registerListValidations } from \"./tools/list-validations.js\";\nimport { registerRecordValidation } from \"./tools/record-validation.js\";\nimport { registerMarkSystemChanged } from \"./tools/mark-system-changed.js\";\nimport { registerCreateSystem } from \"./tools/create-system.js\";\nimport { registerCreateValidationTask } from \"./tools/create-validation-task.js\";\nimport { registerAddSystemToTask } from \"./tools/add-system-to-task.js\";\nimport { registerAddValidationDependency } from \"./tools/add-validation-dependency.js\";\nimport { registerListLabels } from \"./tools/list-labels.js\";\nimport { registerCreateLabel } from \"./tools/create-label.js\";\nimport { registerAddLabelToWorkItem } from \"./tools/add-label-to-work-item.js\";\nimport { registerRemoveLabelFromWorkItem } from \"./tools/remove-label-from-work-item.js\";\nimport { registerListMilestones } from \"./tools/list-milestones.js\";\nimport { registerCreateMilestone } from \"./tools/create-milestone.js\";\nimport { registerAddItemToMilestone } from \"./tools/add-item-to-milestone.js\";\nimport { registerRemoveItemFromMilestone } from \"./tools/remove-item-from-milestone.js\";\n\nexport function createServer(): McpServer {\n const server = new McpServer(\n {\n name: \"nimara\",\n version: pkg.version,\n },\n // Sent at connect time, before any tool is read (NIM-T189).\n { instructions: INSTRUCTIONS },\n );\n // The client's name arrives with initialize; keep it for every later write.\n server.server.oninitialized = () => setClientInfo(server.server.getClientVersion());\n\n registerListOrgs(server);\n registerListProjects(server);\n registerListWorkItems(server);\n registerGetWorkItems(server);\n registerSearchWorkItems(server);\n registerListAiReviewQueue(server);\n registerGetActiveBlock(server);\n registerCreateProject(server);\n registerCreateWorkItem(server);\n registerUpdateWorkItem(server);\n registerMoveWorkItem(server);\n registerCreateDocument(server);\n registerUpdateDocument(server);\n registerListDocuments(server);\n registerCreateProjectLink(server);\n registerListProjectLinks(server);\n registerListScratchNotes(server);\n registerResolveScratchNote(server);\n registerHeartbeatWorkItem(server);\n registerWatchWorkItem(server);\n registerAddWorkItemImage(server);\n registerListWorkItemImages(server);\n registerAddWorkItemComment(server);\n registerListWorkItemComments(server);\n\n // Validation / test-dependency framework\n registerListValidations(server);\n registerRecordValidation(server);\n registerMarkSystemChanged(server);\n registerCreateSystem(server);\n registerCreateValidationTask(server);\n registerAddSystemToTask(server);\n registerAddValidationDependency(server);\n\n // Labels & milestones\n registerListLabels(server);\n registerCreateLabel(server);\n registerAddLabelToWorkItem(server);\n registerRemoveLabelFromWorkItem(server);\n registerListMilestones(server);\n registerCreateMilestone(server);\n registerAddItemToMilestone(server);\n registerRemoveItemFromMilestone(server);\n\n return server;\n}\n", "{\n \"name\": \"@nimara-app/mcp\",\n \"version\": \"0.6.0\",\n \"private\": false,\n \"mcpName\": \"io.github.langskip-studios/nimara\",\n \"description\": \"Nimara MCP server \u2014 AI tool integration for Claude, Codex, and others\",\n \"license\": \"MIT\",\n \"type\": \"module\",\n \"main\": \"dist/index.js\",\n \"bin\": {\n \"nimara-mcp\": \"dist/index.js\"\n },\n \"files\": [\n \"dist\",\n \"README.md\"\n ],\n \"keywords\": [\n \"mcp\",\n \"model-context-protocol\",\n \"nimara\",\n \"claude\",\n \"ai\",\n \"convex\"\n ],\n \"repository\": {\n \"type\": \"git\",\n \"url\": \"git+https://github.com/Langskip-Studios/Nimara.git\",\n \"directory\": \"packages/mcp\"\n },\n \"homepage\": \"https://github.com/Langskip-Studios/Nimara/tree/master/packages/mcp#readme\",\n \"publishConfig\": {\n \"access\": \"public\"\n },\n \"scripts\": {\n \"build\": \"node build.mjs\",\n \"dev\": \"node build.mjs\",\n \"start\": \"node dist/index.js\",\n \"typecheck\": \"tsc --noEmit\",\n \"prepublishOnly\": \"npm run typecheck && npm run build\"\n },\n \"dependencies\": {\n \"@modelcontextprotocol/sdk\": \"^1.0.0\",\n \"convex\": \"^1.18.0\",\n \"zod\": \"^3.23.0\"\n },\n \"devDependencies\": {\n \"@nimara/convex\": \"workspace:*\",\n \"@types/node\": \"^20.0.0\",\n \"esbuild\": \"^0.23.0\",\n \"typescript\": \"^5.0.0\"\n },\n \"engines\": {\n \"node\": \">=20\"\n }\n}\n", "/**\n * What every MCP client is told at connect time, before any tool is read.\n *\n * The rules that span tools \u2014 titles, statuses, the lease, mentions \u2014 each\n * live in one tool's parameter description, so a model that never loads that\n * tool never hears them. This is the map; the tool descriptions stay the\n * detailed reference. Kept short on purpose: it sits in the model's context\n * for the whole session.\n */\nexport const INSTRUCTIONS = `Nimara is the team's work tracker. Work items have a type (epic > feature > task > subtask), a status from the project's own workflow, and a displayId like NIM-T42 that people read and type.\n\nStart with list_orgs \u2192 list_projects \u2192 get_active_block (the committed work; position 0 is next) and list_ai_review_queue (what a person has asked an agent to do; read \\`answer\\` first). Use get_work_items / search_work_items for items you already know of; list_work_items only to survey.\n\nTitles are plain language a teammate understands at a glance: what is wrong or what changes for a person, not the file, function or mechanism. No em dashes, no \"Area: thing, thing\" shapes. Descriptions carry the why, acceptance criteria and file paths; a spec, design or long report goes in a document (create_document) linked from the item.\n\nA status must be one of the project's \\`statuses\\` from list_projects, spelled exactly; never invent one. Labels come from list_labels; do not invent those either.\n\nWhen you pick up an item: update_work_item { status: <in-progress status>, agentWorking: true, model: <the model you run as> }. That lights its row for 15 minutes and lets the app say whose agent, and which, is on it; any write or read of the item renews it, and on a long stretch with no Nimara calls, heartbeat_work_item every few minutes keeps it lit. Post a comment at real milestones. If you stop early, agentWorking: false. Moving to the last status clears it.\n\nMention a person in a comment as [@Name](user:<userId>) and they are notified. Append agent research to a description under the exact heading \"## Research (auto)\", never editing the human text above it. When you open a PR, put the displayId in its title.`;\n", "import { ConvexHttpClient } from \"convex/browser\";\n\nlet cachedClient: ConvexHttpClient | null = null;\n\nexport function getConvexClient(): ConvexHttpClient {\n if (cachedClient) return cachedClient;\n\n const url = process.env.NIMARA_CONVEX_URL;\n if (!url) {\n throw new Error(\n \"NIMARA_CONVEX_URL is not set. Add it to your MCP client config (e.g. Claude Desktop's mcpServers env block).\"\n );\n }\n\n cachedClient = new ConvexHttpClient(url);\n return cachedClient;\n}\n\nexport function getToken(): string {\n const token = process.env.NIMARA_TOKEN;\n if (!token) {\n throw new Error(\n \"NIMARA_TOKEN is not set. Generate a personal access token from Nimara \u2192 Settings \u2192 Personal Access Tokens, then add it to your MCP client config.\"\n );\n }\n return token;\n}\n\n/**\n * Who this server is talking to. Every MCP client names itself in the\n * `initialize` request (claude-code, codex, pi, \u2026); the server keeps it so\n * writes can say which agent made them, and the app can show \"Jordan's\n * Claude Code agent is working on this\" (NIM-F43). The model is not in the\n * protocol: an agent may pass it on the tools that take `model`.\n */\nlet clientInfo: { name: string; version?: string } | undefined;\n\nexport function setClientInfo(info: { name: string; version?: string } | undefined): void {\n clientInfo = info;\n}\n\n/** The `agent` argument for a Convex write, or undefined before initialize. */\nexport function agentArg(model?: string): { client: string; model?: string } | undefined {\n if (!clientInfo) return model ? { client: \"unknown\", model } : undefined;\n const client = clientInfo.version ? `${clientInfo.name} ${clientInfo.version}` : clientInfo.name;\n return model ? { client, model } : { client };\n}\n", "/* eslint-disable */\n/**\n * Generated `api` utility.\n *\n * THIS CODE IS AUTOMATICALLY GENERATED.\n *\n * To regenerate, run `npx convex dev`.\n * @module\n */\n\nimport { anyApi, componentsGeneric } from \"convex/server\";\n\n/**\n * A utility for referencing Convex functions in your app's API.\n *\n * Usage:\n * ```js\n * const myFunctionReference = api.myModule.myFunction;\n * ```\n */\nexport const api = anyApi;\nexport const internal = anyApi;\nexport const components = componentsGeneric();\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerListOrgs(server: McpServer): void {\n server.registerTool(\n \"list_orgs\",\n {\n description:\n \"List all organizations (and the personal workspace) the authenticated user belongs to. Use this first to discover org IDs needed by other tools.\",\n inputSchema: {},\n annotations: {\n readOnlyHint: true,\n openWorldHint: false,\n },\n },\n\n async () => {\n const client = getConvexClient();\n const orgs = await client.action(api.mcp.listOrgs, { token: getToken() });\n return {\n content: [{ type: \"text\", text: JSON.stringify(orgs, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerListProjects(server: McpServer): void {\n server.registerTool(\n \"list_projects\",\n {\n description:\n \"List projects in a given organization. Call list_orgs first to find \" +\n \"the orgId. Each project includes `statuses` \u2014 its workflow in board \" +\n \"order. Read that before setting a status on any item: those names are \" +\n \"the only accepted values, and anything else is rejected.\",\n inputSchema: { orgId: z.string().describe(\"orgId from list_orgs\") },\n annotations: {\n readOnlyHint: true,\n openWorldHint: false,\n },\n },\n\n async ({ orgId }) => {\n const client = getConvexClient();\n const projects = await client.action(api.mcp.listProjects, {\n token: getToken(),\n orgId,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(projects, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerListWorkItems(server: McpServer): void {\n server.registerTool(\n \"list_work_items\",\n {\n // The description is the only place a model learns paging exists, so it\n // states the shape of the response and what to do when hasMore is true.\n description:\n \"List non-archived work items in a project, oldest-created first. Returns \" +\n \"{ items, nextCursor, hasMore }. Long descriptions are previewed \u2014 an \" +\n \"item with descriptionTruncated: true has more text, readable via \" +\n \"fullDescriptions. When hasMore is true, call again with cursor set to \" +\n \"nextCursor to get the next page \u2014 the FIRST page is the OLDEST items, so \" +\n \"recently created ones are on the LAST page and you have not seen the \" +\n \"project until hasMore is false. Narrow with status/type/parentId/\" +\n \"needsReview rather than paging and filtering yourself. If you already \" +\n \"know which items you want, use get_work_items instead \u2014 it takes \" +\n \"displayIds like NIM-T75 and costs a fraction of a list. \" +\n \"Call list_projects first for the projectId.\",\n inputSchema: {\n projectId: z.string().describe(\"projectId from list_projects\"),\n status: z\n .union([z.string(), z.array(z.string())])\n .optional()\n .describe(\n \"Only items in these statuses. Names come from the project's \" +\n \"statusOrder (e.g. 'In Progress'). One name or a list.\",\n ),\n type: z\n .union([\n z.enum([\"epic\", \"feature\", \"task\", \"subtask\"]),\n z.array(z.enum([\"epic\", \"feature\", \"task\", \"subtask\"])),\n ])\n .optional()\n .describe(\"Only items of these types. One type or a list.\"),\n parentId: z\n .string()\n .optional()\n .describe(\n \"Only direct children of this workItemId. One level, not the whole subtree.\",\n ),\n needsReview: z\n .boolean()\n .optional()\n .describe(\n \"true returns only items flagged needsReview; false only unflagged ones. \" +\n \"Omit for both.\",\n ),\n limit: z\n .number()\n .int()\n .min(1)\n .max(200)\n .optional()\n .describe(\"Items per page (default 50, max 200).\"),\n cursor: z\n .number()\n .optional()\n .describe(\n \"nextCursor from the previous page. Omit for the first page.\",\n ),\n fullDescriptions: z\n .boolean()\n .optional()\n .describe(\n \"Return descriptions in full instead of previewed. Costly on large \" +\n \"projects \u2014 prefer paging, or read one item at a time.\",\n ),\n },\n annotations: {\n readOnlyHint: true,\n openWorldHint: false,\n },\n },\n async ({\n projectId,\n limit,\n cursor,\n fullDescriptions,\n status,\n type,\n parentId,\n needsReview,\n }) => {\n const page = await getConvexClient().action(api.mcp.listWorkItems, {\n token: getToken(),\n projectId,\n limit,\n cursor,\n fullDescriptions,\n // Accepting a bare string as well as a list is what keeps a model from\n // failing validation on the overwhelmingly common single-value case.\n status:\n status === undefined\n ? undefined\n : Array.isArray(status)\n ? status\n : [status],\n type:\n type === undefined ? undefined : Array.isArray(type) ? type : [type],\n parentId,\n needsReview,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(page, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerGetWorkItems(server: McpServer): void {\n server.registerTool(\n \"get_work_items\",\n {\n // Written to be chosen *over* list_work_items whenever the caller already\n // knows which items it wants \u2014 that is the whole point of the tool, and\n // the description is the only place a model learns it.\n description:\n \"Read specific work items by id \u2014 the cheap way to re-read items you \" +\n \"already know about. Prefer this over list_work_items whenever you have \" +\n \"a displayId (e.g. NIM-T75) or a workItemId: listing a project returns \" +\n \"every item and its description, which is orders of magnitude more data. \" +\n \"Accepts up to 50 ids per call and always returns descriptions in full. \" +\n \"Returns { items, notFound }; ids in notFound either do not exist or are \" +\n \"not readable by this token. displayIds require projectId (they are \" +\n \"unique per project, not globally); workItemIds do not.\",\n inputSchema: {\n displayIds: z\n .array(z.string())\n .optional()\n .describe(\n \"Human-facing ids like ['NIM-T75', 'NIM-F27']. Case-insensitive. \" +\n \"Requires projectId.\",\n ),\n workItemIds: z\n .array(z.string())\n .optional()\n .describe(\n \"Raw workItemIds, as returned by create_work_item or list_work_items.\",\n ),\n projectId: z\n .string()\n .optional()\n .describe(\n \"projectId from list_projects. Required only when passing displayIds.\",\n ),\n },\n annotations: {\n readOnlyHint: true,\n openWorldHint: false,\n },\n },\n async ({ displayIds, workItemIds, projectId }) => {\n const result = await getConvexClient().action(api.mcp.getWorkItems, {\n token: getToken(),\n displayIds,\n workItemIds,\n projectId,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerSearchWorkItems(server: McpServer): void {\n server.registerTool(\n \"search_work_items\",\n {\n // The point of this description is to stop a model reaching for\n // list_work_items when it is looking for something by name. Listing a\n // project to find one item is the expensive mistake this tool exists to\n // prevent.\n description:\n \"Find work items in a project by title. Use this to answer 'does an \" +\n \"item for X already exist?' \u2014 listing the whole project and filtering \" +\n \"yourself is far more expensive and, because the first page is the \" +\n \"OLDEST items, easy to get wrong. Matches TITLES only, not \" +\n \"descriptions. Returns { items, query } with descriptions previewed; \" +\n \"once you know which item you want, get_work_items returns it in full. \" +\n \"Capped at 25 results \u2014 narrow the query rather than paging. \" +\n \"Call list_projects first for the projectId.\",\n inputSchema: {\n projectId: z.string().describe(\"projectId from list_projects\"),\n q: z\n .string()\n .min(1)\n .describe(\n \"Words to match against item titles, e.g. 'mobile modal' or \" +\n \"'shortcut'. Matching is full-text, so word order does not matter.\",\n ),\n limit: z\n .number()\n .int()\n .min(1)\n .max(25)\n .optional()\n .describe(\"Maximum results (default and maximum 25).\"),\n },\n annotations: { readOnlyHint: true },\n },\n async ({ projectId, q, limit }) => {\n const result = await getConvexClient().action(api.mcp.searchWorkItems, {\n token: getToken(),\n projectId,\n q,\n limit,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerListAiReviewQueue(server: McpServer): void {\n server.registerTool(\n \"list_ai_review_queue\",\n {\n description:\n \"List work items in a project that a human has flagged for AI review \" +\n \"(aiReviewRequested). Descriptions come back in full here, since \" +\n \"enrichment needs the whole text. Each item also carries recentComments \" +\n \"(the last few, oldest first) and, when a person has written one, \" +\n \"`answer`: the newest human comment. READ `answer` FIRST. When you \" +\n \"flagged an item with a question and it is back in this queue, `answer` \" +\n \"is the person's reply to that question; act on it rather than asking \" +\n \"again. Returns { items, nextCursor, hasMore } \u2014 when hasMore is true, \" +\n \"call again with cursor set to nextCursor. Process each item, then clear \" +\n \"its flag by calling update_work_item with aiReviewRequested: false. \" +\n \"Call list_projects first to find the projectId.\",\n inputSchema: {\n projectId: z.string().describe(\"projectId from list_projects\"),\n limit: z\n .number()\n .int()\n .min(1)\n .max(200)\n .optional()\n .describe(\"Items per page (default 50, max 200).\"),\n cursor: z\n .number()\n .optional()\n .describe(\n \"nextCursor from the previous page. Omit for the first page.\",\n ),\n },\n annotations: {\n readOnlyHint: true,\n openWorldHint: false,\n },\n },\n async ({ projectId, limit, cursor }) => {\n const page = await getConvexClient().action(api.mcp.listAiReviewQueue, {\n token: getToken(),\n projectId,\n limit,\n cursor,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(page, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerGetActiveBlock(server: McpServer): void {\n server.registerTool(\n \"get_active_block\",\n {\n description:\n \"The project's ACTIVE BLOCK: the small, ordered set of work a person has \" +\n \"committed to right now. Call this BEFORE list_work_items when deciding what \" +\n \"to work on \u2014 position 0 is the next thing to do, and the wider backlog is \" +\n \"not on the table until the block is empty. Each item carries a lane: \" +\n \"'person' means a human owes it (flagged for review, or parked in a Review \" +\n \"status) and you should not touch it; 'agent' means a human asked an agent \" +\n \"to act on it, so it is yours first, and it carries recentComments and \" +\n \"`answer` (the newest human comment: read it before anything else); \" +\n \"'open' is uncommitted-to-anyone work in \" +\n \"priority order; 'done' is finished. Returns null when the project has no \" +\n \"active block, in which case fall back to list_work_items. Descriptions are \" +\n \"previewed; use get_work_items for the full text of an item you pick up. \" +\n \"Call list_projects first for the projectId.\",\n inputSchema: {\n projectId: z.string().describe(\"projectId from list_projects\"),\n },\n annotations: {\n readOnlyHint: true,\n openWorldHint: false,\n },\n },\n async ({ projectId }) => {\n const block = await getConvexClient().action(api.mcp.getActiveBlock, {\n token: getToken(),\n projectId,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(block, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\nimport { TITLE_GUIDANCE } from \"./titleGuidance.js\";\nimport { STATUS_GUIDANCE } from \"./statusGuidance.js\";\nimport { DESCRIPTION_GUIDANCE, DESCRIPTION_MAX } from \"./descriptionGuidance.js\";\n\nexport function registerCreateWorkItem(server: McpServer): void {\n server.registerTool(\n \"create_work_item\",\n {\n description:\n \"Create a new work item in a project. Hierarchy rules: epics live at the root; features go under epics; tasks go under epics or features (or root); subtasks must go under a task. Returns the new workItemId and its display ID (e.g. NIM-42).\",\n inputSchema: {\n projectId: z.string().describe(\"projectId from list_projects\"),\n type: z\n .enum([\"epic\", \"feature\", \"task\", \"subtask\"])\n .describe(\"Item type \u2014 drives hierarchy validation\"),\n title: z.string().min(1).describe(TITLE_GUIDANCE),\n description: z.string().max(DESCRIPTION_MAX).optional().describe(DESCRIPTION_GUIDANCE),\n parentId: z\n .string()\n .optional()\n .describe(\n \"workItemId of the parent. Required for subtask, optional otherwise.\",\n ),\n status: z\n .string()\n .optional()\n .describe(\n STATUS_GUIDANCE,\n ),\n priority: z\n .enum([\"p0\", \"p1\", \"p2\", \"p3\"])\n .optional()\n .describe(\"p0 highest, p3 lowest. Defaults to p2.\"),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: false,\n idempotentHint: false,\n openWorldHint: false,\n },\n },\n\n async (args) => {\n const client = getConvexClient();\n const result = await client.action(api.mcp.createWorkItem, {\n token: getToken(),\n ...args,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "/**\n * What a work-item title should read like, stated once.\n *\n * This exists because \"Short, descriptive title\" \u2014 the previous guidance on\n * `create_work_item` \u2014 is satisfied by \"Fix hasChildren computation in\n * list.tsx\". That is short and it does describe something, and it is unreadable\n * to anyone who has not just been in that file. Titles are what a board shows;\n * a board full of symbol names cannot be scanned.\n *\n * The em-dash and verbosity rules come from NIM-T117, which Jordan filed\n * before this and which asked for exactly that: \"Remove the em dash and\n * other verbose title that make it hard to read.\"\n *\n * Shared by `create_work_item` and `update_work_item` so the rule cannot hold\n * on one path and not the other \u2014 retitling is the same act as titling, and\n * `update_work_item` previously carried no guidance at all.\n */\nexport const TITLE_GUIDANCE =\n \"A title a teammate can understand at a glance, without opening the item or \" +\n \"knowing the codebase. Say what is wrong or what changes FOR A PERSON, in \" +\n \"plain words \u2014 not the mechanism, the file, or the symbol. \" +\n 'Good: \"Sorted list shows an expand arrow that does nothing\". ' +\n 'Bad: \"Fix hasChildren computation in list.tsx\". ' +\n 'Good: \"Long titles wrap to three lines and are hard to read\". ' +\n 'Bad: \"Adjust COLUMNS.title min-width constant\". ' +\n \"Prefer ordinary words over internal abbreviations, and only name a file, \" +\n \"function or identifier when it genuinely is the clearest way to say it \" +\n \"(a tool or endpoint the user calls by name, for instance). No ticket \" +\n \"prefixes or status markers \u2014 the board renders those already. Root cause, \" +\n \"file paths, and reproduction steps belong in the description, which has \" +\n \"room for them. \" +\n \"Keep it to one plain clause. Do NOT use an em dash, and do not use the \" +\n '\"Area: thing, other thing\" shape \u2014 both are ways of stapling a second ' +\n \"title on and they are what makes these hard to read. \" +\n 'Bad: \"Gantt: tighten row density, match app typography, stop the chart ' +\n 'falling short of its container\". ' +\n 'Good: \"Gantt chart looks nothing like the rest of the app\". ' +\n \"If the title needs a comma-spliced list to be accurate, that is a sign the \" +\n \"item is really several items, not a sign it needs a longer title.\";\n", "/**\n * How to choose a status, stated once.\n *\n * The rule the tools already stated \u2014 \"a status name from the project's\n * statusOrder\" \u2014 referred to data no tool returned. An agent could not read a\n * project's workflow, so it guessed a plausible-sounding name, and the guess\n * was frequently \"In Review\" on boards whose workflow only ever had \"Review\".\n * `list_projects` now returns `statuses`, which is what makes this instruction\n * followable rather than aspirational.\n *\n * The second half matters as much as the first. A status is POSITIONAL \u2014 it is\n * the board column \u2014 so inventing one is not a labelling choice, it reshapes\n * the board and every status chart that aggregates across projects. Anything\n * that describes an item without saying where it sits in the flow is a label:\n * `list_labels`, `create_label` and `add_label_to_work_item` exist for exactly\n * that, and cost nothing to add. This is NIM-T49's decision, held to.\n *\n * Shared by `create_work_item` and `update_work_item`. `update_work_item.status`\n * previously carried no guidance at all, which is the path most likely to move\n * an item to an invented status.\n */\nexport const STATUS_GUIDANCE =\n \"Must be one of the names in the project's `statuses`, returned by \" +\n \"list_projects. Read it rather than guessing \u2014 a status is the board \" +\n \"column, so a name the workflow does not have is rejected, and before that \" +\n \"check existed such items rendered in the first column while claiming \" +\n \"otherwise. Match the existing name exactly, including its wording: if the \" +\n \"workflow says \\\"Review\\\", do not write \\\"In Review\\\". \" +\n \"Do NOT invent a status to capture something about an item. Statuses are \" +\n \"shared across the whole project and aggregated on the dashboard, so each \" +\n \"new one is a permanent extra band there. Anything that describes an item \" +\n \"rather than locating it in the flow belongs in a LABEL \u2014 see create_label \" +\n \"and add_label_to_work_item. Defaults to the first status when omitted.\";\n", "/**\n * The two sizes a work item description is measured against. Kept free of\n * Convex imports so the web app and the MCP package can share the numbers.\n *\n * PREVIEW is what the row carries so lists never join the body\n * (lib/workItemBody.ts). MAX is a sanity cap, not a product decision: no\n * task written by hand comes near it, but an agent pasting a log or a whole\n * research report into a description would \u2014 and that belongs in a document.\n * Descriptions averaged 14 KB when the cap was chosen; 32 KB is roughly\n * 5,000 words, eight pages.\n */\nexport const DESCRIPTION_PREVIEW_CHARS = 500;\nexport const DESCRIPTION_MAX_CHARS = 32_000;\n\n/** Where a description's length stands, for an error or a counter. */\nexport const DESCRIPTION_TOO_LONG =\n `A description can be at most ${DESCRIPTION_MAX_CHARS.toLocaleString(\"en-US\")} characters. ` +\n \"Put specs, research and long reports in a document and link it to the item.\";\n", "import { DESCRIPTION_MAX_CHARS } from \"@nimara/convex/convex/lib/descriptionLimits.js\";\n\n/**\n * What a description is for, and how big it may be, stated once and shared\n * by `create_work_item` and `update_work_item` the way TITLE_GUIDANCE is.\n *\n * The cap is enforced server-side in writeDescription; the zod max here\n * only means an agent hears about it before the round-trip. The guidance is\n * the real lever: descriptions averaged 14 KB because agents used them as\n * the place to put everything, and the row split (lib/workItemBody.ts) made\n * that cheap but not right \u2014 a document is what other items can link to.\n */\nexport const DESCRIPTION_MAX = DESCRIPTION_MAX_CHARS;\n\nexport const DESCRIPTION_GUIDANCE =\n \"Markdown. The what and the why: the problem, acceptance criteria, \" +\n \"reproduction steps, file paths, root cause. Keep it to what someone \" +\n \"picking the item up needs. A spec, a design, research, or a long report \" +\n \"goes in a document (create_document) linked from here, not inline. \" +\n `At most ${DESCRIPTION_MAX_CHARS.toLocaleString(\"en-US\")} characters.`;\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerCreateProject(server: McpServer): void {\n server.registerTool(\n \"create_project\",\n {\n description:\n \"Create a new project in an org. Prefix must be unique within the org and is uppercased (e.g. 'NIM' yields work items NIM-1, NIM-2\u2026). Caller becomes the project admin. Returns the new projectId.\",\n inputSchema: {\n orgId: z.string().describe(\"orgId from list_orgs\"),\n name: z.string().min(1).describe(\"Project name\"),\n prefix: z\n .string()\n .min(1)\n .max(8)\n .describe(\n \"Short uppercase prefix for work item IDs (e.g. 'NIM'). Unique per org.\",\n ),\n description: z\n .string()\n .optional()\n .describe(\"Optional markdown description\"),\n isPrivate: z\n .boolean()\n .optional()\n .describe(\n \"If true, only explicitly added members see it. Defaults to false.\",\n ),\n workflowTemplate: z\n .enum([\"default\", \"simple\", \"kanban\", \"bug\"])\n .optional()\n .describe(\n \"Status workflow. Defaults to 'default' (Backlog/Todo/In Progress/Review/Done).\",\n ),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: false,\n idempotentHint: false,\n openWorldHint: false,\n },\n },\n\n async (args) => {\n const client = getConvexClient();\n const result = await client.action(api.mcp.createProject, {\n token: getToken(),\n ...args,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { agentArg, getConvexClient, getToken } from \"../convex.js\";\nimport { TITLE_GUIDANCE } from \"./titleGuidance.js\";\nimport { STATUS_GUIDANCE } from \"./statusGuidance.js\";\nimport { DESCRIPTION_GUIDANCE, DESCRIPTION_MAX } from \"./descriptionGuidance.js\";\nimport { RESEARCH_FORMAT } from \"./researchFormat.js\";\n\nexport function registerUpdateWorkItem(server: McpServer): void {\n server.registerTool(\n \"update_work_item\",\n {\n description:\n \"Update an existing work item: title, description, status, priority, parent, or review flags. Any update also stamps the item as AI-touched.\",\n inputSchema: {\n workItemId: z.string().describe(\"workItemId from list_work_items\"),\n title: z.string().min(1).optional().describe(TITLE_GUIDANCE),\n description: z\n .string()\n .max(DESCRIPTION_MAX)\n .optional()\n .describe(\n \"Full markdown body, replacing what is there. \" +\n DESCRIPTION_GUIDANCE +\n \" \" +\n RESEARCH_FORMAT,\n ),\n status: z.string().optional().describe(STATUS_GUIDANCE),\n priority: z.enum([\"p0\", \"p1\", \"p2\", \"p3\"]).optional(),\n parentId: z\n .string()\n .nullable()\n .optional()\n .describe(\"New parent workItemId, null to move to root.\"),\n needsReview: z\n .boolean()\n .optional()\n .describe(\n \"Flag the item for manual human review \u2014 set true when your enrichment was thin or uncertain.\",\n ),\n reviewReason: z\n .string()\n .optional()\n .describe(\n \"Short reason the item needs manual review (shown to the human).\",\n ),\n aiReviewRequested: z\n .boolean()\n .optional()\n .describe(\n \"The human\u2192AI review flag. Set false to clear it after you have reviewed/enriched an item from list_ai_review_queue.\",\n ),\n agentWorking: z\n .boolean()\n .optional()\n .describe(\n \"Set true when you start working on this item: the app lights its row so the person can see it is in flight. It is a 15-minute lease renewed by any later MCP write on the item (updates, comments), by reading it (get_work_items, list_work_item_comments), or by heartbeat_work_item \u2014 call that every few minutes on a long task with no other Nimara calls, or the row goes quiet while you are still at it. Set false when you stop without finishing; moving the item to the last status clears it for you.\",\n ),\n model: z\n .string()\n .optional()\n .describe(\"With agentWorking: the model you are running as, e.g. claude-opus-5, so the app can say which agent is on this. Your harness is reported automatically.\"),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: true,\n idempotentHint: true,\n openWorldHint: false,\n },\n },\n\n async ({ model, ...args }) => {\n const result = await getConvexClient().action(api.mcp.updateWorkItem, {\n token: getToken(),\n ...args,\n agent: agentArg(model),\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "/**\n * The shape of the automated research block an enrichment agent appends to a\n * work item's description.\n *\n * Two reasons this is stated here rather than left to each agent's own taste.\n *\n * The web app parses this block out of the description and renders it in its\n * own tab on the item (NIM-T125). The anchor heading is therefore a contract,\n * not a style choice: change its wording and the tab stops appearing, with the\n * text still sitting in the description and nothing failing loudly.\n *\n * And the existing blocks are decorated with emoji section markers \u2014 \uD83D\uDD0E, \uD83D\uDD17,\n * \uD83E\uDDED, \uD83C\uDF9A. They read as noise in a panel that is already labelled \"Research\",\n * they carry no information the heading does not, and they are the first thing\n * Jordan asked to remove. The parser accepts the old emoji heading so the 20\n * items already enriched keep working; nothing new should write one.\n *\n * Deliberately NOT permitted: raw HTML. The app renders this with\n * `react-markdown` and no `rehype-raw`, so HTML is stripped rather than shown \u2014\n * and turning that on would render agent-authored markup whose inputs include\n * untrusted work-item text. Mermaid fences cover the diagram case without\n * opening that door.\n */\nexport const RESEARCH_FORMAT = `When appending automated research to a description, use EXACTLY this format, \\\nafter the human-written text:\n\n---\n## Research (auto)\n\n### Findings\n- One bullet per verified fact, each naming what you checked.\n\n### Dependencies\n- Items this blocks or is blocked by, by displayId. Omit the section if none.\n\n### Duplicates\n- Existing items covering the same work, by displayId. Omit if none.\n\n### Suggested priority\nOne line. Say \"No change\" when it is already right.\n\nRules:\n- The \"## Research (auto)\" heading is EXACT and is what the app keys on to show \\\nthis in its own tab. Do not reword it, renumber its level, or translate it.\n- NO EMOJI anywhere in the block, in headings or in bullets. Older items carry \\\nemoji headings; do not copy them.\n- Omit a section rather than writing \"None found\" in it. An empty section is \\\nnoise the reader still has to read.\n- Never edit or delete the human-written text above the rule. Append only.\n- Markdown only. GFM tables are supported and are the right choice for \\\ncomparisons. Raw HTML is NOT rendered by the app and must not be used.\n- For a workflow, sequence or state machine, use a \\\\\\`\\\\\\`\\\\\\`mermaid fenced block. \\\nThat is the supported way to draw one.\n- Say what you verified and how. \"Confirmed X still returns Y (file:line)\" is \\\nworth more than a conclusion with no trail.`;\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerMoveWorkItem(server: McpServer): void {\n server.registerTool(\n \"move_work_item\",\n {\n // Everything a model needs to predict the damage has to be stated here \u2014\n // the description is the only channel it has. The consequences that are\n // NOT obvious from the name are the ones worth the tokens: the display ID\n // changes, and labels/milestones do not survive.\n description:\n \"Move a work item to a different project, taking its whole subtree \" +\n \"with it \u2014 children and grandchildren move too, and the hierarchy is \" +\n \"preserved. Both projects must be in the same organization, and you \" +\n \"need write access to both. \" +\n \"Not reversible by calling this again: the item is renumbered in the \" +\n \"destination, so NIM-T44 might become SKA-T18 and the old ID stops \" +\n \"resolving. Labels and milestone assignments are dropped, because both \" +\n \"belong to the project being left; a status the destination doesn't \" +\n \"define falls back to its first status. The response reports every \" +\n \"old \u2192 new ID plus everything that was dropped or remapped. \" +\n \"Comments, images, attached documents, PR links and history all follow \" +\n \"the item. Call list_projects first for the target projectId.\",\n inputSchema: {\n workItemId: z\n .string()\n .describe(\"workItemId from list_work_items \u2014 the item to move.\"),\n targetProjectId: z\n .string()\n .describe(\n \"projectId from list_projects \u2014 the destination. Must be in the \" +\n \"same org as the item's current project.\",\n ),\n },\n annotations: {\n readOnlyHint: false,\n // Renumbering display IDs and deleting label/milestone links are\n // overwrites, not additions \u2014 this belongs with the tools a client\n // should prompt on rather than auto-approve.\n destructiveHint: true,\n // Calling it twice does not land in the same place: the second call\n // either errors as already-there or moves the item on again.\n idempotentHint: false,\n openWorldHint: false,\n },\n },\n async ({ workItemId, targetProjectId }) => {\n const result = await getConvexClient().action(\n api.mcp.moveWorkItemToProject,\n { token: getToken(), workItemId, targetProjectId },\n );\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerCreateDocument(server: McpServer): void {\n server.registerTool(\n \"create_document\",\n {\n description:\n \"Create a markdown project document. Use type 'prd' for project docs or 'fd' for feature/work-item documents.\",\n inputSchema: {\n projectId: z.string().describe(\"projectId from list_projects\"),\n title: z.string().min(1),\n type: z\n .enum([\"prd\", \"fd\"])\n .describe(\n \"Document type. 'fd' is stored as the app's feature document type.\",\n ),\n workItemId: z\n .string()\n .optional()\n .describe(\"Required for fd documents; omitted for prd.\"),\n content: z\n .string()\n .optional()\n .describe(\"Optional initial markdown content.\"),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: false,\n idempotentHint: false,\n openWorldHint: false,\n },\n },\n\n async (args) => {\n const result = await getConvexClient().action(api.mcp.createDocument, {\n token: getToken(),\n ...args,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerUpdateDocument(server: McpServer): void {\n server.registerTool(\n \"update_document\",\n {\n description:\n \"Update an existing document's markdown content and/or title. Use this to fill in or revise a document created earlier (e.g. backfill content into an empty doc). documentId comes from list_documents. Provided content fully replaces the existing content.\",\n inputSchema: {\n documentId: z.string().describe(\"documentId from list_documents\"),\n content: z\n .string()\n .optional()\n .describe(\n \"New markdown content. Replaces the document's existing content.\",\n ),\n title: z.string().min(1).optional().describe(\"New title (optional).\"),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: true,\n idempotentHint: true,\n openWorldHint: false,\n },\n },\n\n async (args) => {\n const result = await getConvexClient().action(api.mcp.updateDocument, {\n token: getToken(),\n ...args,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerListDocuments(server: McpServer): void {\n server.registerTool(\n \"list_documents\",\n {\n description:\n \"List PRD/FD markdown documents for a project, optionally filtered to one work item.\",\n inputSchema: {\n projectId: z.string().describe(\"projectId from list_projects\"),\n workItemId: z\n .string()\n .optional()\n .describe(\"Optional workItemId to list linked FD documents.\"),\n },\n annotations: {\n readOnlyHint: true,\n openWorldHint: false,\n },\n },\n\n async (args) => {\n const result = await getConvexClient().action(api.mcp.listDocuments, {\n token: getToken(),\n ...args,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nconst projectLinkCategory = z.enum([\n \"api\",\n \"dashboard\",\n \"documentation\",\n \"repository\",\n \"service\",\n \"other\",\n]);\n\nexport function registerCreateProjectLink(server: McpServer): void {\n server.registerTool(\n \"create_project_link\",\n {\n description:\n \"Save a link on a project for resources like APIs, dashboards, documentation, repositories, or services.\",\n inputSchema: {\n projectId: z.string().describe(\"projectId from list_projects\"),\n title: z.string().min(1).max(120),\n url: z.string().url().describe(\"http(s) URL to save\"),\n description: z.string().max(500).optional(),\n category: projectLinkCategory.optional().describe(\"Defaults to other.\"),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: false,\n idempotentHint: false,\n openWorldHint: false,\n },\n },\n\n async (args) => {\n const result = await getConvexClient().action(api.mcp.createProjectLink, {\n token: getToken(),\n ...args,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerListProjectLinks(server: McpServer): void {\n server.registerTool(\n \"list_project_links\",\n {\n description:\n \"List saved links for a project, such as APIs, dashboards, docs, repositories, and services.\",\n inputSchema: {\n projectId: z.string().describe(\"projectId from list_projects\"),\n },\n annotations: {\n readOnlyHint: true,\n openWorldHint: false,\n },\n },\n\n async ({ projectId }) => {\n const result = await getConvexClient().action(api.mcp.listProjectLinks, {\n token: getToken(),\n projectId,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerListScratchNotes(server: McpServer): void {\n server.registerTool(\n \"list_scratch_notes\",\n {\n description:\n \"The token owner's OPEN scratch notes: thoughts and ideas they captured \" +\n \"in the app with the `s` shortcut before deciding what to do with them. \" +\n \"Returns the notes that belong with this project (tagged with it, or \" +\n \"tagged with nothing), oldest first, each with noteId, body, projectId \" +\n \"and createdAt. These are raw: a note may be one line or a paragraph, \" +\n \"may describe one task or three, and may not be a task at all. Read \" +\n \"each, decide what it should become (usually one or more work items \" +\n \"via create_work_item, sometimes a comment on an existing item, \" +\n \"sometimes nothing), do that, then call resolve_scratch_note with the \" +\n \"noteId and the workItemId it became so the person sees where their \" +\n \"note went. Ask in a comment rather than guess when a note is too \" +\n \"thin to act on. Call list_projects first for the projectId.\",\n inputSchema: {\n projectId: z.string().describe(\"projectId from list_projects\"),\n },\n annotations: {\n readOnlyHint: true,\n openWorldHint: false,\n },\n },\n async ({ projectId }) => {\n const notes = await getConvexClient().action(api.mcp.listScratchNotes, {\n token: getToken(),\n projectId,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(notes, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerResolveScratchNote(server: McpServer): void {\n server.registerTool(\n \"resolve_scratch_note\",\n {\n description:\n \"Mark a scratch note as used, recording the work item it became. Call \" +\n \"this after acting on a note from list_scratch_notes: pass the noteId \" +\n \"and the workItemId you created or updated from it (omit workItemId \" +\n \"only when the note needed no item). The note leaves the person's open \" +\n \"list and shows where it went. Only the token owner's own notes.\",\n inputSchema: {\n noteId: z.string().describe(\"noteId from list_scratch_notes\"),\n workItemId: z\n .string()\n .optional()\n .describe(\"The workItemId the note became, from create_work_item or list_work_items.\"),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: false,\n idempotentHint: true,\n openWorldHint: false,\n },\n },\n async ({ noteId, workItemId }) => {\n const result = await getConvexClient().action(api.mcp.resolveScratchNote, {\n token: getToken(),\n noteId,\n workItemId,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { agentArg, getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerHeartbeatWorkItem(server: McpServer): void {\n server.registerTool(\n \"heartbeat_work_item\",\n {\n description:\n \"Say you are still working on an item. Renews (or starts) its 15-minute \" +\n \"\\\"agent working\\\" lease and does nothing else: no comment, no activity \" +\n \"event, no change to the item. The app lights the row while the lease is \" +\n \"live, so on a long task call this every few minutes or every handful of \" +\n \"tool calls \u2014 otherwise the row goes quiet while you are still at it. \" +\n \"Reads of the item (get_work_items, list_work_item_comments) also renew a \" +\n \"live lease, and any update or comment does; this is for the stretches \" +\n \"where you do none of those. Cheap and idempotent.\",\n inputSchema: {\n workItemId: z.string().describe(\"workItemId of the item you are working on\"),\n model: z\n .string()\n .optional()\n .describe(\"The model you are running as, e.g. claude-opus-5 or gpt-5, so the app can say which agent is on this. Your harness is reported automatically.\"),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: false,\n idempotentHint: true,\n openWorldHint: false,\n },\n },\n async ({ workItemId, model }) => {\n const result = await getConvexClient().action(api.mcp.heartbeatWorkItem, {\n token: getToken(),\n workItemId,\n agent: agentArg(model),\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerWatchWorkItem(server: McpServer): void {\n server.registerTool(\n \"watch_work_item\",\n {\n description:\n \"Put the token owner on (or take them off) an item's watch list. A watcher \" +\n \"is notified when the item changes status, gets a comment, gets a reviewer, \" +\n \"is archived or moved \u2014 not on title or description edits. The item's \" +\n \"assignee and reviewer already hear about it. Use this when you start work \" +\n \"the person will want to follow, or when they ask to keep an eye on something.\",\n inputSchema: {\n workItemId: z.string().describe(\"workItemId of the item\"),\n watching: z.boolean().default(true).describe(\"true to watch, false to stop\"),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: false,\n idempotentHint: true,\n openWorldHint: false,\n },\n },\n async ({ workItemId, watching }) => {\n const result = await getConvexClient().action(api.mcp.watchWorkItem, {\n token: getToken(),\n workItemId,\n watching,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerAddWorkItemImage(server: McpServer): void {\n server.registerTool(\n \"add_work_item_image\",\n {\n description:\n \"Attach an externally hosted image URL to a work item. Use this when an MCP client has a screenshot, mockup, or generated image URL to preserve with the task.\",\n inputSchema: {\n workItemId: z.string().describe(\"workItemId from list_work_items\"),\n imageUrl: z\n .string()\n .url()\n .describe(\"Public or otherwise fetchable http(s) image URL\"),\n filename: z.string().optional().describe(\"Optional display filename\"),\n altText: z\n .string()\n .optional()\n .describe(\"Optional description/caption for the image\"),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: false,\n idempotentHint: false,\n openWorldHint: false,\n },\n },\n\n async (args) => {\n const result = await getConvexClient().action(api.mcp.addWorkItemImage, {\n token: getToken(),\n ...args,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerListWorkItemImages(server: McpServer): void {\n server.registerTool(\n \"list_work_item_images\",\n {\n description:\n \"List image attachments for a work item, including uploaded images and externally attached MCP images. Call list_work_items first to find the workItemId.\",\n inputSchema: {\n workItemId: z.string().describe(\"workItemId from list_work_items\"),\n },\n annotations: {\n readOnlyHint: true,\n openWorldHint: false,\n },\n },\n\n async ({ workItemId }) => {\n const result = await getConvexClient().action(\n api.mcp.listWorkItemImages,\n {\n token: getToken(),\n workItemId,\n },\n );\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { agentArg, getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerAddWorkItemComment(server: McpServer): void {\n server.registerTool(\n \"add_work_item_comment\",\n {\n description:\n \"Add a timestamped comment to a work item. Use this to record notes, updates, \" +\n \"or an 'AI touched' entry instead of editing the description. Comments are \" +\n \"stamped with the current time automatically and never overwrite each other.\",\n inputSchema: {\n workItemId: z.string().describe(\"workItemId from list_work_items\"),\n body: z\n .string()\n .min(1)\n .describe(\n \"Comment text (markdown supported). To pull a person into the thread, mention them as [@Name](user:<userId>) \u2014 they are notified and the app renders it as a chip. userIds come from an item's assigneeId/reviewerId; there is no member lookup tool yet, so only mention ids you have seen.\",\n ),\n source: z\n .enum([\"user\", \"ai\"])\n .optional()\n .describe('Who authored it; defaults to \"ai\" for MCP callers'),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: false,\n idempotentHint: false,\n openWorldHint: false,\n },\n },\n\n async (args) => {\n const result = await getConvexClient().action(\n api.mcp.addWorkItemComment,\n {\n token: getToken(),\n ...args,\n agent: agentArg(),\n },\n );\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerListWorkItemComments(server: McpServer): void {\n server.registerTool(\n \"list_work_item_comments\",\n {\n description:\n \"List the timestamped comments on a work item, oldest first. Use this to check \" +\n \"whether the item was already touched/commented before adding a new comment.\",\n inputSchema: {\n workItemId: z.string().describe(\"workItemId from list_work_items\"),\n },\n annotations: {\n readOnlyHint: true,\n openWorldHint: false,\n },\n },\n\n async (args) => {\n const result = await getConvexClient().action(\n api.mcp.listWorkItemComments,\n {\n token: getToken(),\n ...args,\n },\n );\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerListValidations(server: McpServer): void {\n server.registerTool(\n \"list_validations\",\n {\n description:\n \"List a project's validation graph: core systems and validation/test tasks with their DERIVED state (passing, failing, stale, unvalidated). A task is 'stale' when a system it covers changed since it was last validated, or an upstream dependency is no longer passing. Call list_projects first to find the projectId.\",\n inputSchema: {\n projectId: z.string().describe(\"projectId from list_projects\"),\n },\n annotations: {\n readOnlyHint: true,\n openWorldHint: false,\n },\n },\n\n async ({ projectId }) => {\n const client = getConvexClient();\n const graph = await client.action(api.mcp.listValidations, {\n token: getToken(),\n projectId,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(graph, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerRecordValidation(server: McpServer): void {\n server.registerTool(\n \"record_validation\",\n {\n description:\n \"Check off a validation task by recording a pass or fail. Stamps the task as validated 'now', clearing any stale flag until a covered system changes or an upstream dependency moves again. Get validationTaskId from list_validations.\",\n inputSchema: {\n validationTaskId: z\n .string()\n .describe(\"validationTaskId from list_validations\"),\n result: z\n .enum([\"pass\", \"fail\"])\n .describe(\"Outcome of running the test\"),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: true,\n idempotentHint: true,\n openWorldHint: false,\n },\n },\n\n async ({ validationTaskId, result }) => {\n const client = getConvexClient();\n const res = await client.action(api.mcp.recordValidation, {\n token: getToken(),\n validationTaskId,\n result,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(res, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerMarkSystemChanged(server: McpServer): void {\n server.registerTool(\n \"mark_system_changed\",\n {\n description:\n \"Mark a core system as changed. This is the single action that invalidates testing: every validation task that covers this system (and everything transitively depending on those tasks) immediately becomes 'stale' and needs revalidation. Get systemId from list_validations.\",\n inputSchema: {\n systemId: z.string().describe(\"systemId from list_validations\"),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: false,\n idempotentHint: false,\n openWorldHint: false,\n },\n },\n\n async ({ systemId }) => {\n const client = getConvexClient();\n const res = await client.action(api.mcp.markSystemChanged, {\n token: getToken(),\n systemId,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(res, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerCreateSystem(server: McpServer): void {\n server.registerTool(\n \"create_system\",\n {\n description:\n \"Create a core system in a project \u2014 a subsystem (e.g. Auth, Payments, Sync) whose change should invalidate the validation tasks that cover it. Returns the new systemId.\",\n inputSchema: {\n projectId: z.string().describe(\"projectId from list_projects\"),\n name: z.string().min(1).describe(\"Short system name, e.g. 'Auth'\"),\n description: z.string().optional().describe(\"Optional details\"),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: false,\n idempotentHint: false,\n openWorldHint: false,\n },\n },\n\n async (args) => {\n const client = getConvexClient();\n const res = await client.action(api.mcp.createSystem, {\n token: getToken(),\n ...args,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(res, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerCreateValidationTask(server: McpServer): void {\n server.registerTool(\n \"create_validation_task\",\n {\n description:\n \"Create a validation/test task in a project. After creating it, use add_system_to_task to declare which systems it exercises (so it goes stale when they change) and add_validation_dependency to order it after other tasks. Returns the new validationTaskId.\",\n inputSchema: {\n projectId: z.string().describe(\"projectId from list_projects\"),\n title: z.string().min(1).describe(\"What this test validates\"),\n description: z.string().optional().describe(\"Optional steps / details\"),\n kind: z\n .enum([\"auto\", \"manual\"])\n .optional()\n .describe(\n \"'auto' if runnable by a test runner, 'manual' if a human checks it. Defaults to manual.\",\n ),\n workItemId: z\n .string()\n .optional()\n .describe(\n \"Optional workItemId to link this test to a feature for traceability\",\n ),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: false,\n idempotentHint: false,\n openWorldHint: false,\n },\n },\n\n async (args) => {\n const client = getConvexClient();\n const res = await client.action(api.mcp.createValidationTask, {\n token: getToken(),\n ...args,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(res, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerAddSystemToTask(server: McpServer): void {\n server.registerTool(\n \"add_system_to_task\",\n {\n description:\n \"Declare that a validation task COVERS (exercises) a system. Once linked, the task becomes 'stale' whenever that system is marked changed. Idempotent. Both IDs come from list_validations and must be in the same project.\",\n inputSchema: {\n validationTaskId: z\n .string()\n .describe(\"validationTaskId from list_validations\"),\n systemId: z.string().describe(\"systemId from list_validations\"),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: false,\n idempotentHint: true,\n openWorldHint: false,\n },\n },\n\n async ({ validationTaskId, systemId }) => {\n const client = getConvexClient();\n const res = await client.action(api.mcp.addSystemToTask, {\n token: getToken(),\n validationTaskId,\n systemId,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(res, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerAddValidationDependency(server: McpServer): void {\n server.registerTool(\n \"add_validation_dependency\",\n {\n description:\n \"Make one validation task depend on another (validationTaskId depends on dependsOnTaskId). The dependent goes 'stale' whenever the upstream task is not passing or gets revalidated. Cycles and self-dependencies are rejected. Idempotent. Both IDs come from list_validations and must be in the same project.\",\n inputSchema: {\n validationTaskId: z\n .string()\n .describe(\"The dependent (downstream) task\"),\n dependsOnTaskId: z\n .string()\n .describe(\"The dependency (upstream) task it relies on\"),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: false,\n idempotentHint: true,\n openWorldHint: false,\n },\n },\n\n async ({ validationTaskId, dependsOnTaskId }) => {\n const client = getConvexClient();\n const res = await client.action(api.mcp.addValidationDependency, {\n token: getToken(),\n validationTaskId,\n dependsOnTaskId,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(res, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerListLabels(server: McpServer): void {\n server.registerTool(\n \"list_labels\",\n {\n description:\n \"List all labels defined in a project. Returns each label's id, name, and color. Use the labelId with add_label_to_work_item / remove_label_from_work_item.\",\n inputSchema: {\n projectId: z.string().describe(\"projectId from list_projects\"),\n },\n annotations: {\n readOnlyHint: true,\n openWorldHint: false,\n },\n },\n\n async (args) => {\n const result = await getConvexClient().action(api.mcp.listLabels, {\n token: getToken(),\n ...args,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerCreateLabel(server: McpServer): void {\n server.registerTool(\n \"create_label\",\n {\n description:\n \"Apply-or-seed a label. Returns the existing label if the name is \" +\n \"already taken (idempotent), and otherwise creates it ONLY if the name \" +\n \"is one of the curated ones. Any other new name is REFUSED \u2014 the reply \" +\n \"carries `refused: true`, the reason, and `available`, the project's \" +\n \"existing labels. Agents apply labels; they do not invent them, because \" +\n \"a near-duplicate of an existing label splits the vocabulary silently. \" +\n \"Prefer list_labels first. Colors are ignored for curated names so the \" +\n \"vocabulary looks the same in every project.\",\n inputSchema: {\n projectId: z.string().describe(\"projectId from list_projects\"),\n name: z\n .string()\n .min(1)\n .describe(\"Label name, unique within the project\"),\n color: z\n .string()\n .regex(/^#[0-9a-fA-F]{6}$/)\n .optional()\n .describe(\"Hex color like #2563eb. Defaults to a neutral slate.\"),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: false,\n idempotentHint: true,\n openWorldHint: false,\n },\n },\n\n async (args) => {\n const result = await getConvexClient().action(api.mcp.createLabel, {\n token: getToken(),\n ...args,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerAddLabelToWorkItem(server: McpServer): void {\n server.registerTool(\n \"add_label_to_work_item\",\n {\n description:\n \"Attach a label to a work item (idempotent). The label and work item must be in the same project. Get labelIds from list_labels / create_label.\",\n inputSchema: {\n workItemId: z.string().describe(\"workItemId from list_work_items\"),\n labelId: z\n .string()\n .describe(\"labelId from list_labels or create_label\"),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: false,\n idempotentHint: true,\n openWorldHint: false,\n },\n },\n\n async (args) => {\n const result = await getConvexClient().action(api.mcp.setWorkItemLabel, {\n token: getToken(),\n ...args,\n attached: true,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerRemoveLabelFromWorkItem(server: McpServer): void {\n server.registerTool(\n \"remove_label_from_work_item\",\n {\n description:\n \"Remove a label from a work item (idempotent \u2014 a no-op if it wasn't attached).\",\n inputSchema: {\n workItemId: z.string().describe(\"workItemId from list_work_items\"),\n labelId: z.string().describe(\"labelId from list_labels\"),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: true,\n idempotentHint: true,\n openWorldHint: false,\n },\n },\n\n async (args) => {\n const result = await getConvexClient().action(api.mcp.setWorkItemLabel, {\n token: getToken(),\n ...args,\n attached: false,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerListMilestones(server: McpServer): void {\n server.registerTool(\n \"list_milestones\",\n {\n description:\n \"List all milestones in a project. Returns each milestone's id, name, description, dueDate (unix ms), and status. Use the milestoneId with add_item_to_milestone / remove_item_from_milestone.\",\n inputSchema: {\n projectId: z.string().describe(\"projectId from list_projects\"),\n },\n annotations: {\n readOnlyHint: true,\n openWorldHint: false,\n },\n },\n\n async (args) => {\n const result = await getConvexClient().action(api.mcp.listMilestones, {\n token: getToken(),\n ...args,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerCreateMilestone(server: McpServer): void {\n server.registerTool(\n \"create_milestone\",\n {\n description:\n \"Create a milestone in a project. Returns the milestoneId. Good for grouping work into phases (e.g. 'Phase 1 \u2014 Web', 'Phase 2 \u2014 Native').\",\n inputSchema: {\n projectId: z.string().describe(\"projectId from list_projects\"),\n name: z.string().min(1).describe(\"Milestone name\"),\n description: z\n .string()\n .optional()\n .describe(\"Optional markdown description\"),\n dueDate: z\n .number()\n .optional()\n .describe(\"Optional due date as a unix timestamp in milliseconds\"),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: false,\n idempotentHint: false,\n openWorldHint: false,\n },\n },\n\n async (args) => {\n const result = await getConvexClient().action(api.mcp.createMilestone, {\n token: getToken(),\n ...args,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerAddItemToMilestone(server: McpServer): void {\n server.registerTool(\n \"add_item_to_milestone\",\n {\n description:\n \"Associate a work item with a milestone (idempotent). Both must be in the same project.\",\n inputSchema: {\n milestoneId: z\n .string()\n .describe(\"milestoneId from list_milestones or create_milestone\"),\n workItemId: z.string().describe(\"workItemId from list_work_items\"),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: false,\n idempotentHint: true,\n openWorldHint: false,\n },\n },\n\n async (args) => {\n const result = await getConvexClient().action(\n api.mcp.setWorkItemMilestone,\n {\n token: getToken(),\n ...args,\n attached: true,\n },\n );\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n", "import type { McpServer } from \"@modelcontextprotocol/sdk/server/mcp.js\";\nimport { z } from \"zod\";\nimport { api } from \"@nimara/convex/convex/_generated/api.js\";\nimport { getConvexClient, getToken } from \"../convex.js\";\n\nexport function registerRemoveItemFromMilestone(server: McpServer): void {\n server.registerTool(\n \"remove_item_from_milestone\",\n {\n description:\n \"Remove a work item's association with a milestone (idempotent \u2014 a no-op if it wasn't associated).\",\n inputSchema: {\n milestoneId: z.string().describe(\"milestoneId from list_milestones\"),\n workItemId: z.string().describe(\"workItemId from list_work_items\"),\n },\n annotations: {\n readOnlyHint: false,\n destructiveHint: true,\n idempotentHint: true,\n openWorldHint: false,\n },\n },\n\n async (args) => {\n const result = await getConvexClient().action(\n api.mcp.setWorkItemMilestone,\n {\n token: getToken(),\n ...args,\n attached: false,\n },\n );\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n },\n );\n}\n"],
|
|
5
|
+
"mappings": "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",
|
|
6
|
+
"names": ["z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z", "z"]
|
|
7
7
|
}
|