opencara 0.106.0 → 0.107.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/dist/bin.js +175 -6
- package/dist/claude-acp.js +44 -8
- package/dist/opencara-mcp.js +187 -4
- package/package.json +1 -1
package/dist/bin.js
CHANGED
|
@@ -82,12 +82,19 @@ var AcpHistoryTurnSchema = z3.object({
|
|
|
82
82
|
role: z3.enum(["user", "assistant"]),
|
|
83
83
|
text: z3.string()
|
|
84
84
|
});
|
|
85
|
+
var AcpPermissionModeSchema = z3.enum([
|
|
86
|
+
"default",
|
|
87
|
+
"acceptEdits",
|
|
88
|
+
"plan",
|
|
89
|
+
"bypassPermissions"
|
|
90
|
+
]);
|
|
85
91
|
var AcpSpecSchema = z3.object({
|
|
86
92
|
systemPromptMd: z3.string(),
|
|
87
93
|
userPromptMd: z3.string(),
|
|
88
94
|
history: z3.array(AcpHistoryTurnSchema).default([]),
|
|
89
95
|
pageContextJson: z3.string().optional(),
|
|
90
|
-
priorSessionId: z3.string().optional()
|
|
96
|
+
priorSessionId: z3.string().optional(),
|
|
97
|
+
permissionMode: AcpPermissionModeSchema.optional()
|
|
91
98
|
});
|
|
92
99
|
var AgentSpecSchema = z3.object({
|
|
93
100
|
kind: z3.string(),
|
|
@@ -198,6 +205,11 @@ var HelloAckSchema = z4.object({
|
|
|
198
205
|
agentHostId: z4.string(),
|
|
199
206
|
deviceName: z4.string()
|
|
200
207
|
});
|
|
208
|
+
var CancelJobSchema = z4.object({
|
|
209
|
+
type: z4.literal("cancel"),
|
|
210
|
+
runId: z4.string(),
|
|
211
|
+
reason: z4.enum(["user_stopped", "wave_cancelled"])
|
|
212
|
+
});
|
|
201
213
|
var PingSchema = z4.object({ type: z4.literal("ping") });
|
|
202
214
|
var PongSchema = z4.object({ type: z4.literal("pong") });
|
|
203
215
|
var AgentCallEnvelope = {
|
|
@@ -225,10 +237,56 @@ var TemplateNodeConfigSetCallSchema = z4.object({
|
|
|
225
237
|
nodeId: z4.string().min(1),
|
|
226
238
|
config: z4.record(z4.string(), z4.unknown())
|
|
227
239
|
});
|
|
240
|
+
var KanbanWaveDispatchCallSchema = z4.object({
|
|
241
|
+
...AgentCallEnvelope,
|
|
242
|
+
kind: z4.literal("kanban.wave.dispatch"),
|
|
243
|
+
flowSlug: z4.string().min(1),
|
|
244
|
+
issueNumbers: z4.array(z4.number().int()).min(1).max(10)
|
|
245
|
+
});
|
|
246
|
+
var IssueSubissueCreateCallSchema = z4.object({
|
|
247
|
+
...AgentCallEnvelope,
|
|
248
|
+
kind: z4.literal("issue.subissue.create"),
|
|
249
|
+
parentIssueNumber: z4.number().int(),
|
|
250
|
+
title: z4.string().min(1),
|
|
251
|
+
bodyMd: z4.string(),
|
|
252
|
+
labels: z4.array(z4.string()).optional()
|
|
253
|
+
});
|
|
254
|
+
var IssueCreateCallSchema = z4.object({
|
|
255
|
+
...AgentCallEnvelope,
|
|
256
|
+
kind: z4.literal("issue.create"),
|
|
257
|
+
title: z4.string().min(1),
|
|
258
|
+
bodyMd: z4.string(),
|
|
259
|
+
labels: z4.array(z4.string()).optional()
|
|
260
|
+
});
|
|
261
|
+
var IssueStateSetCallSchema = z4.object({
|
|
262
|
+
...AgentCallEnvelope,
|
|
263
|
+
kind: z4.literal("issue.state.set"),
|
|
264
|
+
issueNumber: z4.number().int(),
|
|
265
|
+
state: z4.enum(["open", "closed"]),
|
|
266
|
+
stateReason: z4.enum(["completed", "not_planned", "reopened"]).nullable().optional()
|
|
267
|
+
});
|
|
268
|
+
var IssueCommentCreateCallSchema = z4.object({
|
|
269
|
+
...AgentCallEnvelope,
|
|
270
|
+
kind: z4.literal("issue.comment.create"),
|
|
271
|
+
issueNumber: z4.number().int(),
|
|
272
|
+
bodyMd: z4.string().min(1)
|
|
273
|
+
});
|
|
274
|
+
var IssueLabelsSetCallSchema = z4.object({
|
|
275
|
+
...AgentCallEnvelope,
|
|
276
|
+
kind: z4.literal("issue.labels.set"),
|
|
277
|
+
issueNumber: z4.number().int(),
|
|
278
|
+
labels: z4.array(z4.string())
|
|
279
|
+
});
|
|
228
280
|
var AgentCallSchema = z4.discriminatedUnion("kind", [
|
|
229
281
|
IssueBodySetCallSchema,
|
|
230
282
|
FlowNodeConfigSetCallSchema,
|
|
231
|
-
TemplateNodeConfigSetCallSchema
|
|
283
|
+
TemplateNodeConfigSetCallSchema,
|
|
284
|
+
KanbanWaveDispatchCallSchema,
|
|
285
|
+
IssueSubissueCreateCallSchema,
|
|
286
|
+
IssueCreateCallSchema,
|
|
287
|
+
IssueStateSetCallSchema,
|
|
288
|
+
IssueCommentCreateCallSchema,
|
|
289
|
+
IssueLabelsSetCallSchema
|
|
232
290
|
]);
|
|
233
291
|
var AgentCallRequestEnvelope = {
|
|
234
292
|
type: z4.literal("agent-call-request"),
|
|
@@ -255,10 +313,56 @@ var TemplateNodeConfigSetCallRequestSchema = z4.object({
|
|
|
255
313
|
nodeId: z4.string().min(1),
|
|
256
314
|
config: z4.record(z4.string(), z4.unknown())
|
|
257
315
|
});
|
|
316
|
+
var KanbanWaveDispatchCallRequestSchema = z4.object({
|
|
317
|
+
...AgentCallRequestEnvelope,
|
|
318
|
+
kind: z4.literal("kanban.wave.dispatch"),
|
|
319
|
+
flowSlug: z4.string().min(1),
|
|
320
|
+
issueNumbers: z4.array(z4.number().int()).min(1).max(10)
|
|
321
|
+
});
|
|
322
|
+
var IssueSubissueCreateCallRequestSchema = z4.object({
|
|
323
|
+
...AgentCallRequestEnvelope,
|
|
324
|
+
kind: z4.literal("issue.subissue.create"),
|
|
325
|
+
parentIssueNumber: z4.number().int(),
|
|
326
|
+
title: z4.string().min(1),
|
|
327
|
+
bodyMd: z4.string(),
|
|
328
|
+
labels: z4.array(z4.string()).optional()
|
|
329
|
+
});
|
|
330
|
+
var IssueCreateCallRequestSchema = z4.object({
|
|
331
|
+
...AgentCallRequestEnvelope,
|
|
332
|
+
kind: z4.literal("issue.create"),
|
|
333
|
+
title: z4.string().min(1),
|
|
334
|
+
bodyMd: z4.string(),
|
|
335
|
+
labels: z4.array(z4.string()).optional()
|
|
336
|
+
});
|
|
337
|
+
var IssueStateSetCallRequestSchema = z4.object({
|
|
338
|
+
...AgentCallRequestEnvelope,
|
|
339
|
+
kind: z4.literal("issue.state.set"),
|
|
340
|
+
issueNumber: z4.number().int(),
|
|
341
|
+
state: z4.enum(["open", "closed"]),
|
|
342
|
+
stateReason: z4.enum(["completed", "not_planned", "reopened"]).nullable().optional()
|
|
343
|
+
});
|
|
344
|
+
var IssueCommentCreateCallRequestSchema = z4.object({
|
|
345
|
+
...AgentCallRequestEnvelope,
|
|
346
|
+
kind: z4.literal("issue.comment.create"),
|
|
347
|
+
issueNumber: z4.number().int(),
|
|
348
|
+
bodyMd: z4.string().min(1)
|
|
349
|
+
});
|
|
350
|
+
var IssueLabelsSetCallRequestSchema = z4.object({
|
|
351
|
+
...AgentCallRequestEnvelope,
|
|
352
|
+
kind: z4.literal("issue.labels.set"),
|
|
353
|
+
issueNumber: z4.number().int(),
|
|
354
|
+
labels: z4.array(z4.string())
|
|
355
|
+
});
|
|
258
356
|
var AgentCallRequestSchema = z4.discriminatedUnion("kind", [
|
|
259
357
|
IssueBodySetCallRequestSchema,
|
|
260
358
|
FlowNodeConfigSetCallRequestSchema,
|
|
261
|
-
TemplateNodeConfigSetCallRequestSchema
|
|
359
|
+
TemplateNodeConfigSetCallRequestSchema,
|
|
360
|
+
KanbanWaveDispatchCallRequestSchema,
|
|
361
|
+
IssueSubissueCreateCallRequestSchema,
|
|
362
|
+
IssueCreateCallRequestSchema,
|
|
363
|
+
IssueStateSetCallRequestSchema,
|
|
364
|
+
IssueCommentCreateCallRequestSchema,
|
|
365
|
+
IssueLabelsSetCallRequestSchema
|
|
262
366
|
]);
|
|
263
367
|
var AgentCallResultSchema = z4.object({
|
|
264
368
|
type: z4.literal("agent-call-result"),
|
|
@@ -273,7 +377,8 @@ var ServerToDeviceMessageSchema = z4.discriminatedUnion("type", [
|
|
|
273
377
|
JobAssignmentSchema,
|
|
274
378
|
HelloAckSchema,
|
|
275
379
|
PingSchema,
|
|
276
|
-
AgentCallResultSchema
|
|
380
|
+
AgentCallResultSchema,
|
|
381
|
+
CancelJobSchema
|
|
277
382
|
]);
|
|
278
383
|
var DeviceToServerMessageSchema = z4.union([
|
|
279
384
|
HelloMessageSchema,
|
|
@@ -1073,9 +1178,35 @@ function runAcpJob(opts) {
|
|
|
1073
1178
|
const translator = createUpdateTranslator(handlers.onLog);
|
|
1074
1179
|
client.onSessionUpdate((p) => translator.handle(p.update));
|
|
1075
1180
|
client.onStderr((chunk) => handlers.onLog("stderr", chunk));
|
|
1181
|
+
let activeSessionId = null;
|
|
1182
|
+
let cancelRequested = false;
|
|
1183
|
+
let forceCloseScheduled = false;
|
|
1184
|
+
const scheduleForceClose = () => {
|
|
1185
|
+
if (forceCloseScheduled) return;
|
|
1186
|
+
forceCloseScheduled = true;
|
|
1187
|
+
setTimeout(() => {
|
|
1188
|
+
client.close(0).catch(() => void 0);
|
|
1189
|
+
}, 2e3);
|
|
1190
|
+
};
|
|
1076
1191
|
const controller = {
|
|
1077
1192
|
onAgentCallResult(msg) {
|
|
1078
1193
|
bridge.onResult(msg);
|
|
1194
|
+
},
|
|
1195
|
+
cancel() {
|
|
1196
|
+
if (cancelRequested) return;
|
|
1197
|
+
cancelRequested = true;
|
|
1198
|
+
if (activeSessionId) {
|
|
1199
|
+
try {
|
|
1200
|
+
client.cancel(activeSessionId);
|
|
1201
|
+
} catch (err) {
|
|
1202
|
+
handlers.onLog(
|
|
1203
|
+
"stderr",
|
|
1204
|
+
`[opencara] cancel notify failed: ${err instanceof Error ? err.message : String(err)}
|
|
1205
|
+
`
|
|
1206
|
+
);
|
|
1207
|
+
}
|
|
1208
|
+
}
|
|
1209
|
+
scheduleForceClose();
|
|
1079
1210
|
}
|
|
1080
1211
|
};
|
|
1081
1212
|
const promise = (async () => {
|
|
@@ -1102,8 +1233,21 @@ function runAcpJob(opts) {
|
|
|
1102
1233
|
const session = await client.newSession({ cwd, mcpServers });
|
|
1103
1234
|
sessionId = session.sessionId;
|
|
1104
1235
|
}
|
|
1236
|
+
activeSessionId = sessionId;
|
|
1237
|
+
if (cancelRequested) {
|
|
1238
|
+
try {
|
|
1239
|
+
client.cancel(sessionId);
|
|
1240
|
+
} catch {
|
|
1241
|
+
}
|
|
1242
|
+
result = { exitCode: 1, stopReason: "cancelled", sessionId };
|
|
1243
|
+
return result;
|
|
1244
|
+
}
|
|
1105
1245
|
const prompt = buildPromptContent(acpSpec);
|
|
1106
|
-
const promptResult = await client.prompt({
|
|
1246
|
+
const promptResult = await client.prompt({
|
|
1247
|
+
sessionId,
|
|
1248
|
+
prompt,
|
|
1249
|
+
...acpSpec.permissionMode ? { permissionMode: acpSpec.permissionMode } : {}
|
|
1250
|
+
});
|
|
1107
1251
|
result = {
|
|
1108
1252
|
exitCode: promptResult.stopReason === "end_turn" ? 0 : 1,
|
|
1109
1253
|
stopReason: promptResult.stopReason,
|
|
@@ -1232,7 +1376,7 @@ function resolveLocalAcpAdapter(command, args) {
|
|
|
1232
1376
|
}
|
|
1233
1377
|
|
|
1234
1378
|
// src/commands/run.ts
|
|
1235
|
-
var PKG_VERSION = "0.
|
|
1379
|
+
var PKG_VERSION = "0.107.0";
|
|
1236
1380
|
var LOG_FLUSH_MS = 800;
|
|
1237
1381
|
var MAX_CHUNK_SIZE = 4 * 1024;
|
|
1238
1382
|
async function run(opts = {}) {
|
|
@@ -1283,6 +1427,16 @@ function handleServerMessage(msg, client, _cfg) {
|
|
|
1283
1427
|
acpControllers.get(msg.runId)?.onAgentCallResult(msg);
|
|
1284
1428
|
return;
|
|
1285
1429
|
}
|
|
1430
|
+
if (msg.type === "cancel") {
|
|
1431
|
+
const ctrl = acpControllers.get(msg.runId);
|
|
1432
|
+
if (ctrl) {
|
|
1433
|
+
console.log(
|
|
1434
|
+
`[opencara] job ${msg.runId.slice(-8)} cancel requested (${msg.reason})`
|
|
1435
|
+
);
|
|
1436
|
+
ctrl.cancel();
|
|
1437
|
+
}
|
|
1438
|
+
return;
|
|
1439
|
+
}
|
|
1286
1440
|
}
|
|
1287
1441
|
async function executeJob(job, client) {
|
|
1288
1442
|
const runId = job.run.id;
|
|
@@ -1561,6 +1715,11 @@ function worktreeCreate(args) {
|
|
|
1561
1715
|
if (useLfs && !useCache) {
|
|
1562
1716
|
fail("--lfs requires --cache-repo");
|
|
1563
1717
|
}
|
|
1718
|
+
if (useLfs && !hasGitLfs()) {
|
|
1719
|
+
fail(
|
|
1720
|
+
"--lfs is set but git-lfs is not installed on this host \u2014 install it (e.g. `apt install git-lfs && git lfs install`) or disable LFS on the agent.worktree.cacheRepo config"
|
|
1721
|
+
);
|
|
1722
|
+
}
|
|
1564
1723
|
const cacheDir = useCache ? join2(CACHE_ROOT, safeKey(repo)) : null;
|
|
1565
1724
|
const gitEnv = useCache && !useLfs ? { ...process.env, GIT_LFS_SKIP_SMUDGE: "1" } : void 0;
|
|
1566
1725
|
const HELPER_SNIPPET = '!f() { echo username=x-access-token; echo "password=$GH_TOKEN"; }; f';
|
|
@@ -1733,6 +1892,16 @@ function refExists(cwd, ref) {
|
|
|
1733
1892
|
return false;
|
|
1734
1893
|
}
|
|
1735
1894
|
}
|
|
1895
|
+
function hasGitLfs() {
|
|
1896
|
+
try {
|
|
1897
|
+
execFileSync("git", ["lfs", "version"], {
|
|
1898
|
+
stdio: ["ignore", "ignore", "ignore"]
|
|
1899
|
+
});
|
|
1900
|
+
return true;
|
|
1901
|
+
} catch {
|
|
1902
|
+
return false;
|
|
1903
|
+
}
|
|
1904
|
+
}
|
|
1736
1905
|
function pickFlag(argv, name) {
|
|
1737
1906
|
const i = argv.indexOf(name);
|
|
1738
1907
|
if (i === -1) return void 0;
|
package/dist/claude-acp.js
CHANGED
|
@@ -62,7 +62,7 @@ function notify(method, params) {
|
|
|
62
62
|
send({ jsonrpc: "2.0", method, params });
|
|
63
63
|
}
|
|
64
64
|
var sessions = /* @__PURE__ */ new Map();
|
|
65
|
-
async function runClaudeTurn(sessionId, state, promptText) {
|
|
65
|
+
async function runClaudeTurn(sessionId, state, promptText, permissionMode) {
|
|
66
66
|
return new Promise((resolve, reject) => {
|
|
67
67
|
const idFlag = state.resume ? "--resume" : "--session-id";
|
|
68
68
|
const args = [
|
|
@@ -75,16 +75,19 @@ async function runClaudeTurn(sessionId, state, promptText) {
|
|
|
75
75
|
"--include-partial-messages",
|
|
76
76
|
"--verbose",
|
|
77
77
|
idFlag,
|
|
78
|
-
sessionId
|
|
79
|
-
// Headless: no human in the loop to approve tool use. Matches the
|
|
80
|
-
// legacy `claudeAdapter` posture in agents/kinds.ts.
|
|
81
|
-
"--dangerously-skip-permissions"
|
|
78
|
+
sessionId
|
|
82
79
|
];
|
|
80
|
+
if (permissionMode && permissionMode !== "default") {
|
|
81
|
+
args.push("--permission-mode", permissionMode);
|
|
82
|
+
} else {
|
|
83
|
+
args.push("--dangerously-skip-permissions");
|
|
84
|
+
}
|
|
83
85
|
const child = spawn("claude", args, {
|
|
84
86
|
cwd: state.cwd,
|
|
85
87
|
env: process.env,
|
|
86
88
|
stdio: ["pipe", "pipe", "pipe"]
|
|
87
89
|
});
|
|
90
|
+
state.activeChild = child;
|
|
88
91
|
child.stdin.on("error", () => {
|
|
89
92
|
});
|
|
90
93
|
child.stdin.end(promptText);
|
|
@@ -116,9 +119,14 @@ async function runClaudeTurn(sessionId, state, promptText) {
|
|
|
116
119
|
reject(err);
|
|
117
120
|
}
|
|
118
121
|
});
|
|
119
|
-
child.on("close", (code) => {
|
|
122
|
+
child.on("close", (code, signal) => {
|
|
123
|
+
state.activeChild = null;
|
|
120
124
|
if (!resolved) {
|
|
121
125
|
resolved = true;
|
|
126
|
+
if (signal === "SIGTERM" || signal === "SIGINT") {
|
|
127
|
+
resolve({ stopReason: "cancelled" });
|
|
128
|
+
return;
|
|
129
|
+
}
|
|
122
130
|
if (code !== 0) {
|
|
123
131
|
stderr.write(`[claude-acp] claude exited code=${code} without result event
|
|
124
132
|
`);
|
|
@@ -225,10 +233,29 @@ async function handlePrompt(params) {
|
|
|
225
233
|
if (promptText.length === 0) {
|
|
226
234
|
throw new Error("session/prompt: no text content blocks");
|
|
227
235
|
}
|
|
228
|
-
const result = await runClaudeTurn(
|
|
236
|
+
const result = await runClaudeTurn(
|
|
237
|
+
params.sessionId,
|
|
238
|
+
state,
|
|
239
|
+
promptText,
|
|
240
|
+
params.permissionMode
|
|
241
|
+
);
|
|
229
242
|
state.resume = true;
|
|
230
243
|
return { stopReason: result.stopReason };
|
|
231
244
|
}
|
|
245
|
+
function handleCancel(params) {
|
|
246
|
+
const state = sessions.get(params.sessionId);
|
|
247
|
+
if (!state) return;
|
|
248
|
+
const child = state.activeChild;
|
|
249
|
+
if (!child) return;
|
|
250
|
+
try {
|
|
251
|
+
child.kill("SIGTERM");
|
|
252
|
+
} catch (err) {
|
|
253
|
+
stderr.write(
|
|
254
|
+
`[claude-acp] session/cancel kill failed: ${err instanceof Error ? err.message : String(err)}
|
|
255
|
+
`
|
|
256
|
+
);
|
|
257
|
+
}
|
|
258
|
+
}
|
|
232
259
|
var isMainModule = import.meta.url === `file://${process.argv[1]}` || process.argv[1]?.endsWith("claude-acp.ts") === true || process.argv[1]?.endsWith("claude-acp.js") === true;
|
|
233
260
|
if (isMainModule) {
|
|
234
261
|
const decoder = new FrameDecoder();
|
|
@@ -246,7 +273,16 @@ if (isMainModule) {
|
|
|
246
273
|
});
|
|
247
274
|
}
|
|
248
275
|
async function dispatch(msg) {
|
|
249
|
-
if (!("id" in msg) || msg.id == null)
|
|
276
|
+
if (!("id" in msg) || msg.id == null) {
|
|
277
|
+
const notification = msg;
|
|
278
|
+
if (notification.method === "session/cancel") {
|
|
279
|
+
const params = notification.params;
|
|
280
|
+
if (params && typeof params.sessionId === "string") {
|
|
281
|
+
handleCancel(params);
|
|
282
|
+
}
|
|
283
|
+
}
|
|
284
|
+
return;
|
|
285
|
+
}
|
|
250
286
|
if ("result" in msg || "error" in msg) return;
|
|
251
287
|
const req = msg;
|
|
252
288
|
try {
|
package/dist/opencara-mcp.js
CHANGED
|
@@ -123,12 +123,19 @@ var AcpHistoryTurnSchema = z2.object({
|
|
|
123
123
|
role: z2.enum(["user", "assistant"]),
|
|
124
124
|
text: z2.string()
|
|
125
125
|
});
|
|
126
|
+
var AcpPermissionModeSchema = z2.enum([
|
|
127
|
+
"default",
|
|
128
|
+
"acceptEdits",
|
|
129
|
+
"plan",
|
|
130
|
+
"bypassPermissions"
|
|
131
|
+
]);
|
|
126
132
|
var AcpSpecSchema = z2.object({
|
|
127
133
|
systemPromptMd: z2.string(),
|
|
128
134
|
userPromptMd: z2.string(),
|
|
129
135
|
history: z2.array(AcpHistoryTurnSchema).default([]),
|
|
130
136
|
pageContextJson: z2.string().optional(),
|
|
131
|
-
priorSessionId: z2.string().optional()
|
|
137
|
+
priorSessionId: z2.string().optional(),
|
|
138
|
+
permissionMode: AcpPermissionModeSchema.optional()
|
|
132
139
|
});
|
|
133
140
|
var AgentSpecSchema = z2.object({
|
|
134
141
|
kind: z2.string(),
|
|
@@ -239,6 +246,11 @@ var HelloAckSchema = z3.object({
|
|
|
239
246
|
agentHostId: z3.string(),
|
|
240
247
|
deviceName: z3.string()
|
|
241
248
|
});
|
|
249
|
+
var CancelJobSchema = z3.object({
|
|
250
|
+
type: z3.literal("cancel"),
|
|
251
|
+
runId: z3.string(),
|
|
252
|
+
reason: z3.enum(["user_stopped", "wave_cancelled"])
|
|
253
|
+
});
|
|
242
254
|
var PingSchema = z3.object({ type: z3.literal("ping") });
|
|
243
255
|
var PongSchema = z3.object({ type: z3.literal("pong") });
|
|
244
256
|
var AgentCallEnvelope = {
|
|
@@ -266,10 +278,56 @@ var TemplateNodeConfigSetCallSchema = z3.object({
|
|
|
266
278
|
nodeId: z3.string().min(1),
|
|
267
279
|
config: z3.record(z3.string(), z3.unknown())
|
|
268
280
|
});
|
|
281
|
+
var KanbanWaveDispatchCallSchema = z3.object({
|
|
282
|
+
...AgentCallEnvelope,
|
|
283
|
+
kind: z3.literal("kanban.wave.dispatch"),
|
|
284
|
+
flowSlug: z3.string().min(1),
|
|
285
|
+
issueNumbers: z3.array(z3.number().int()).min(1).max(10)
|
|
286
|
+
});
|
|
287
|
+
var IssueSubissueCreateCallSchema = z3.object({
|
|
288
|
+
...AgentCallEnvelope,
|
|
289
|
+
kind: z3.literal("issue.subissue.create"),
|
|
290
|
+
parentIssueNumber: z3.number().int(),
|
|
291
|
+
title: z3.string().min(1),
|
|
292
|
+
bodyMd: z3.string(),
|
|
293
|
+
labels: z3.array(z3.string()).optional()
|
|
294
|
+
});
|
|
295
|
+
var IssueCreateCallSchema = z3.object({
|
|
296
|
+
...AgentCallEnvelope,
|
|
297
|
+
kind: z3.literal("issue.create"),
|
|
298
|
+
title: z3.string().min(1),
|
|
299
|
+
bodyMd: z3.string(),
|
|
300
|
+
labels: z3.array(z3.string()).optional()
|
|
301
|
+
});
|
|
302
|
+
var IssueStateSetCallSchema = z3.object({
|
|
303
|
+
...AgentCallEnvelope,
|
|
304
|
+
kind: z3.literal("issue.state.set"),
|
|
305
|
+
issueNumber: z3.number().int(),
|
|
306
|
+
state: z3.enum(["open", "closed"]),
|
|
307
|
+
stateReason: z3.enum(["completed", "not_planned", "reopened"]).nullable().optional()
|
|
308
|
+
});
|
|
309
|
+
var IssueCommentCreateCallSchema = z3.object({
|
|
310
|
+
...AgentCallEnvelope,
|
|
311
|
+
kind: z3.literal("issue.comment.create"),
|
|
312
|
+
issueNumber: z3.number().int(),
|
|
313
|
+
bodyMd: z3.string().min(1)
|
|
314
|
+
});
|
|
315
|
+
var IssueLabelsSetCallSchema = z3.object({
|
|
316
|
+
...AgentCallEnvelope,
|
|
317
|
+
kind: z3.literal("issue.labels.set"),
|
|
318
|
+
issueNumber: z3.number().int(),
|
|
319
|
+
labels: z3.array(z3.string())
|
|
320
|
+
});
|
|
269
321
|
var AgentCallSchema = z3.discriminatedUnion("kind", [
|
|
270
322
|
IssueBodySetCallSchema,
|
|
271
323
|
FlowNodeConfigSetCallSchema,
|
|
272
|
-
TemplateNodeConfigSetCallSchema
|
|
324
|
+
TemplateNodeConfigSetCallSchema,
|
|
325
|
+
KanbanWaveDispatchCallSchema,
|
|
326
|
+
IssueSubissueCreateCallSchema,
|
|
327
|
+
IssueCreateCallSchema,
|
|
328
|
+
IssueStateSetCallSchema,
|
|
329
|
+
IssueCommentCreateCallSchema,
|
|
330
|
+
IssueLabelsSetCallSchema
|
|
273
331
|
]);
|
|
274
332
|
var AgentCallRequestEnvelope = {
|
|
275
333
|
type: z3.literal("agent-call-request"),
|
|
@@ -296,10 +354,56 @@ var TemplateNodeConfigSetCallRequestSchema = z3.object({
|
|
|
296
354
|
nodeId: z3.string().min(1),
|
|
297
355
|
config: z3.record(z3.string(), z3.unknown())
|
|
298
356
|
});
|
|
357
|
+
var KanbanWaveDispatchCallRequestSchema = z3.object({
|
|
358
|
+
...AgentCallRequestEnvelope,
|
|
359
|
+
kind: z3.literal("kanban.wave.dispatch"),
|
|
360
|
+
flowSlug: z3.string().min(1),
|
|
361
|
+
issueNumbers: z3.array(z3.number().int()).min(1).max(10)
|
|
362
|
+
});
|
|
363
|
+
var IssueSubissueCreateCallRequestSchema = z3.object({
|
|
364
|
+
...AgentCallRequestEnvelope,
|
|
365
|
+
kind: z3.literal("issue.subissue.create"),
|
|
366
|
+
parentIssueNumber: z3.number().int(),
|
|
367
|
+
title: z3.string().min(1),
|
|
368
|
+
bodyMd: z3.string(),
|
|
369
|
+
labels: z3.array(z3.string()).optional()
|
|
370
|
+
});
|
|
371
|
+
var IssueCreateCallRequestSchema = z3.object({
|
|
372
|
+
...AgentCallRequestEnvelope,
|
|
373
|
+
kind: z3.literal("issue.create"),
|
|
374
|
+
title: z3.string().min(1),
|
|
375
|
+
bodyMd: z3.string(),
|
|
376
|
+
labels: z3.array(z3.string()).optional()
|
|
377
|
+
});
|
|
378
|
+
var IssueStateSetCallRequestSchema = z3.object({
|
|
379
|
+
...AgentCallRequestEnvelope,
|
|
380
|
+
kind: z3.literal("issue.state.set"),
|
|
381
|
+
issueNumber: z3.number().int(),
|
|
382
|
+
state: z3.enum(["open", "closed"]),
|
|
383
|
+
stateReason: z3.enum(["completed", "not_planned", "reopened"]).nullable().optional()
|
|
384
|
+
});
|
|
385
|
+
var IssueCommentCreateCallRequestSchema = z3.object({
|
|
386
|
+
...AgentCallRequestEnvelope,
|
|
387
|
+
kind: z3.literal("issue.comment.create"),
|
|
388
|
+
issueNumber: z3.number().int(),
|
|
389
|
+
bodyMd: z3.string().min(1)
|
|
390
|
+
});
|
|
391
|
+
var IssueLabelsSetCallRequestSchema = z3.object({
|
|
392
|
+
...AgentCallRequestEnvelope,
|
|
393
|
+
kind: z3.literal("issue.labels.set"),
|
|
394
|
+
issueNumber: z3.number().int(),
|
|
395
|
+
labels: z3.array(z3.string())
|
|
396
|
+
});
|
|
299
397
|
var AgentCallRequestSchema = z3.discriminatedUnion("kind", [
|
|
300
398
|
IssueBodySetCallRequestSchema,
|
|
301
399
|
FlowNodeConfigSetCallRequestSchema,
|
|
302
|
-
TemplateNodeConfigSetCallRequestSchema
|
|
400
|
+
TemplateNodeConfigSetCallRequestSchema,
|
|
401
|
+
KanbanWaveDispatchCallRequestSchema,
|
|
402
|
+
IssueSubissueCreateCallRequestSchema,
|
|
403
|
+
IssueCreateCallRequestSchema,
|
|
404
|
+
IssueStateSetCallRequestSchema,
|
|
405
|
+
IssueCommentCreateCallRequestSchema,
|
|
406
|
+
IssueLabelsSetCallRequestSchema
|
|
303
407
|
]);
|
|
304
408
|
var AgentCallResultSchema = z3.object({
|
|
305
409
|
type: z3.literal("agent-call-result"),
|
|
@@ -314,7 +418,8 @@ var ServerToDeviceMessageSchema = z3.discriminatedUnion("type", [
|
|
|
314
418
|
JobAssignmentSchema,
|
|
315
419
|
HelloAckSchema,
|
|
316
420
|
PingSchema,
|
|
317
|
-
AgentCallResultSchema
|
|
421
|
+
AgentCallResultSchema,
|
|
422
|
+
CancelJobSchema
|
|
318
423
|
]);
|
|
319
424
|
var DeviceToServerMessageSchema = z3.union([
|
|
320
425
|
HelloMessageSchema,
|
|
@@ -383,6 +488,42 @@ var templateNodeConfigSetShape = TemplateNodeConfigSetCallSchema.omit({
|
|
|
383
488
|
callId: true,
|
|
384
489
|
kind: true
|
|
385
490
|
}).shape;
|
|
491
|
+
var kanbanWaveDispatchShape = KanbanWaveDispatchCallSchema.omit({
|
|
492
|
+
type: true,
|
|
493
|
+
runId: true,
|
|
494
|
+
callId: true,
|
|
495
|
+
kind: true
|
|
496
|
+
}).shape;
|
|
497
|
+
var issueSubissueCreateShape = IssueSubissueCreateCallSchema.omit({
|
|
498
|
+
type: true,
|
|
499
|
+
runId: true,
|
|
500
|
+
callId: true,
|
|
501
|
+
kind: true
|
|
502
|
+
}).shape;
|
|
503
|
+
var issueCreateShape = IssueCreateCallSchema.omit({
|
|
504
|
+
type: true,
|
|
505
|
+
runId: true,
|
|
506
|
+
callId: true,
|
|
507
|
+
kind: true
|
|
508
|
+
}).shape;
|
|
509
|
+
var issueStateSetShape = IssueStateSetCallSchema.omit({
|
|
510
|
+
type: true,
|
|
511
|
+
runId: true,
|
|
512
|
+
callId: true,
|
|
513
|
+
kind: true
|
|
514
|
+
}).shape;
|
|
515
|
+
var issueCommentCreateShape = IssueCommentCreateCallSchema.omit({
|
|
516
|
+
type: true,
|
|
517
|
+
runId: true,
|
|
518
|
+
callId: true,
|
|
519
|
+
kind: true
|
|
520
|
+
}).shape;
|
|
521
|
+
var issueLabelsSetShape = IssueLabelsSetCallSchema.omit({
|
|
522
|
+
type: true,
|
|
523
|
+
runId: true,
|
|
524
|
+
callId: true,
|
|
525
|
+
kind: true
|
|
526
|
+
}).shape;
|
|
386
527
|
var TOOLS = [
|
|
387
528
|
{
|
|
388
529
|
name: "opencara_issue_body_set",
|
|
@@ -404,6 +545,48 @@ var TOOLS = [
|
|
|
404
545
|
title: "Update a flow-template draft node's config",
|
|
405
546
|
description: "Replace the config blob of a node in the user's draft of the named flow template. Per-user scope, not per-project. Reject with reason if the template draft isn't owned by the run's user.",
|
|
406
547
|
inputShape: templateNodeConfigSetShape
|
|
548
|
+
},
|
|
549
|
+
{
|
|
550
|
+
name: "opencara_kanban_wave_dispatch",
|
|
551
|
+
kind: "kanban.wave.dispatch",
|
|
552
|
+
title: "Dispatch a batch of issues to a flow",
|
|
553
|
+
description: "Dispatch up to 10 issues in parallel to the named project flow. Requires project scope. Reject if the flow does not exist, is disabled, or any of the issue numbers are not in the project. Returns the wave id.",
|
|
554
|
+
inputShape: kanbanWaveDispatchShape
|
|
555
|
+
},
|
|
556
|
+
{
|
|
557
|
+
name: "opencara_issue_subissue_create",
|
|
558
|
+
kind: "issue.subissue.create",
|
|
559
|
+
title: "Create a GitHub sub-issue under a parent",
|
|
560
|
+
description: "Create a new GitHub issue and link it as a child of the given parent issue via the GraphQL addSubIssue mutation. Requires project scope. Reject if the parent issue is not in the project.",
|
|
561
|
+
inputShape: issueSubissueCreateShape
|
|
562
|
+
},
|
|
563
|
+
{
|
|
564
|
+
name: "opencara_issue_create",
|
|
565
|
+
kind: "issue.create",
|
|
566
|
+
title: "Create a top-level GitHub issue",
|
|
567
|
+
description: "Create a new GitHub issue in the run's project with no parent link. Requires project scope. Returns the new issueNumber and nodeId.",
|
|
568
|
+
inputShape: issueCreateShape
|
|
569
|
+
},
|
|
570
|
+
{
|
|
571
|
+
name: "opencara_issue_state_set",
|
|
572
|
+
kind: "issue.state.set",
|
|
573
|
+
title: "Open or close an existing issue",
|
|
574
|
+
description: "Set an issue's state to open or closed. Optional stateReason: completed | not_planned | reopened. Requires project scope. Reject if the issue is not in the project.",
|
|
575
|
+
inputShape: issueStateSetShape
|
|
576
|
+
},
|
|
577
|
+
{
|
|
578
|
+
name: "opencara_issue_comment_create",
|
|
579
|
+
kind: "issue.comment.create",
|
|
580
|
+
title: "Post a comment on an issue",
|
|
581
|
+
description: "Post a Markdown comment on the named issue. Comments are not mirrored locally; the comment lives on GitHub. Requires project scope. Reject if the issue is not in the project.",
|
|
582
|
+
inputShape: issueCommentCreateShape
|
|
583
|
+
},
|
|
584
|
+
{
|
|
585
|
+
name: "opencara_issue_labels_set",
|
|
586
|
+
kind: "issue.labels.set",
|
|
587
|
+
title: "Replace the label set on an issue",
|
|
588
|
+
description: "Set the issue's labels to exactly the listed names (REST setLabels semantics). Any label not in the list is removed; empty array clears all labels. Requires project scope.",
|
|
589
|
+
inputShape: issueLabelsSetShape
|
|
407
590
|
}
|
|
408
591
|
];
|
|
409
592
|
function registerOpencaraTools(server, router) {
|