@a5c-ai/tasks-mux 5.0.1-staging.a2e883985f51
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 +103 -0
- package/dist/auth/forge-interface.d.ts +67 -0
- package/dist/auth/forge-interface.d.ts.map +1 -0
- package/dist/auth/forge-interface.js +69 -0
- package/dist/auth/github-app.d.ts +64 -0
- package/dist/auth/github-app.d.ts.map +1 -0
- package/dist/auth/github-app.js +141 -0
- package/dist/auth/github-oauth.d.ts +27 -0
- package/dist/auth/github-oauth.d.ts.map +1 -0
- package/dist/auth/github-oauth.js +89 -0
- package/dist/auth/index.d.ts +8 -0
- package/dist/auth/index.d.ts.map +1 -0
- package/dist/auth/index.js +14 -0
- package/dist/auth/jwt.d.ts +24 -0
- package/dist/auth/jwt.d.ts.map +1 -0
- package/dist/auth/jwt.js +43 -0
- package/dist/auth/middleware.d.ts +22 -0
- package/dist/auth/middleware.d.ts.map +1 -0
- package/dist/auth/middleware.js +36 -0
- package/dist/auth/ssh-keys.d.ts +21 -0
- package/dist/auth/ssh-keys.d.ts.map +1 -0
- package/dist/auth/ssh-keys.js +59 -0
- package/dist/auth/types.d.ts +165 -0
- package/dist/auth/types.d.ts.map +1 -0
- package/dist/auth/types.js +53 -0
- package/dist/backend.d.ts +117 -0
- package/dist/backend.d.ts.map +1 -0
- package/dist/backend.js +15 -0
- package/dist/backends/git-native.d.ts +51 -0
- package/dist/backends/git-native.d.ts.map +1 -0
- package/dist/backends/git-native.js +324 -0
- package/dist/backends/github-issues.d.ts +77 -0
- package/dist/backends/github-issues.d.ts.map +1 -0
- package/dist/backends/github-issues.js +796 -0
- package/dist/backends/index.d.ts +48 -0
- package/dist/backends/index.d.ts.map +1 -0
- package/dist/backends/index.js +139 -0
- package/dist/backends/server.d.ts +41 -0
- package/dist/backends/server.d.ts.map +1 -0
- package/dist/backends/server.js +298 -0
- package/dist/cli/auth-store.d.ts +49 -0
- package/dist/cli/auth-store.d.ts.map +1 -0
- package/dist/cli/auth-store.js +150 -0
- package/dist/cli/client-config.d.ts +10 -0
- package/dist/cli/client-config.d.ts.map +1 -0
- package/dist/cli/client-config.js +87 -0
- package/dist/cli/commands/ask.d.ts +3 -0
- package/dist/cli/commands/ask.d.ts.map +1 -0
- package/dist/cli/commands/ask.js +171 -0
- package/dist/cli/commands/auth.d.ts +3 -0
- package/dist/cli/commands/auth.d.ts.map +1 -0
- package/dist/cli/commands/auth.js +510 -0
- package/dist/cli/commands/breakpoints.d.ts +3 -0
- package/dist/cli/commands/breakpoints.d.ts.map +1 -0
- package/dist/cli/commands/breakpoints.js +152 -0
- package/dist/cli/commands/responder-loop.d.ts +3 -0
- package/dist/cli/commands/responder-loop.d.ts.map +1 -0
- package/dist/cli/commands/responder-loop.js +78 -0
- package/dist/cli/commands/responders.d.ts +3 -0
- package/dist/cli/commands/responders.d.ts.map +1 -0
- package/dist/cli/commands/responders.js +74 -0
- package/dist/cli/commands/server.d.ts +3 -0
- package/dist/cli/commands/server.d.ts.map +1 -0
- package/dist/cli/commands/server.js +34 -0
- package/dist/cli/index.d.ts +4 -0
- package/dist/cli/index.d.ts.map +1 -0
- package/dist/cli/index.js +9 -0
- package/dist/cli/output.d.ts +26 -0
- package/dist/cli/output.d.ts.map +1 -0
- package/dist/cli/output.js +143 -0
- package/dist/cli/program.d.ts +6 -0
- package/dist/cli/program.d.ts.map +1 -0
- package/dist/cli/program.js +32 -0
- package/dist/client/answer-poller.d.ts +52 -0
- package/dist/client/answer-poller.d.ts.map +1 -0
- package/dist/client/answer-poller.js +199 -0
- package/dist/client/auth-client.d.ts +200 -0
- package/dist/client/auth-client.d.ts.map +1 -0
- package/dist/client/auth-client.js +309 -0
- package/dist/client/breakpoint-router.d.ts +45 -0
- package/dist/client/breakpoint-router.d.ts.map +1 -0
- package/dist/client/breakpoint-router.js +45 -0
- package/dist/client/index.d.ts +17 -0
- package/dist/client/index.d.ts.map +1 -0
- package/dist/client/index.js +16 -0
- package/dist/client/profile-validator.d.ts +34 -0
- package/dist/client/profile-validator.d.ts.map +1 -0
- package/dist/client/profile-validator.js +89 -0
- package/dist/client/responder-client.d.ts +39 -0
- package/dist/client/responder-client.d.ts.map +1 -0
- package/dist/client/responder-client.js +72 -0
- package/dist/client/responder-matcher.d.ts +49 -0
- package/dist/client/responder-matcher.d.ts.map +1 -0
- package/dist/client/responder-matcher.js +226 -0
- package/dist/client/server-client.d.ts +124 -0
- package/dist/client/server-client.d.ts.map +1 -0
- package/dist/client/server-client.js +266 -0
- package/dist/client/timeout-manager.d.ts +47 -0
- package/dist/client/timeout-manager.d.ts.map +1 -0
- package/dist/client/timeout-manager.js +77 -0
- package/dist/config.d.ts +20 -0
- package/dist/config.d.ts.map +1 -0
- package/dist/config.js +93 -0
- package/dist/harness/index.d.ts +4 -0
- package/dist/harness/index.d.ts.map +1 -0
- package/dist/harness/index.js +2 -0
- package/dist/harness/interaction-provider.d.ts +71 -0
- package/dist/harness/interaction-provider.d.ts.map +1 -0
- package/dist/harness/interaction-provider.js +124 -0
- package/dist/harness/routing-rules.d.ts +7 -0
- package/dist/harness/routing-rules.d.ts.map +1 -0
- package/dist/harness/routing-rules.js +37 -0
- package/dist/index.d.ts +19 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +26 -0
- package/dist/mcp/backend-resolver.d.ts +43 -0
- package/dist/mcp/backend-resolver.d.ts.map +1 -0
- package/dist/mcp/backend-resolver.js +111 -0
- package/dist/mcp/http-transport.d.ts +37 -0
- package/dist/mcp/http-transport.d.ts.map +1 -0
- package/dist/mcp/http-transport.js +103 -0
- package/dist/mcp/index.d.ts +14 -0
- package/dist/mcp/index.d.ts.map +1 -0
- package/dist/mcp/index.js +11 -0
- package/dist/mcp/server.d.ts +20 -0
- package/dist/mcp/server.d.ts.map +1 -0
- package/dist/mcp/server.js +121 -0
- package/dist/mcp/tools/answer-breakpoint.d.ts +32 -0
- package/dist/mcp/tools/answer-breakpoint.d.ts.map +1 -0
- package/dist/mcp/tools/answer-breakpoint.js +45 -0
- package/dist/mcp/tools/ask-breakpoint.d.ts +58 -0
- package/dist/mcp/tools/ask-breakpoint.d.ts.map +1 -0
- package/dist/mcp/tools/ask-breakpoint.js +78 -0
- package/dist/mcp/tools/check-status.d.ts +16 -0
- package/dist/mcp/tools/check-status.d.ts.map +1 -0
- package/dist/mcp/tools/check-status.js +18 -0
- package/dist/mcp/tools/claim-breakpoint.d.ts +18 -0
- package/dist/mcp/tools/claim-breakpoint.d.ts.map +1 -0
- package/dist/mcp/tools/claim-breakpoint.js +28 -0
- package/dist/mcp/tools/list-breakpoints.d.ts +16 -0
- package/dist/mcp/tools/list-breakpoints.d.ts.map +1 -0
- package/dist/mcp/tools/list-breakpoints.js +14 -0
- package/dist/mcp/tools/list-responders.d.ts +18 -0
- package/dist/mcp/tools/list-responders.d.ts.map +1 -0
- package/dist/mcp/tools/list-responders.js +37 -0
- package/dist/mcp/tools/poll-breakpoints.d.ts +18 -0
- package/dist/mcp/tools/poll-breakpoints.d.ts.map +1 -0
- package/dist/mcp/tools/poll-breakpoints.js +36 -0
- package/dist/mcp/tools/verify-answer.d.ts +16 -0
- package/dist/mcp/tools/verify-answer.d.ts.map +1 -0
- package/dist/mcp/tools/verify-answer.js +38 -0
- package/dist/proven/index.d.ts +5 -0
- package/dist/proven/index.d.ts.map +1 -0
- package/dist/proven/index.js +3 -0
- package/dist/proven/keys.d.ts +33 -0
- package/dist/proven/keys.d.ts.map +1 -0
- package/dist/proven/keys.js +117 -0
- package/dist/proven/sign.d.ts +16 -0
- package/dist/proven/sign.d.ts.map +1 -0
- package/dist/proven/sign.js +60 -0
- package/dist/proven/types.d.ts +26 -0
- package/dist/proven/types.d.ts.map +1 -0
- package/dist/proven/types.js +5 -0
- package/dist/proven/verify.d.ts +6 -0
- package/dist/proven/verify.d.ts.map +1 -0
- package/dist/proven/verify.js +58 -0
- package/dist/types.d.ts +4034 -0
- package/dist/types.d.ts.map +1 -0
- package/dist/types.js +244 -0
- package/package.json +86 -0
- package/responder/README.md +42 -0
- package/responder/backend-responder.json +9 -0
- package/responder/devops-responder.json +9 -0
- package/responder/frontend-responder.json +9 -0
- package/responder/schema.json +52 -0
|
@@ -0,0 +1,78 @@
|
|
|
1
|
+
import { Command } from "commander";
|
|
2
|
+
import { ResponderClient, } from "../../client/index.js";
|
|
3
|
+
import { formatTable, printError } from "../output.js";
|
|
4
|
+
import { createCliServerClient } from "../client-config.js";
|
|
5
|
+
export function createResponderLoopCommand() {
|
|
6
|
+
const cmd = new Command("responder-loop")
|
|
7
|
+
.description("Start a polling loop to check for new breakpoints")
|
|
8
|
+
.requiredOption("-e, --responder <responderId>", "Responder ID")
|
|
9
|
+
.option("-i, --interval <seconds>", "Polling interval in seconds", "30")
|
|
10
|
+
.option("--once", "Check once and exit (for agent integration)", false)
|
|
11
|
+
.action(async (opts, command) => {
|
|
12
|
+
const allOpts = command.optsWithGlobals();
|
|
13
|
+
const localOpts = opts;
|
|
14
|
+
const jsonMode = allOpts.json === true;
|
|
15
|
+
try {
|
|
16
|
+
const client = await createCliServerClient({
|
|
17
|
+
serverUrl: allOpts.serverUrl,
|
|
18
|
+
authToken: allOpts.authToken,
|
|
19
|
+
});
|
|
20
|
+
const responderClient = new ResponderClient(client, localOpts.responder);
|
|
21
|
+
const intervalMs = parseInt(localOpts.interval ?? "30", 10) * 1000;
|
|
22
|
+
if (localOpts.once) {
|
|
23
|
+
// Single check mode
|
|
24
|
+
const breakpoints = await responderClient.fetchPendingBreakpoints();
|
|
25
|
+
displayBreakpoints(breakpoints, jsonMode);
|
|
26
|
+
return;
|
|
27
|
+
}
|
|
28
|
+
// Continuous polling mode
|
|
29
|
+
if (!jsonMode) {
|
|
30
|
+
console.log(`Starting responder loop for ${localOpts.responder} (interval: ${localOpts.interval ?? "30"}s)`);
|
|
31
|
+
console.log("Press Ctrl+C to stop.\n");
|
|
32
|
+
}
|
|
33
|
+
const stop = responderClient.startPollingLoop((breakpoints) => {
|
|
34
|
+
displayBreakpoints(breakpoints, jsonMode);
|
|
35
|
+
}, intervalMs);
|
|
36
|
+
// Handle graceful shutdown
|
|
37
|
+
const shutdown = () => {
|
|
38
|
+
stop();
|
|
39
|
+
if (!jsonMode) {
|
|
40
|
+
console.log("\nResponder loop stopped.");
|
|
41
|
+
}
|
|
42
|
+
process.exit(0);
|
|
43
|
+
};
|
|
44
|
+
process.on("SIGTERM", shutdown);
|
|
45
|
+
process.on("SIGINT", shutdown);
|
|
46
|
+
// Keep the process alive
|
|
47
|
+
await new Promise(() => {
|
|
48
|
+
// This promise never resolves; the process is kept alive
|
|
49
|
+
// until SIGTERM/SIGINT is received.
|
|
50
|
+
});
|
|
51
|
+
}
|
|
52
|
+
catch (error) {
|
|
53
|
+
printError(error, jsonMode);
|
|
54
|
+
process.exitCode = 1;
|
|
55
|
+
}
|
|
56
|
+
});
|
|
57
|
+
return cmd;
|
|
58
|
+
}
|
|
59
|
+
function displayBreakpoints(breakpoints, jsonMode) {
|
|
60
|
+
if (jsonMode) {
|
|
61
|
+
console.log(JSON.stringify(breakpoints, null, 2));
|
|
62
|
+
return;
|
|
63
|
+
}
|
|
64
|
+
if (breakpoints.length === 0) {
|
|
65
|
+
console.log("No pending breakpoints.");
|
|
66
|
+
return;
|
|
67
|
+
}
|
|
68
|
+
console.log(`Found ${breakpoints.length} pending breakpoint(s):\n`);
|
|
69
|
+
const rows = breakpoints.map((b) => [
|
|
70
|
+
b.id,
|
|
71
|
+
b.status,
|
|
72
|
+
b.text.length > 60 ? b.text.substring(0, 57) + "..." : b.text,
|
|
73
|
+
b.routing.strategy,
|
|
74
|
+
b.createdAt,
|
|
75
|
+
]);
|
|
76
|
+
console.log(formatTable(rows, ["ID", "Status", "Breakpoint", "Strategy", "Created"]));
|
|
77
|
+
console.log("");
|
|
78
|
+
}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"responders.d.ts","sourceRoot":"","sources":["../../../src/cli/commands/responders.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAC;AAgBpC,wBAAgB,uBAAuB,IAAI,OAAO,CA6EjD"}
|
|
@@ -0,0 +1,74 @@
|
|
|
1
|
+
import { Command } from "commander";
|
|
2
|
+
import { ResponderMatcher } from "../../client/index.js";
|
|
3
|
+
import { formatResponder, formatTable, printError } from "../output.js";
|
|
4
|
+
export function createRespondersCommand() {
|
|
5
|
+
const cmd = new Command("responders").description("Manage and view responder profiles");
|
|
6
|
+
cmd
|
|
7
|
+
.command("list")
|
|
8
|
+
.description("List available responders")
|
|
9
|
+
.option("-d, --domain <domain>", "Filter by domain")
|
|
10
|
+
.action(async (opts, command) => {
|
|
11
|
+
const allOpts = command.optsWithGlobals();
|
|
12
|
+
const localOpts = opts;
|
|
13
|
+
const jsonMode = allOpts.json === true;
|
|
14
|
+
try {
|
|
15
|
+
const matcher = new ResponderMatcher({
|
|
16
|
+
responderDir: allOpts.responderDir,
|
|
17
|
+
repoRoot: allOpts.repoRoot,
|
|
18
|
+
configRoot: allOpts.configRoot,
|
|
19
|
+
});
|
|
20
|
+
const responders = await matcher.loadResponders();
|
|
21
|
+
let filtered = responders;
|
|
22
|
+
if (localOpts.domain) {
|
|
23
|
+
const domain = localOpts.domain.toLowerCase();
|
|
24
|
+
filtered = responders.filter((r) => r.domains.some((d) => d.toLowerCase().includes(domain)));
|
|
25
|
+
}
|
|
26
|
+
if (jsonMode) {
|
|
27
|
+
console.log(JSON.stringify(filtered, null, 2));
|
|
28
|
+
}
|
|
29
|
+
else if (filtered.length === 0) {
|
|
30
|
+
console.log("No responders found.");
|
|
31
|
+
}
|
|
32
|
+
else {
|
|
33
|
+
const rows = filtered.map((r) => [
|
|
34
|
+
r.id,
|
|
35
|
+
r.name,
|
|
36
|
+
r.title,
|
|
37
|
+
r.availability ? "yes" : "no",
|
|
38
|
+
r.domains.join(", "),
|
|
39
|
+
]);
|
|
40
|
+
console.log(formatTable(rows, ["ID", "Name", "Title", "Available", "Domains"]));
|
|
41
|
+
}
|
|
42
|
+
}
|
|
43
|
+
catch (error) {
|
|
44
|
+
printError(error, jsonMode);
|
|
45
|
+
process.exitCode = 1;
|
|
46
|
+
}
|
|
47
|
+
});
|
|
48
|
+
cmd
|
|
49
|
+
.command("show")
|
|
50
|
+
.description("Show responder profile details")
|
|
51
|
+
.argument("<responderId>", "Responder ID")
|
|
52
|
+
.action(async (responderId, _opts, command) => {
|
|
53
|
+
const allOpts = command.optsWithGlobals();
|
|
54
|
+
const jsonMode = allOpts.json === true;
|
|
55
|
+
try {
|
|
56
|
+
const matcher = new ResponderMatcher({
|
|
57
|
+
responderDir: allOpts.responderDir,
|
|
58
|
+
repoRoot: allOpts.repoRoot,
|
|
59
|
+
configRoot: allOpts.configRoot,
|
|
60
|
+
});
|
|
61
|
+
const responders = await matcher.loadResponders();
|
|
62
|
+
const responder = responders.find((r) => r.id === responderId);
|
|
63
|
+
if (!responder) {
|
|
64
|
+
throw new Error(`Responder not found: ${responderId}`);
|
|
65
|
+
}
|
|
66
|
+
console.log(formatResponder(responder, jsonMode));
|
|
67
|
+
}
|
|
68
|
+
catch (error) {
|
|
69
|
+
printError(error, jsonMode);
|
|
70
|
+
process.exitCode = 1;
|
|
71
|
+
}
|
|
72
|
+
});
|
|
73
|
+
return cmd;
|
|
74
|
+
}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"server.d.ts","sourceRoot":"","sources":["../../../src/cli/commands/server.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAC;AAWpC,wBAAgB,mBAAmB,IAAI,OAAO,CAoC7C"}
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
import { Command } from "commander";
|
|
2
|
+
import { printError } from "../output.js";
|
|
3
|
+
export function createServerCommand() {
|
|
4
|
+
const cmd = new Command("server").description("Server management commands");
|
|
5
|
+
cmd
|
|
6
|
+
.command("start")
|
|
7
|
+
.description("Start the tasks-mux MCP server (stdio)")
|
|
8
|
+
.action(async (_opts, command) => {
|
|
9
|
+
const allOpts = command.optsWithGlobals();
|
|
10
|
+
const jsonMode = allOpts.json === true;
|
|
11
|
+
try {
|
|
12
|
+
if (allOpts.responderDir) {
|
|
13
|
+
process.env.BMUX_RESPONDER_DIR = allOpts.responderDir;
|
|
14
|
+
}
|
|
15
|
+
if (allOpts.repoRoot) {
|
|
16
|
+
process.env.BMUX_REPO_ROOT = allOpts.repoRoot;
|
|
17
|
+
}
|
|
18
|
+
if (allOpts.configRoot) {
|
|
19
|
+
process.env.BMUX_CONFIG_ROOT = allOpts.configRoot;
|
|
20
|
+
}
|
|
21
|
+
// Dynamically import the MCP server to avoid heavy dependency at load time
|
|
22
|
+
const { startBreakpointMcpServer } = await import("../../mcp/index.js");
|
|
23
|
+
if (!jsonMode) {
|
|
24
|
+
console.error("Starting tasks-mux MCP server on stdio...");
|
|
25
|
+
}
|
|
26
|
+
await startBreakpointMcpServer();
|
|
27
|
+
}
|
|
28
|
+
catch (error) {
|
|
29
|
+
printError(error, jsonMode);
|
|
30
|
+
process.exitCode = 1;
|
|
31
|
+
}
|
|
32
|
+
});
|
|
33
|
+
return cmd;
|
|
34
|
+
}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/cli/index.ts"],"names":[],"mappings":";AAIA,OAAO,EAAE,aAAa,EAAE,MAAM,cAAc,CAAC;AAC7C,eAAO,MAAM,WAAW,UAAU,CAAC"}
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
import { createProgram } from "./program.js";
|
|
3
|
+
export { createProgram } from "./program.js";
|
|
4
|
+
export const CLI_VERSION = "5.0.0";
|
|
5
|
+
const program = createProgram();
|
|
6
|
+
program.parseAsync(process.argv).catch((err) => {
|
|
7
|
+
console.error(err);
|
|
8
|
+
process.exit(1);
|
|
9
|
+
});
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
import type { Breakpoint, BreakpointAnswer, ResponderProfile } from "../types.js";
|
|
2
|
+
/**
|
|
3
|
+
* Format a breakpoint for display.
|
|
4
|
+
*/
|
|
5
|
+
export declare function formatBreakpoint(breakpoint: Breakpoint, jsonMode: boolean): string;
|
|
6
|
+
/**
|
|
7
|
+
* Format an answer for display.
|
|
8
|
+
*/
|
|
9
|
+
export declare function formatAnswer(answer: BreakpointAnswer, jsonMode: boolean): string;
|
|
10
|
+
/**
|
|
11
|
+
* Format a responder profile for display.
|
|
12
|
+
*/
|
|
13
|
+
export declare function formatResponder(responder: ResponderProfile, jsonMode: boolean): string;
|
|
14
|
+
/**
|
|
15
|
+
* Format data as a simple table.
|
|
16
|
+
*/
|
|
17
|
+
export declare function formatTable(rows: string[][], headers: string[]): string;
|
|
18
|
+
/**
|
|
19
|
+
* Print output, handling JSON mode.
|
|
20
|
+
*/
|
|
21
|
+
export declare function printOutput(data: unknown, jsonMode: boolean): void;
|
|
22
|
+
/**
|
|
23
|
+
* Print an error, handling JSON mode.
|
|
24
|
+
*/
|
|
25
|
+
export declare function printError(error: unknown, jsonMode: boolean): void;
|
|
26
|
+
//# sourceMappingURL=output.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"output.d.ts","sourceRoot":"","sources":["../../src/cli/output.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,UAAU,EAAE,gBAAgB,EAAE,gBAAgB,EAAE,MAAM,aAAa,CAAC;AAmBlF;;GAEG;AACH,wBAAgB,gBAAgB,CAAC,UAAU,EAAE,UAAU,EAAE,QAAQ,EAAE,OAAO,GAAG,MAAM,CAuBlF;AAED;;GAEG;AACH,wBAAgB,YAAY,CAAC,MAAM,EAAE,gBAAgB,EAAE,QAAQ,EAAE,OAAO,GAAG,MAAM,CA8BhF;AAED;;GAEG;AACH,wBAAgB,eAAe,CAAC,SAAS,EAAE,gBAAgB,EAAE,QAAQ,EAAE,OAAO,GAAG,MAAM,CAqBtF;AAED;;GAEG;AACH,wBAAgB,WAAW,CAAC,IAAI,EAAE,MAAM,EAAE,EAAE,EAAE,OAAO,EAAE,MAAM,EAAE,GAAG,MAAM,CA2BvE;AAED;;GAEG;AACH,wBAAgB,WAAW,CAAC,IAAI,EAAE,OAAO,EAAE,QAAQ,EAAE,OAAO,GAAG,IAAI,CAQlE;AAED;;GAEG;AACH,wBAAgB,UAAU,CAAC,KAAK,EAAE,OAAO,EAAE,QAAQ,EAAE,OAAO,GAAG,IAAI,CAQlE"}
|
|
@@ -0,0 +1,143 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Format a duration in milliseconds as a human-readable string.
|
|
3
|
+
*/
|
|
4
|
+
function formatDuration(ms) {
|
|
5
|
+
if (ms < 1000)
|
|
6
|
+
return `${ms}ms`;
|
|
7
|
+
const seconds = Math.floor(ms / 1000);
|
|
8
|
+
if (seconds < 60)
|
|
9
|
+
return `${seconds}s`;
|
|
10
|
+
const minutes = Math.floor(seconds / 60);
|
|
11
|
+
const remainingSeconds = seconds % 60;
|
|
12
|
+
if (minutes < 60) {
|
|
13
|
+
return remainingSeconds > 0 ? `${minutes}m ${remainingSeconds}s` : `${minutes}m`;
|
|
14
|
+
}
|
|
15
|
+
const hours = Math.floor(minutes / 60);
|
|
16
|
+
const remainingMinutes = minutes % 60;
|
|
17
|
+
return remainingMinutes > 0 ? `${hours}h ${remainingMinutes}m` : `${hours}h`;
|
|
18
|
+
}
|
|
19
|
+
/**
|
|
20
|
+
* Format a breakpoint for display.
|
|
21
|
+
*/
|
|
22
|
+
export function formatBreakpoint(breakpoint, jsonMode) {
|
|
23
|
+
if (jsonMode) {
|
|
24
|
+
return JSON.stringify(breakpoint, null, 2);
|
|
25
|
+
}
|
|
26
|
+
const lines = [];
|
|
27
|
+
lines.push(`Breakpoint: ${breakpoint.id}`);
|
|
28
|
+
lines.push(`Status: ${breakpoint.status}`);
|
|
29
|
+
lines.push(`Text: ${breakpoint.text}`);
|
|
30
|
+
lines.push(`Strategy: ${breakpoint.routing.strategy}`);
|
|
31
|
+
lines.push(`Responders: ${breakpoint.routing.targetResponders.join(", ") || "(none)"}`);
|
|
32
|
+
lines.push(`Created: ${breakpoint.createdAt}`);
|
|
33
|
+
lines.push(`Expires: ${breakpoint.expiresAt}`);
|
|
34
|
+
if (breakpoint.context.tags.length > 0) {
|
|
35
|
+
lines.push(`Tags: ${breakpoint.context.tags.join(", ")}`);
|
|
36
|
+
}
|
|
37
|
+
if (breakpoint.answers.length > 0) {
|
|
38
|
+
lines.push(`Answers: ${breakpoint.answers.length}`);
|
|
39
|
+
}
|
|
40
|
+
return lines.join("\n");
|
|
41
|
+
}
|
|
42
|
+
/**
|
|
43
|
+
* Format an answer for display.
|
|
44
|
+
*/
|
|
45
|
+
export function formatAnswer(answer, jsonMode) {
|
|
46
|
+
if (jsonMode) {
|
|
47
|
+
return JSON.stringify(answer, null, 2);
|
|
48
|
+
}
|
|
49
|
+
const lines = [];
|
|
50
|
+
lines.push(`Answer: ${answer.id}`);
|
|
51
|
+
lines.push(`Breakpoint: ${answer.breakpointId}`);
|
|
52
|
+
lines.push(`Responder: ${answer.responderName} (${answer.responderId})`);
|
|
53
|
+
lines.push(`Confidence: ${answer.confidence}%`);
|
|
54
|
+
lines.push(`Answered: ${answer.answeredAt}`);
|
|
55
|
+
lines.push(`---`);
|
|
56
|
+
lines.push(answer.text);
|
|
57
|
+
if (answer.references.length > 0) {
|
|
58
|
+
lines.push(`---`);
|
|
59
|
+
lines.push(`References:`);
|
|
60
|
+
for (const ref of answer.references) {
|
|
61
|
+
lines.push(` - ${ref}`);
|
|
62
|
+
}
|
|
63
|
+
}
|
|
64
|
+
if (answer.followUpQuestions.length > 0) {
|
|
65
|
+
lines.push(`Follow-up questions:`);
|
|
66
|
+
for (const q of answer.followUpQuestions) {
|
|
67
|
+
lines.push(` - ${q}`);
|
|
68
|
+
}
|
|
69
|
+
}
|
|
70
|
+
return lines.join("\n");
|
|
71
|
+
}
|
|
72
|
+
/**
|
|
73
|
+
* Format a responder profile for display.
|
|
74
|
+
*/
|
|
75
|
+
export function formatResponder(responder, jsonMode) {
|
|
76
|
+
if (jsonMode) {
|
|
77
|
+
return JSON.stringify(responder, null, 2);
|
|
78
|
+
}
|
|
79
|
+
const lines = [];
|
|
80
|
+
lines.push(`Responder: ${responder.id}`);
|
|
81
|
+
lines.push(`Name: ${responder.name}`);
|
|
82
|
+
lines.push(`Title: ${responder.title}`);
|
|
83
|
+
lines.push(`Available: ${responder.availability ? "yes" : "no"}`);
|
|
84
|
+
lines.push(`Response SLA: ${formatDuration(responder.responseTimeSla)}`);
|
|
85
|
+
if (responder.domains.length > 0) {
|
|
86
|
+
lines.push(`Domains: ${responder.domains.join(", ")}`);
|
|
87
|
+
}
|
|
88
|
+
if (responder.tags.length > 0) {
|
|
89
|
+
lines.push(`Tags: ${responder.tags.join(", ")}`);
|
|
90
|
+
}
|
|
91
|
+
return lines.join("\n");
|
|
92
|
+
}
|
|
93
|
+
/**
|
|
94
|
+
* Format data as a simple table.
|
|
95
|
+
*/
|
|
96
|
+
export function formatTable(rows, headers) {
|
|
97
|
+
if (rows.length === 0) {
|
|
98
|
+
return "(no results)";
|
|
99
|
+
}
|
|
100
|
+
// Calculate column widths
|
|
101
|
+
const widths = headers.map((h, i) => {
|
|
102
|
+
const maxDataWidth = rows.reduce((max, row) => Math.max(max, (row[i] ?? "").length), 0);
|
|
103
|
+
return Math.max(h.length, maxDataWidth);
|
|
104
|
+
});
|
|
105
|
+
const pad = (str, width) => str.padEnd(width);
|
|
106
|
+
const lines = [];
|
|
107
|
+
// Header row
|
|
108
|
+
lines.push(headers.map((h, i) => pad(h, widths[i])).join(" "));
|
|
109
|
+
// Separator
|
|
110
|
+
lines.push(widths.map((w) => "-".repeat(w)).join(" "));
|
|
111
|
+
// Data rows
|
|
112
|
+
for (const row of rows) {
|
|
113
|
+
lines.push(row.map((cell, i) => pad(cell ?? "", widths[i])).join(" "));
|
|
114
|
+
}
|
|
115
|
+
return lines.join("\n");
|
|
116
|
+
}
|
|
117
|
+
/**
|
|
118
|
+
* Print output, handling JSON mode.
|
|
119
|
+
*/
|
|
120
|
+
export function printOutput(data, jsonMode) {
|
|
121
|
+
if (jsonMode) {
|
|
122
|
+
console.log(JSON.stringify(data, null, 2));
|
|
123
|
+
}
|
|
124
|
+
else if (typeof data === "string") {
|
|
125
|
+
console.log(data);
|
|
126
|
+
}
|
|
127
|
+
else {
|
|
128
|
+
console.log(data);
|
|
129
|
+
}
|
|
130
|
+
}
|
|
131
|
+
/**
|
|
132
|
+
* Print an error, handling JSON mode.
|
|
133
|
+
*/
|
|
134
|
+
export function printError(error, jsonMode) {
|
|
135
|
+
if (jsonMode) {
|
|
136
|
+
const message = error instanceof Error ? error.message : String(error);
|
|
137
|
+
console.error(JSON.stringify({ error: message }));
|
|
138
|
+
}
|
|
139
|
+
else {
|
|
140
|
+
const message = error instanceof Error ? error.message : String(error);
|
|
141
|
+
console.error(`Error: ${message}`);
|
|
142
|
+
}
|
|
143
|
+
}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"program.d.ts","sourceRoot":"","sources":["../../src/cli/program.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAC;AASpC;;GAEG;AACH,wBAAgB,aAAa,IAAI,OAAO,CAmCvC"}
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
import { Command } from "commander";
|
|
2
|
+
import { createAskCommand } from "./commands/ask.js";
|
|
3
|
+
import { createRespondersCommand } from "./commands/responders.js";
|
|
4
|
+
import { createBreakpointsCommand } from "./commands/breakpoints.js";
|
|
5
|
+
import { createServerCommand } from "./commands/server.js";
|
|
6
|
+
import { createResponderLoopCommand } from "./commands/responder-loop.js";
|
|
7
|
+
import { createAuthCommand } from "./commands/auth.js";
|
|
8
|
+
import { DEFAULT_BMUX_SERVER_URL } from "../client/index.js";
|
|
9
|
+
/**
|
|
10
|
+
* Create and configure the main CLI program.
|
|
11
|
+
*/
|
|
12
|
+
export function createProgram() {
|
|
13
|
+
const program = new Command();
|
|
14
|
+
program
|
|
15
|
+
.name("tasks-mux")
|
|
16
|
+
.version("5.0.0")
|
|
17
|
+
.description("CLI for Breakpoints Mux - route breakpoints to domain responders")
|
|
18
|
+
.option("--server-url <url>", `Server URL (defaults to ${DEFAULT_BMUX_SERVER_URL})`)
|
|
19
|
+
.option("--auth-token <token>", "Bearer token for BMUX API access")
|
|
20
|
+
.option("--json", "Output in JSON format", false)
|
|
21
|
+
.option("--responder-dir <path>", "Responder profile directory, relative to the associated repo or config root when not absolute")
|
|
22
|
+
.option("--repo-root <path>", "Associated repository root for resolving .a5c-based configuration")
|
|
23
|
+
.option("--config-root <path>", "Associated configuration root (.a5c) for resolving repo-scoped responder config");
|
|
24
|
+
// Register subcommands
|
|
25
|
+
program.addCommand(createAskCommand());
|
|
26
|
+
program.addCommand(createRespondersCommand());
|
|
27
|
+
program.addCommand(createBreakpointsCommand());
|
|
28
|
+
program.addCommand(createServerCommand());
|
|
29
|
+
program.addCommand(createResponderLoopCommand());
|
|
30
|
+
program.addCommand(createAuthCommand());
|
|
31
|
+
return program;
|
|
32
|
+
}
|
|
@@ -0,0 +1,52 @@
|
|
|
1
|
+
import type { BreakpointWaitResult } from "../types.js";
|
|
2
|
+
import type { BreakpointBackend } from "../backend.js";
|
|
3
|
+
import { ServerClient } from "./server-client.js";
|
|
4
|
+
/**
|
|
5
|
+
* Options for waiting for an answer via the client-side poller.
|
|
6
|
+
*/
|
|
7
|
+
export interface PollerWaitForAnswerOptions {
|
|
8
|
+
/** Maximum time to wait in milliseconds. Defaults to DEFAULT_TIMEOUT_MS (30 min). */
|
|
9
|
+
timeoutMs?: number;
|
|
10
|
+
/** Polling interval in milliseconds when using HTTP polling. Defaults to DEFAULT_POLL_INTERVAL_MS (3s). */
|
|
11
|
+
pollIntervalMs?: number;
|
|
12
|
+
/** Whether to use SSE for real-time updates. Falls back to polling if false or on error. */
|
|
13
|
+
useSSE?: boolean;
|
|
14
|
+
/** AbortSignal for external cancellation. */
|
|
15
|
+
signal?: AbortSignal;
|
|
16
|
+
}
|
|
17
|
+
/**
|
|
18
|
+
* Waits for answers to breakpoints using either SSE streaming or HTTP polling.
|
|
19
|
+
*
|
|
20
|
+
* Accepts either a ServerClient (legacy) or a BreakpointBackend.
|
|
21
|
+
* When a BreakpointBackend is passed, delegates to its waitForAnswer method.
|
|
22
|
+
* When a ServerClient is passed, uses the existing SSE/polling logic.
|
|
23
|
+
*/
|
|
24
|
+
export declare class AnswerPoller {
|
|
25
|
+
private readonly client;
|
|
26
|
+
private readonly backend;
|
|
27
|
+
constructor(clientOrBackend: ServerClient | BreakpointBackend);
|
|
28
|
+
/**
|
|
29
|
+
* Wait for an answer to a breakpoint.
|
|
30
|
+
*
|
|
31
|
+
* Resolves when:
|
|
32
|
+
* - An answer is received (status becomes "answered" or "completed")
|
|
33
|
+
* - The breakpoint expires or is cancelled
|
|
34
|
+
* - The timeout is reached
|
|
35
|
+
* - The operation is aborted via AbortSignal
|
|
36
|
+
*/
|
|
37
|
+
waitForAnswer(breakpointId: string, options?: PollerWaitForAnswerOptions): Promise<BreakpointWaitResult>;
|
|
38
|
+
/**
|
|
39
|
+
* Wait for an answer using SSE streaming.
|
|
40
|
+
*/
|
|
41
|
+
private waitViaSSE;
|
|
42
|
+
/**
|
|
43
|
+
* Wait for an answer using HTTP polling.
|
|
44
|
+
*/
|
|
45
|
+
private waitViaPolling;
|
|
46
|
+
/**
|
|
47
|
+
* Fetch the current breakpoint state and build a BreakpointWaitResult.
|
|
48
|
+
*/
|
|
49
|
+
private buildResult;
|
|
50
|
+
private breakpointToResult;
|
|
51
|
+
}
|
|
52
|
+
//# sourceMappingURL=answer-poller.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"answer-poller.d.ts","sourceRoot":"","sources":["../../src/client/answer-poller.ts"],"names":[],"mappings":"AAIA,OAAO,KAAK,EAAc,oBAAoB,EAAE,MAAM,aAAa,CAAC;AACpE,OAAO,KAAK,EAAE,iBAAiB,EAAE,MAAM,eAAe,CAAC;AACvD,OAAO,EAAE,YAAY,EAAE,MAAM,oBAAoB,CAAC;AAElD;;GAEG;AACH,MAAM,WAAW,0BAA0B;IACzC,qFAAqF;IACrF,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,2GAA2G;IAC3G,cAAc,CAAC,EAAE,MAAM,CAAC;IACxB,4FAA4F;IAC5F,MAAM,CAAC,EAAE,OAAO,CAAC;IACjB,6CAA6C;IAC7C,MAAM,CAAC,EAAE,WAAW,CAAC;CACtB;AAED;;;;;;GAMG;AACH,qBAAa,YAAY;IACvB,OAAO,CAAC,QAAQ,CAAC,MAAM,CAAsB;IAC7C,OAAO,CAAC,QAAQ,CAAC,OAAO,CAA2B;gBAEvC,eAAe,EAAE,YAAY,GAAG,iBAAiB;IAU7D;;;;;;;;OAQG;IACG,aAAa,CACjB,YAAY,EAAE,MAAM,EACpB,OAAO,GAAE,0BAA+B,GACvC,OAAO,CAAC,oBAAoB,CAAC;IAmDhC;;OAEG;IACH,OAAO,CAAC,UAAU;IAkElB;;OAEG;YACW,cAAc;IA+B5B;;OAEG;YACW,WAAW;IA6BzB,OAAO,CAAC,kBAAkB;CAe3B"}
|