agent-relay 8.8.5 → 8.9.1

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.
Files changed (56) hide show
  1. package/dist/cli/agent-relay-mcp.d.ts +2 -53
  2. package/dist/cli/agent-relay-mcp.d.ts.map +1 -1
  3. package/dist/cli/agent-relay-mcp.js +11 -943
  4. package/dist/cli/agent-relay-mcp.js.map +1 -1
  5. package/dist/cli/commands/fleet.d.ts.map +1 -1
  6. package/dist/cli/commands/fleet.js +86 -13
  7. package/dist/cli/commands/fleet.js.map +1 -1
  8. package/dist/cli/lib/broker-dashboard.d.ts +12 -0
  9. package/dist/cli/lib/broker-dashboard.d.ts.map +1 -0
  10. package/dist/cli/lib/broker-dashboard.js +431 -0
  11. package/dist/cli/lib/broker-dashboard.js.map +1 -0
  12. package/dist/cli/lib/broker-lifecycle.d.ts.map +1 -1
  13. package/dist/cli/lib/broker-lifecycle.js +1 -428
  14. package/dist/cli/lib/broker-lifecycle.js.map +1 -1
  15. package/dist/cli/mcp/action-schema.d.ts +20 -0
  16. package/dist/cli/mcp/action-schema.d.ts.map +1 -0
  17. package/dist/cli/mcp/action-schema.js +132 -0
  18. package/dist/cli/mcp/action-schema.js.map +1 -0
  19. package/dist/cli/mcp/action-tools.d.ts +10 -0
  20. package/dist/cli/mcp/action-tools.d.ts.map +1 -0
  21. package/dist/cli/mcp/action-tools.js +114 -0
  22. package/dist/cli/mcp/action-tools.js.map +1 -0
  23. package/dist/cli/mcp/inbox.d.ts +9 -0
  24. package/dist/cli/mcp/inbox.d.ts.map +1 -0
  25. package/dist/cli/mcp/inbox.js +49 -0
  26. package/dist/cli/mcp/inbox.js.map +1 -0
  27. package/dist/cli/mcp/messaging-tools.d.ts +9 -0
  28. package/dist/cli/mcp/messaging-tools.d.ts.map +1 -0
  29. package/dist/cli/mcp/messaging-tools.js +315 -0
  30. package/dist/cli/mcp/messaging-tools.js.map +1 -0
  31. package/dist/cli/mcp/resources.d.ts +39 -0
  32. package/dist/cli/mcp/resources.d.ts.map +1 -0
  33. package/dist/cli/mcp/resources.js +158 -0
  34. package/dist/cli/mcp/resources.js.map +1 -0
  35. package/dist/cli/mcp/telemetry.d.ts +9 -0
  36. package/dist/cli/mcp/telemetry.d.ts.map +1 -0
  37. package/dist/cli/mcp/telemetry.js +176 -0
  38. package/dist/cli/mcp/telemetry.js.map +1 -0
  39. package/dist/cli/mcp/tool-results.d.ts +29 -0
  40. package/dist/cli/mcp/tool-results.d.ts.map +1 -0
  41. package/dist/cli/mcp/tool-results.js +39 -0
  42. package/dist/cli/mcp/tool-results.js.map +1 -0
  43. package/dist/cli/mcp/tool-shapes.d.ts +13 -0
  44. package/dist/cli/mcp/tool-shapes.d.ts.map +1 -0
  45. package/dist/cli/mcp/tool-shapes.js +16 -0
  46. package/dist/cli/mcp/tool-shapes.js.map +1 -0
  47. package/dist/cli/mcp/types.d.ts +38 -0
  48. package/dist/cli/mcp/types.d.ts.map +1 -0
  49. package/dist/cli/mcp/types.js +2 -0
  50. package/dist/cli/mcp/types.js.map +1 -0
  51. package/dist/cli/mcp/workspace.d.ts +10 -0
  52. package/dist/cli/mcp/workspace.d.ts.map +1 -0
  53. package/dist/cli/mcp/workspace.js +36 -0
  54. package/dist/cli/mcp/workspace.js.map +1 -0
  55. package/dist/index.cjs +47 -2
  56. package/package.json +8 -8
@@ -0,0 +1,176 @@
1
+ import { agentTokenRecoveryMessage, isInvalidAgentTokenError, isInvalidAgentTokenToolResult, } from '@agent-relay/sdk';
2
+ import { track } from '../telemetry/index.js';
3
+ import { errorClassName } from '../lib/telemetry-helpers.js';
4
+ import { formatInbox, SKIP_PIGGYBACK } from './inbox.js';
5
+ import { hasContentArray, invalidAgentTokenToolResult, isErrorToolResult } from './tool-results.js';
6
+ /**
7
+ * Owned tools that delegate to the actions surface (`actions.invoke(...)`)
8
+ * rather than the agents/messaging APIs. Together with the dynamic per-action
9
+ * tools (tracked via `actionToolNames`), these intentionally skip per-tool
10
+ * telemetry so the same underlying action is not counted differently depending
11
+ * on which MCP surface the caller used (e.g. `spawn` vs `invoke_action`).
12
+ */
13
+ const ACTION_ROUTED_TOOL_NAMES = new Set(['invoke_action', 'spawn']);
14
+ /**
15
+ * Coarse type/category metadata for the statically-registered ("owned") MCP
16
+ * tools. Action-routed calls (see `ACTION_ROUTED_TOOL_NAMES`) and the dynamic
17
+ * per-action tools surfaced from the actions registry are intentionally
18
+ * excluded from per-tool telemetry (see the skip in `enableInboxPiggyback`),
19
+ * so they have no entry.
20
+ */
21
+ const AGENT_RELAY_TOOL_CALL_METADATA = {
22
+ add_agent: { toolType: 'agent.create', toolCategory: 'spawn' },
23
+ remove_agent: { toolType: 'agent.release', toolCategory: 'release' },
24
+ list_actions: { toolType: 'action.list', toolCategory: 'action' },
25
+ submit_result: { toolType: 'result.submit', toolCategory: 'result' },
26
+ create_workspace: { toolType: 'workspace.create', toolCategory: 'workspace' },
27
+ set_workspace_key: { toolType: 'workspace.set_key', toolCategory: 'workspace' },
28
+ register_agent: { toolType: 'agent.register', toolCategory: 'agent' },
29
+ list_agents: { toolType: 'agent.list', toolCategory: 'agent' },
30
+ post_message: { toolType: 'message.post', toolCategory: 'message' },
31
+ send_dm: { toolType: 'message.dm', toolCategory: 'message' },
32
+ send_group_dm: { toolType: 'message.group_dm', toolCategory: 'message' },
33
+ list_dms: { toolType: 'message.dm_list', toolCategory: 'message' },
34
+ list_messages: { toolType: 'message.list', toolCategory: 'message' },
35
+ reply_to_thread: { toolType: 'message.reply', toolCategory: 'message' },
36
+ get_message_thread: { toolType: 'message.thread', toolCategory: 'message' },
37
+ search_messages: { toolType: 'message.search', toolCategory: 'message' },
38
+ create_channel: { toolType: 'channel.create', toolCategory: 'channel' },
39
+ list_channels: { toolType: 'channel.list', toolCategory: 'channel' },
40
+ join_channel: { toolType: 'channel.join', toolCategory: 'channel' },
41
+ leave_channel: { toolType: 'channel.leave', toolCategory: 'channel' },
42
+ set_channel_topic: { toolType: 'channel.set_topic', toolCategory: 'channel' },
43
+ archive_channel: { toolType: 'channel.archive', toolCategory: 'channel' },
44
+ invite_to_channel: { toolType: 'channel.invite', toolCategory: 'channel' },
45
+ add_reaction: { toolType: 'reaction.add', toolCategory: 'reaction' },
46
+ remove_reaction: { toolType: 'reaction.remove', toolCategory: 'reaction' },
47
+ check_inbox: { toolType: 'inbox.check', toolCategory: 'inbox' },
48
+ mark_message_read: { toolType: 'inbox.mark_read', toolCategory: 'inbox' },
49
+ get_message_readers: { toolType: 'inbox.reader_list', toolCategory: 'inbox' },
50
+ };
51
+ function agentRelayToolCallMetadata(name) {
52
+ const known = AGENT_RELAY_TOOL_CALL_METADATA[name];
53
+ return known ?? { toolType: name, toolCategory: 'tool' };
54
+ }
55
+ function trackAgentRelayToolCall(input) {
56
+ track('agent_relay_tool_call', {
57
+ tool_name: input.toolName,
58
+ tool_type: input.toolType,
59
+ tool_category: input.toolCategory,
60
+ transport: input.transport ?? 'unknown',
61
+ success: input.success,
62
+ duration_ms: Date.now() - input.startedAt,
63
+ ...(input.errorClass ? { error_class: input.errorClass } : {}),
64
+ });
65
+ }
66
+ function readAsIdentity(args) {
67
+ const [input] = args;
68
+ if (typeof input !== 'object' || input === null)
69
+ return undefined;
70
+ const as = input.as;
71
+ return typeof as === 'string' ? as : undefined;
72
+ }
73
+ /**
74
+ * Wrap `server.registerTool` so every owned tool emits `agent_relay_tool_call`
75
+ * telemetry, surfaces invalid-agent-token errors as recoverable results, and
76
+ * piggybacks a compact inbox summary onto successful results.
77
+ */
78
+ export function enableInboxPiggyback(mcpServer, getSession, getAgentClient, invalidateAgentToken, telemetryTransport, actionToolNames = new Set()) {
79
+ const original = mcpServer.registerTool.bind(mcpServer);
80
+ const mutableServer = mcpServer;
81
+ mutableServer.registerTool = (name, config, handler) => {
82
+ if (!handler) {
83
+ return original(name, config, handler);
84
+ }
85
+ const wrapped = async (...args) => {
86
+ const asIdentity = readAsIdentity(args);
87
+ const startedAt = Date.now();
88
+ // Action-routed calls (`invoke_action`, `spawn`, and the dynamic
89
+ // per-action tools) run through the actions surface and deliberately skip
90
+ // per-tool telemetry; only the owned tools emit `agent_relay_tool_call`.
91
+ const toolMetadata = !ACTION_ROUTED_TOOL_NAMES.has(name) && !actionToolNames.has(name)
92
+ ? agentRelayToolCallMetadata(name)
93
+ : undefined;
94
+ let result;
95
+ try {
96
+ result = await handler(...args);
97
+ }
98
+ catch (err) {
99
+ if (name !== 'register_agent' && isInvalidAgentTokenError(err)) {
100
+ invalidateAgentToken(asIdentity);
101
+ if (toolMetadata) {
102
+ trackAgentRelayToolCall({
103
+ toolName: name,
104
+ toolType: toolMetadata.toolType,
105
+ toolCategory: toolMetadata.toolCategory,
106
+ transport: telemetryTransport,
107
+ startedAt,
108
+ success: false,
109
+ errorClass: errorClassName(err) ?? 'InvalidAgentToken',
110
+ });
111
+ }
112
+ return invalidAgentTokenToolResult();
113
+ }
114
+ if (toolMetadata) {
115
+ trackAgentRelayToolCall({
116
+ toolName: name,
117
+ toolType: toolMetadata.toolType,
118
+ toolCategory: toolMetadata.toolCategory,
119
+ transport: telemetryTransport,
120
+ startedAt,
121
+ success: false,
122
+ errorClass: errorClassName(err),
123
+ });
124
+ }
125
+ throw err;
126
+ }
127
+ if (name !== 'register_agent' && isInvalidAgentTokenToolResult(result)) {
128
+ invalidateAgentToken(asIdentity);
129
+ if (toolMetadata) {
130
+ trackAgentRelayToolCall({
131
+ toolName: name,
132
+ toolType: toolMetadata.toolType,
133
+ toolCategory: toolMetadata.toolCategory,
134
+ transport: telemetryTransport,
135
+ startedAt,
136
+ success: false,
137
+ errorClass: 'InvalidAgentToken',
138
+ });
139
+ }
140
+ if (hasContentArray(result)) {
141
+ result.content.push({ type: 'text', text: agentTokenRecoveryMessage() });
142
+ }
143
+ return result;
144
+ }
145
+ if (!SKIP_PIGGYBACK.has(name) && getSession().agentToken && hasContentArray(result)) {
146
+ try {
147
+ const inbox = await getAgentClient(asIdentity).inbox();
148
+ const inboxText = formatInbox(inbox, asIdentity ?? getSession().agentName);
149
+ if (inboxText) {
150
+ result.content.push({ type: 'text', text: inboxText });
151
+ }
152
+ }
153
+ catch (err) {
154
+ if (isInvalidAgentTokenError(err)) {
155
+ invalidateAgentToken(asIdentity);
156
+ }
157
+ }
158
+ }
159
+ if (toolMetadata) {
160
+ const resultIsError = isErrorToolResult(result);
161
+ trackAgentRelayToolCall({
162
+ toolName: name,
163
+ toolType: toolMetadata.toolType,
164
+ toolCategory: toolMetadata.toolCategory,
165
+ transport: telemetryTransport,
166
+ startedAt,
167
+ success: !resultIsError,
168
+ ...(resultIsError ? { errorClass: 'ToolResultError' } : {}),
169
+ });
170
+ }
171
+ return result;
172
+ };
173
+ return original(name, config, wrapped);
174
+ };
175
+ }
176
+ //# sourceMappingURL=telemetry.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"telemetry.js","sourceRoot":"","sources":["../../../src/cli/mcp/telemetry.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,29 @@
1
+ import { z } from 'zod';
2
+ /** Permissive output schema for tools that return arbitrary JSON objects. */
3
+ export declare const jsonResult: z.ZodObject<{}, "passthrough", z.ZodTypeAny, z.objectOutputType<{}, z.ZodTypeAny, "passthrough">, z.objectInputType<{}, z.ZodTypeAny, "passthrough">>;
4
+ export type JsonToolResult = {
5
+ content: Array<{
6
+ type: 'text';
7
+ text: string;
8
+ }>;
9
+ structuredContent: Record<string, unknown>;
10
+ };
11
+ /** Wrap an arbitrary value as an MCP tool result with both text and structured content. */
12
+ export declare function jsonContent(value: unknown): JsonToolResult;
13
+ /** Wrap a human-readable message as an MCP tool result. */
14
+ export declare function textContent(message: string, structuredContent?: Record<string, unknown>): {
15
+ content: {
16
+ type: "text";
17
+ text: string;
18
+ }[];
19
+ structuredContent: Record<string, unknown>;
20
+ };
21
+ export declare function hasContentArray(value: unknown): value is {
22
+ content: Array<Record<string, unknown>>;
23
+ };
24
+ export declare function isErrorToolResult(value: unknown): boolean;
25
+ /** Standard MCP error result describing an invalid/expired agent token. */
26
+ export declare function invalidAgentTokenToolResult(): JsonToolResult & {
27
+ isError: true;
28
+ };
29
+ //# sourceMappingURL=tool-results.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"tool-results.d.ts","sourceRoot":"","sources":["../../../src/cli/mcp/tool-results.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AAExB,6EAA6E;AAC7E,eAAO,MAAM,UAAU,uJAA6B,CAAC;AAErD,MAAM,MAAM,cAAc,GAAG;IAC3B,OAAO,EAAE,KAAK,CAAC;QAAE,IAAI,EAAE,MAAM,CAAC;QAAC,IAAI,EAAE,MAAM,CAAA;KAAE,CAAC,CAAC;IAC/C,iBAAiB,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;CAC5C,CAAC;AAEF,2FAA2F;AAC3F,wBAAgB,WAAW,CAAC,KAAK,EAAE,OAAO,GAAG,cAAc,CAS1D;AAED,2DAA2D;AAC3D,wBAAgB,WAAW,CAAC,OAAO,EAAE,MAAM,EAAE,iBAAiB,GAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAe;;;;;;EAKpG;AAED,wBAAgB,eAAe,CAAC,KAAK,EAAE,OAAO,GAAG,KAAK,IAAI;IAAE,OAAO,EAAE,KAAK,CAAC,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC,CAAA;CAAE,CAIpG;AAED,wBAAgB,iBAAiB,CAAC,KAAK,EAAE,OAAO,GAAG,OAAO,CAEzD;AAED,2EAA2E;AAC3E,wBAAgB,2BAA2B,IAAI,cAAc,GAAG;IAAE,OAAO,EAAE,IAAI,CAAA;CAAE,CAShF"}
@@ -0,0 +1,39 @@
1
+ import { INVALID_AGENT_TOKEN_CODE, agentTokenRecoveryMessage } from '@agent-relay/sdk';
2
+ import { z } from 'zod';
3
+ /** Permissive output schema for tools that return arbitrary JSON objects. */
4
+ export const jsonResult = z.object({}).passthrough();
5
+ /** Wrap an arbitrary value as an MCP tool result with both text and structured content. */
6
+ export function jsonContent(value) {
7
+ const structuredContent = typeof value === 'object' && value !== null && !Array.isArray(value)
8
+ ? value
9
+ : { value };
10
+ return {
11
+ content: [{ type: 'text', text: JSON.stringify(value, null, 2) }],
12
+ structuredContent,
13
+ };
14
+ }
15
+ /** Wrap a human-readable message as an MCP tool result. */
16
+ export function textContent(message, structuredContent = { message }) {
17
+ return {
18
+ content: [{ type: 'text', text: message }],
19
+ structuredContent,
20
+ };
21
+ }
22
+ export function hasContentArray(value) {
23
+ return (typeof value === 'object' && value !== null && Array.isArray(value.content));
24
+ }
25
+ export function isErrorToolResult(value) {
26
+ return Boolean(value && typeof value === 'object' && value.isError === true);
27
+ }
28
+ /** Standard MCP error result describing an invalid/expired agent token. */
29
+ export function invalidAgentTokenToolResult() {
30
+ const text = agentTokenRecoveryMessage();
31
+ return {
32
+ content: [{ type: 'text', text }],
33
+ structuredContent: {
34
+ error: { code: INVALID_AGENT_TOKEN_CODE, message: text },
35
+ },
36
+ isError: true,
37
+ };
38
+ }
39
+ //# sourceMappingURL=tool-results.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"tool-results.js","sourceRoot":"","sources":["../../../src/cli/mcp/tool-results.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,wBAAwB,EAAE,yBAAyB,EAAE,MAAM,kBAAkB,CAAC;AACvF,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AAExB,6EAA6E;AAC7E,MAAM,CAAC,MAAM,UAAU,GAAG,CAAC,CAAC,MAAM,CAAC,EAAE,CAAC,CAAC,WAAW,EAAE,CAAC;AAOrD,2FAA2F;AAC3F,MAAM,UAAU,WAAW,CAAC,KAAc;IACxC,MAAM,iBAAiB,GACrB,OAAO,KAAK,KAAK,QAAQ,IAAI,KAAK,KAAK,IAAI,IAAI,CAAC,KAAK,CAAC,OAAO,CAAC,KAAK,CAAC;QAClE,CAAC,CAAE,KAAiC;QACpC,CAAC,CAAC,EAAE,KAAK,EAAE,CAAC;IAChB,OAAO;QACL,OAAO,EAAE,CAAC,EAAE,IAAI,EAAE,MAAM,EAAE,IAAI,EAAE,IAAI,CAAC,SAAS,CAAC,KAAK,EAAE,IAAI,EAAE,CAAC,CAAC,EAAE,CAAC;QACjE,iBAAiB;KAClB,CAAC;AACJ,CAAC;AAED,2DAA2D;AAC3D,MAAM,UAAU,WAAW,CAAC,OAAe,EAAE,oBAA6C,EAAE,OAAO,EAAE;IACnG,OAAO;QACL,OAAO,EAAE,CAAC,EAAE,IAAI,EAAE,MAAe,EAAE,IAAI,EAAE,OAAO,EAAE,CAAC;QACnD,iBAAiB;KAClB,CAAC;AACJ,CAAC;AAED,MAAM,UAAU,eAAe,CAAC,KAAc;IAC5C,OAAO,CACL,OAAO,KAAK,KAAK,QAAQ,IAAI,KAAK,KAAK,IAAI,IAAI,KAAK,CAAC,OAAO,CAAE,KAA+B,CAAC,OAAO,CAAC,CACvG,CAAC;AACJ,CAAC;AAED,MAAM,UAAU,iBAAiB,CAAC,KAAc;IAC9C,OAAO,OAAO,CAAC,KAAK,IAAI,OAAO,KAAK,KAAK,QAAQ,IAAK,KAA+B,CAAC,OAAO,KAAK,IAAI,CAAC,CAAC;AAC1G,CAAC;AAED,2EAA2E;AAC3E,MAAM,UAAU,2BAA2B;IACzC,MAAM,IAAI,GAAG,yBAAyB,EAAE,CAAC;IACzC,OAAO;QACL,OAAO,EAAE,CAAC,EAAE,IAAI,EAAE,MAAM,EAAE,IAAI,EAAE,CAAC;QACjC,iBAAiB,EAAE;YACjB,KAAK,EAAE,EAAE,IAAI,EAAE,wBAAwB,EAAE,OAAO,EAAE,IAAI,EAAE;SACzD;QACD,OAAO,EAAE,IAAI;KACd,CAAC;AACJ,CAAC"}
@@ -0,0 +1,13 @@
1
+ import { z } from 'zod';
2
+ /** Standard output schema for tools that return a single confirmation message. */
3
+ export declare const messageResult: {
4
+ message: z.ZodString;
5
+ };
6
+ /**
7
+ * Optional `as` input field that lets a tool act on behalf of one of several
8
+ * registered agent identities in the same MCP session.
9
+ */
10
+ export declare const identityOverrideInputShape: {
11
+ as: z.ZodOptional<z.ZodString>;
12
+ };
13
+ //# sourceMappingURL=tool-shapes.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"tool-shapes.d.ts","sourceRoot":"","sources":["../../../src/cli/mcp/tool-shapes.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AAExB,kFAAkF;AAClF,eAAO,MAAM,aAAa;;CAEzB,CAAC;AAEF;;;GAGG;AACH,eAAO,MAAM,0BAA0B;;CAKtC,CAAC"}
@@ -0,0 +1,16 @@
1
+ import { z } from 'zod';
2
+ /** Standard output schema for tools that return a single confirmation message. */
3
+ export const messageResult = {
4
+ message: z.string().describe('Human-readable confirmation message'),
5
+ };
6
+ /**
7
+ * Optional `as` input field that lets a tool act on behalf of one of several
8
+ * registered agent identities in the same MCP session.
9
+ */
10
+ export const identityOverrideInputShape = {
11
+ as: z
12
+ .string()
13
+ .optional()
14
+ .describe('Registered agent identity to act as when multiple identities have been registered'),
15
+ };
16
+ //# sourceMappingURL=tool-shapes.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"tool-shapes.js","sourceRoot":"","sources":["../../../src/cli/mcp/tool-shapes.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AAExB,kFAAkF;AAClF,MAAM,CAAC,MAAM,aAAa,GAAG;IAC3B,OAAO,EAAE,CAAC,CAAC,MAAM,EAAE,CAAC,QAAQ,CAAC,qCAAqC,CAAC;CACpE,CAAC;AAEF;;;GAGG;AACH,MAAM,CAAC,MAAM,0BAA0B,GAAG;IACxC,EAAE,EAAE,CAAC;SACF,MAAM,EAAE;SACR,QAAQ,EAAE;SACV,QAAQ,CAAC,mFAAmF,CAAC;CACjG,CAAC"}
@@ -0,0 +1,38 @@
1
+ import type { RelayCast, AgentClient } from '@relaycast/sdk';
2
+ import type { ActionAuditEvent, AgentRelayActions } from '@agent-relay/sdk/actions';
3
+ import type { RealtimeResourceBridge, SubscriptionManager } from './resources.js';
4
+ export type AgentType = 'agent' | 'human';
5
+ export type RelayCastLike = Pick<RelayCast, 'agents'>;
6
+ export type AgentClientLike = AgentClient;
7
+ export interface AgentRelayMcpServerOptions {
8
+ workspaceKey?: string;
9
+ /** @deprecated Use workspaceKey. */
10
+ apiKey?: string;
11
+ baseUrl?: string;
12
+ agentToken?: string;
13
+ agentName?: string;
14
+ agentType?: AgentType;
15
+ strictAgentName?: boolean;
16
+ telemetryTransport?: 'stdio' | 'http';
17
+ skipBootstrap?: boolean;
18
+ actions?: AgentRelayActions;
19
+ onActionAuditEvent?: (event: ActionAuditEvent) => Promise<void> | void;
20
+ }
21
+ export interface RegisteredAgent {
22
+ agentName: string;
23
+ agentToken: string;
24
+ }
25
+ export interface SessionState {
26
+ workspaceKey: string | null;
27
+ agentToken: string | null;
28
+ agentName: string | null;
29
+ agents: Map<string, RegisteredAgent>;
30
+ wsBridge: RealtimeResourceBridge | null;
31
+ subscriptions: SubscriptionManager | null;
32
+ wsInitAttempted: boolean;
33
+ }
34
+ export type RegistrationSession = Pick<SessionState, 'workspaceKey' | 'agentToken' | 'agentName'> & {
35
+ agents?: Map<string, RegisteredAgent>;
36
+ };
37
+ export type SessionSetter = (partial: Partial<SessionState>) => void;
38
+ //# sourceMappingURL=types.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../../src/cli/mcp/types.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,SAAS,EAAE,WAAW,EAAE,MAAM,gBAAgB,CAAC;AAC7D,OAAO,KAAK,EAAE,gBAAgB,EAAE,iBAAiB,EAAE,MAAM,0BAA0B,CAAC;AAEpF,OAAO,KAAK,EAAE,sBAAsB,EAAE,mBAAmB,EAAE,MAAM,gBAAgB,CAAC;AAElF,MAAM,MAAM,SAAS,GAAG,OAAO,GAAG,OAAO,CAAC;AAC1C,MAAM,MAAM,aAAa,GAAG,IAAI,CAAC,SAAS,EAAE,QAAQ,CAAC,CAAC;AACtD,MAAM,MAAM,eAAe,GAAG,WAAW,CAAC;AAE1C,MAAM,WAAW,0BAA0B;IACzC,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,oCAAoC;IACpC,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,SAAS,CAAC,EAAE,SAAS,CAAC;IACtB,eAAe,CAAC,EAAE,OAAO,CAAC;IAC1B,kBAAkB,CAAC,EAAE,OAAO,GAAG,MAAM,CAAC;IACtC,aAAa,CAAC,EAAE,OAAO,CAAC;IACxB,OAAO,CAAC,EAAE,iBAAiB,CAAC;IAC5B,kBAAkB,CAAC,EAAE,CAAC,KAAK,EAAE,gBAAgB,KAAK,OAAO,CAAC,IAAI,CAAC,GAAG,IAAI,CAAC;CACxE;AAED,MAAM,WAAW,eAAe;IAC9B,SAAS,EAAE,MAAM,CAAC;IAClB,UAAU,EAAE,MAAM,CAAC;CACpB;AAED,MAAM,WAAW,YAAY;IAC3B,YAAY,EAAE,MAAM,GAAG,IAAI,CAAC;IAC5B,UAAU,EAAE,MAAM,GAAG,IAAI,CAAC;IAC1B,SAAS,EAAE,MAAM,GAAG,IAAI,CAAC;IACzB,MAAM,EAAE,GAAG,CAAC,MAAM,EAAE,eAAe,CAAC,CAAC;IACrC,QAAQ,EAAE,sBAAsB,GAAG,IAAI,CAAC;IACxC,aAAa,EAAE,mBAAmB,GAAG,IAAI,CAAC;IAC1C,eAAe,EAAE,OAAO,CAAC;CAC1B;AAED,MAAM,MAAM,mBAAmB,GAAG,IAAI,CAAC,YAAY,EAAE,cAAc,GAAG,YAAY,GAAG,WAAW,CAAC,GAAG;IAClG,MAAM,CAAC,EAAE,GAAG,CAAC,MAAM,EAAE,eAAe,CAAC,CAAC;CACvC,CAAC;AAEF,MAAM,MAAM,aAAa,GAAG,CAAC,OAAO,EAAE,OAAO,CAAC,YAAY,CAAC,KAAK,IAAI,CAAC"}
@@ -0,0 +1,2 @@
1
+ export {};
2
+ //# sourceMappingURL=types.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"types.js","sourceRoot":"","sources":["../../../src/cli/mcp/types.ts"],"names":[],"mappings":""}
@@ -0,0 +1,10 @@
1
+ import type { RegistrationSession } from './types.js';
2
+ /** Create a new RelayCast workspace, returning the raw provisioning payload. */
3
+ export declare function createWorkspace(name: string, baseUrl?: string): Promise<Record<string, unknown>>;
4
+ /** Extract a workspace key from a provisioning payload, tolerating naming variants. */
5
+ export declare function extractWorkspaceKey(payload: Record<string, unknown>): string | undefined;
6
+ /** Extract a workspace name from a provisioning payload, falling back to `fallback`. */
7
+ export declare function extractWorkspaceName(payload: Record<string, unknown>, fallback: string): string;
8
+ /** Throw a descriptive error when the session has no workspace key configured. */
9
+ export declare function requireWorkspaceKey(session: RegistrationSession): void;
10
+ //# sourceMappingURL=workspace.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"workspace.d.ts","sourceRoot":"","sources":["../../../src/cli/mcp/workspace.ts"],"names":[],"mappings":"AAGA,OAAO,KAAK,EAAE,mBAAmB,EAAE,MAAM,YAAY,CAAC;AAEtD,gFAAgF;AAChF,wBAAsB,eAAe,CAAC,IAAI,EAAE,MAAM,EAAE,OAAO,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC,CAKtG;AAED,uFAAuF;AACvF,wBAAgB,mBAAmB,CAAC,OAAO,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,MAAM,GAAG,SAAS,CAcxF;AAED,wFAAwF;AACxF,wBAAgB,oBAAoB,CAAC,OAAO,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EAAE,QAAQ,EAAE,MAAM,GAAG,MAAM,CAK/F;AAED,kFAAkF;AAClF,wBAAgB,mBAAmB,CAAC,OAAO,EAAE,mBAAmB,GAAG,IAAI,CAQtE"}
@@ -0,0 +1,36 @@
1
+ import { RelayCast } from '@relaycast/sdk';
2
+ import { relaycastWorkspaceTelemetryOptions } from '../lib/relaycast-telemetry.js';
3
+ /** Create a new RelayCast workspace, returning the raw provisioning payload. */
4
+ export async function createWorkspace(name, baseUrl) {
5
+ return (await RelayCast.createWorkspace(name, {
6
+ baseUrl,
7
+ ...relaycastWorkspaceTelemetryOptions(),
8
+ }));
9
+ }
10
+ /** Extract a workspace key from a provisioning payload, tolerating naming variants. */
11
+ export function extractWorkspaceKey(payload) {
12
+ const data = payload.data && typeof payload.data === 'object' ? payload.data : {};
13
+ const value = payload.workspaceKey ??
14
+ payload.workspace_key ??
15
+ payload.apiKey ??
16
+ payload.api_key ??
17
+ data.workspaceKey ??
18
+ data.workspace_key ??
19
+ data.apiKey ??
20
+ data.api_key;
21
+ return typeof value === 'string' && value.trim() ? value : undefined;
22
+ }
23
+ /** Extract a workspace name from a provisioning payload, falling back to `fallback`. */
24
+ export function extractWorkspaceName(payload, fallback) {
25
+ const data = payload.data && typeof payload.data === 'object' ? payload.data : {};
26
+ const value = payload.workspaceName ?? payload.workspace_name ?? payload.name ?? data.workspaceName;
27
+ return typeof value === 'string' && value.trim() ? value : fallback;
28
+ }
29
+ /** Throw a descriptive error when the session has no workspace key configured. */
30
+ export function requireWorkspaceKey(session) {
31
+ if (session.workspaceKey) {
32
+ return;
33
+ }
34
+ throw new Error('Workspace key not configured. Call "create_workspace" first, or "set_workspace_key" if someone shared a workspace key.');
35
+ }
36
+ //# sourceMappingURL=workspace.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"workspace.js","sourceRoot":"","sources":["../../../src/cli/mcp/workspace.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,SAAS,EAAE,MAAM,gBAAgB,CAAC;AAE3C,OAAO,EAAE,kCAAkC,EAAE,MAAM,+BAA+B,CAAC;AAGnF,gFAAgF;AAChF,MAAM,CAAC,KAAK,UAAU,eAAe,CAAC,IAAY,EAAE,OAAgB;IAClE,OAAO,CAAC,MAAM,SAAS,CAAC,eAAe,CAAC,IAAI,EAAE;QAC5C,OAAO;QACP,GAAG,kCAAkC,EAAE;KACxC,CAAC,CAA4B,CAAC;AACjC,CAAC;AAED,uFAAuF;AACvF,MAAM,UAAU,mBAAmB,CAAC,OAAgC;IAClE,MAAM,IAAI,GACR,OAAO,CAAC,IAAI,IAAI,OAAO,OAAO,CAAC,IAAI,KAAK,QAAQ,CAAC,CAAC,CAAE,OAAO,CAAC,IAAgC,CAAC,CAAC,CAAC,EAAE,CAAC;IACpG,MAAM,KAAK,GACT,OAAO,CAAC,YAAY;QACpB,OAAO,CAAC,aAAa;QACrB,OAAO,CAAC,MAAM;QACd,OAAO,CAAC,OAAO;QACf,IAAI,CAAC,YAAY;QACjB,IAAI,CAAC,aAAa;QAClB,IAAI,CAAC,MAAM;QACX,IAAI,CAAC,OAAO,CAAC;IAEf,OAAO,OAAO,KAAK,KAAK,QAAQ,IAAI,KAAK,CAAC,IAAI,EAAE,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,SAAS,CAAC;AACvE,CAAC;AAED,wFAAwF;AACxF,MAAM,UAAU,oBAAoB,CAAC,OAAgC,EAAE,QAAgB;IACrF,MAAM,IAAI,GACR,OAAO,CAAC,IAAI,IAAI,OAAO,OAAO,CAAC,IAAI,KAAK,QAAQ,CAAC,CAAC,CAAE,OAAO,CAAC,IAAgC,CAAC,CAAC,CAAC,EAAE,CAAC;IACpG,MAAM,KAAK,GAAG,OAAO,CAAC,aAAa,IAAI,OAAO,CAAC,cAAc,IAAI,OAAO,CAAC,IAAI,IAAI,IAAI,CAAC,aAAa,CAAC;IACpG,OAAO,OAAO,KAAK,KAAK,QAAQ,IAAI,KAAK,CAAC,IAAI,EAAE,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,QAAQ,CAAC;AACtE,CAAC;AAED,kFAAkF;AAClF,MAAM,UAAU,mBAAmB,CAAC,OAA4B;IAC9D,IAAI,OAAO,CAAC,YAAY,EAAE,CAAC;QACzB,OAAO;IACT,CAAC;IAED,MAAM,IAAI,KAAK,CACb,wHAAwH,CACzH,CAAC;AACJ,CAAC"}
package/dist/index.cjs CHANGED
@@ -283,7 +283,7 @@ __export(index_exports, {
283
283
  module.exports = __toCommonJS(index_exports);
284
284
 
285
285
  // ../sdk/node_modules/@relaycast/sdk/dist/version.js
286
- var SDK_VERSION = "4.0.0";
286
+ var SDK_VERSION = "4.1.2";
287
287
 
288
288
  // ../sdk/node_modules/zod/v4/classic/external.js
289
289
  var external_exports = {};
@@ -16007,7 +16007,21 @@ var FleetNodeHeartbeatMessageSchema = external_exports.object({
16007
16007
  type: external_exports.literal("node.heartbeat"),
16008
16008
  load: external_exports.number().finite().nonnegative(),
16009
16009
  active_agents: external_exports.number().int().nonnegative(),
16010
- handlers_live: external_exports.boolean()
16010
+ handlers_live: external_exports.boolean(),
16011
+ // Roster snapshot carried for liveness: lets the engine refresh a node's
16012
+ // descriptor (name/capabilities/max_agents/version) from the steady-state
16013
+ // heartbeat without waiting for a fresh node.register — important after an
16014
+ // engine restart where the broker keeps heartbeating an already-registered
16015
+ // node. All optional and backward-compatible: a minimal heartbeat
16016
+ // (load/active_agents/handlers_live only) is still valid.
16017
+ //
16018
+ // NOTE: the broker does NOT send last_heartbeat_at — receipt time is stamped
16019
+ // server-side by the engine as the single source of truth for liveness.
16020
+ name: external_exports.string().optional(),
16021
+ node_id: external_exports.string().optional(),
16022
+ capabilities: external_exports.array(FleetCapabilitySchema).optional(),
16023
+ max_agents: external_exports.number().int().nonnegative().optional(),
16024
+ version: external_exports.string().optional()
16011
16025
  }).strict();
16012
16026
  var FleetNodeDeregisterMessageSchema = external_exports.object({
16013
16027
  ...FleetRequestEnvelopeFields,
@@ -17723,6 +17737,11 @@ var RelayCast = class _RelayCast {
17723
17737
  get: () => this.client.get("/v1/workspace/stream"),
17724
17738
  set: (enabled) => this.client.put("/v1/workspace/stream", { enabled }),
17725
17739
  inherit: () => this.client.put("/v1/workspace/stream", { mode: "inherit" })
17740
+ },
17741
+ fleetNodes: {
17742
+ get: () => this.client.get("/v1/workspace/fleet-nodes"),
17743
+ set: (enabled) => this.client.put("/v1/workspace/fleet-nodes", { enabled }),
17744
+ inherit: () => this.client.put("/v1/workspace/fleet-nodes", { mode: "inherit" })
17726
17745
  }
17727
17746
  };
17728
17747
  systemPrompt = {
@@ -19264,6 +19283,14 @@ function readRecord2(record2, ...keys) {
19264
19283
  }
19265
19284
  return void 0;
19266
19285
  }
19286
+ function toRelayWorkspaceFleetNodesConfig(raw) {
19287
+ const record2 = asRecord(raw);
19288
+ return {
19289
+ enabled: readBoolean2(record2, "enabled") ?? false,
19290
+ defaultEnabled: readBoolean2(record2, "defaultEnabled", "default_enabled") ?? false,
19291
+ override: readBoolean2(record2, "override") ?? null
19292
+ };
19293
+ }
19267
19294
  var RelayPlacementError = class extends Error {
19268
19295
  code;
19269
19296
  capability;
@@ -19847,6 +19874,17 @@ var RelaycastMessagingClient = class {
19847
19874
  throw new Error("RelaycastMessagingClient.workspace.info requires the relaycast workspace API.");
19848
19875
  }
19849
19876
  return await this.relaycast.workspace.info();
19877
+ },
19878
+ fleetNodes: {
19879
+ get: async () => {
19880
+ return toRelayWorkspaceFleetNodesConfig(await this.requireWorkspaceFleetNodes().get());
19881
+ },
19882
+ set: async (enabled) => {
19883
+ return toRelayWorkspaceFleetNodesConfig(await this.requireWorkspaceFleetNodes().set(enabled));
19884
+ },
19885
+ inherit: async () => {
19886
+ return toRelayWorkspaceFleetNodesConfig(await this.requireWorkspaceFleetNodes().inherit());
19887
+ }
19850
19888
  }
19851
19889
  };
19852
19890
  resolvePlacementNode(node, selfNodeName) {
@@ -19968,6 +20006,12 @@ var RelaycastMessagingClient = class {
19968
20006
  }
19969
20007
  return this.relaycast.triggers;
19970
20008
  }
20009
+ requireWorkspaceFleetNodes() {
20010
+ if (!this.relaycast.workspace?.fleetNodes) {
20011
+ throw new Error("RelaycastMessagingClient.workspace.fleetNodes requires @relaycast/sdk with the workspace fleet nodes API.");
20012
+ }
20013
+ return this.relaycast.workspace.fleetNodes;
20014
+ }
19971
20015
  requireAgentActions(operation) {
19972
20016
  const actions = this.agentClient?.actions;
19973
20017
  if (!actions) {
@@ -20647,6 +20691,7 @@ function createWorkspaceFacade(messaging, deps) {
20647
20691
  };
20648
20692
  return {
20649
20693
  info: () => messaging.workspace.info(),
20694
+ fleetNodes: messaging.workspace.fleetNodes,
20650
20695
  register,
20651
20696
  reconnect: async ({ apiToken }) => {
20652
20697
  if (!deps) {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "agent-relay",
3
- "version": "8.8.5",
3
+ "version": "8.9.1",
4
4
  "description": "Real-time agent-to-agent communication system",
5
5
  "type": "module",
6
6
  "main": "dist/index.cjs",
@@ -43,14 +43,14 @@
43
43
  "pack:validate": "npm pack --dry-run"
44
44
  },
45
45
  "dependencies": {
46
- "@agent-relay/cloud": "8.8.5",
47
- "@agent-relay/config": "8.8.5",
48
- "@agent-relay/fleet": "8.8.5",
49
- "@agent-relay/harness-driver": "8.8.5",
50
- "@agent-relay/sdk": "8.8.5",
51
- "@agent-relay/utils": "8.8.5",
46
+ "@agent-relay/cloud": "8.9.1",
47
+ "@agent-relay/config": "8.9.1",
48
+ "@agent-relay/fleet": "8.9.1",
49
+ "@agent-relay/harness-driver": "8.9.1",
50
+ "@agent-relay/sdk": "8.9.1",
51
+ "@agent-relay/utils": "8.9.1",
52
52
  "@modelcontextprotocol/sdk": "^1.0.0",
53
- "@relaycast/sdk": "^4.0.0",
53
+ "@relaycast/sdk": "^4.1.2",
54
54
  "@relayflows/cli": "^1.0.1",
55
55
  "@xterm/headless": "^6.0.0",
56
56
  "commander": "^12.1.0",