@assemblyline-agents/core 2.0.0 → 3.1.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.
Files changed (105) hide show
  1. package/LICENSE +1 -1
  2. package/dist/adapter-metadata.d.ts.map +1 -1
  3. package/dist/adapter-metadata.js +93 -35
  4. package/dist/adapter-metadata.js.map +1 -1
  5. package/dist/agent-definition.d.ts +10 -0
  6. package/dist/agent-definition.d.ts.map +1 -1
  7. package/dist/agent-definition.js.map +1 -1
  8. package/dist/agent-hooks.d.ts +11 -3
  9. package/dist/agent-hooks.d.ts.map +1 -1
  10. package/dist/agent-hooks.js +10 -16
  11. package/dist/agent-hooks.js.map +1 -1
  12. package/dist/artifact-dir.d.ts +1 -7
  13. package/dist/artifact-dir.d.ts.map +1 -1
  14. package/dist/artifact-dir.js +3 -12
  15. package/dist/artifact-dir.js.map +1 -1
  16. package/dist/audience.d.ts +16 -0
  17. package/dist/audience.d.ts.map +1 -0
  18. package/dist/audience.js +2 -0
  19. package/dist/audience.js.map +1 -0
  20. package/dist/brand.d.ts +2 -17
  21. package/dist/brand.d.ts.map +1 -1
  22. package/dist/brand.js +2 -17
  23. package/dist/brand.js.map +1 -1
  24. package/dist/connection-auth.d.ts.map +1 -1
  25. package/dist/connection-auth.js +17 -2
  26. package/dist/connection-auth.js.map +1 -1
  27. package/dist/connection-events.d.ts +35 -0
  28. package/dist/connection-events.d.ts.map +1 -0
  29. package/dist/connection-events.js +131 -0
  30. package/dist/connection-events.js.map +1 -0
  31. package/dist/connection-types.d.ts +232 -6
  32. package/dist/connection-types.d.ts.map +1 -1
  33. package/dist/connection-types.js +8 -1
  34. package/dist/connection-types.js.map +1 -1
  35. package/dist/definitions.d.ts +7 -2
  36. package/dist/definitions.d.ts.map +1 -1
  37. package/dist/definitions.js +58 -3
  38. package/dist/definitions.js.map +1 -1
  39. package/dist/deploy.d.ts +12 -2
  40. package/dist/deploy.d.ts.map +1 -1
  41. package/dist/deploy.js.map +1 -1
  42. package/dist/harness.d.ts +31 -2
  43. package/dist/harness.d.ts.map +1 -1
  44. package/dist/harness.js.map +1 -1
  45. package/dist/index.d.ts +54 -6
  46. package/dist/index.d.ts.map +1 -1
  47. package/dist/index.js +27 -2
  48. package/dist/index.js.map +1 -1
  49. package/dist/manifest-types.d.ts +89 -4
  50. package/dist/manifest-types.d.ts.map +1 -1
  51. package/dist/model-metadata.d.ts +33 -0
  52. package/dist/model-metadata.d.ts.map +1 -0
  53. package/dist/model-metadata.js +13 -0
  54. package/dist/model-metadata.js.map +1 -0
  55. package/dist/plugin-connection-factories.d.ts +31 -0
  56. package/dist/plugin-connection-factories.d.ts.map +1 -0
  57. package/dist/plugin-connection-factories.js +416 -0
  58. package/dist/plugin-connection-factories.js.map +1 -0
  59. package/dist/plugin-contract.d.ts +161 -0
  60. package/dist/plugin-contract.d.ts.map +1 -0
  61. package/dist/plugin-contract.js +52 -0
  62. package/dist/plugin-contract.js.map +1 -0
  63. package/dist/plugin.d.ts +5 -126
  64. package/dist/plugin.d.ts.map +1 -1
  65. package/dist/plugin.js +769 -370
  66. package/dist/plugin.js.map +1 -1
  67. package/dist/resource-types.d.ts +1 -1
  68. package/dist/resource-types.d.ts.map +1 -1
  69. package/dist/sandbox-file-metadata.d.ts +9 -0
  70. package/dist/sandbox-file-metadata.d.ts.map +1 -0
  71. package/dist/sandbox-file-metadata.js +33 -0
  72. package/dist/sandbox-file-metadata.js.map +1 -0
  73. package/dist/sandbox-filesystem-contract.d.ts +9 -9
  74. package/dist/sandbox-filesystem-contract.d.ts.map +1 -1
  75. package/dist/sandbox-filesystem-contract.js +31 -29
  76. package/dist/sandbox-filesystem-contract.js.map +1 -1
  77. package/dist/sandbox-paths.d.ts +1 -1
  78. package/dist/sandbox-paths.d.ts.map +1 -1
  79. package/dist/sandbox-paths.js +1 -1
  80. package/dist/sandbox-paths.js.map +1 -1
  81. package/dist/sandbox-security.d.ts +0 -3
  82. package/dist/sandbox-security.d.ts.map +1 -1
  83. package/dist/sandbox-security.js +7 -12
  84. package/dist/sandbox-security.js.map +1 -1
  85. package/dist/sandbox-types.d.ts +74 -3
  86. package/dist/sandbox-types.d.ts.map +1 -1
  87. package/dist/sandbox-types.js +13 -1
  88. package/dist/sandbox-types.js.map +1 -1
  89. package/dist/secrets-types.d.ts +25 -0
  90. package/dist/secrets-types.d.ts.map +1 -0
  91. package/dist/secrets-types.js +22 -0
  92. package/dist/secrets-types.js.map +1 -0
  93. package/dist/skill-bundles.d.ts +14 -0
  94. package/dist/skill-bundles.d.ts.map +1 -0
  95. package/dist/skill-bundles.js +85 -0
  96. package/dist/skill-bundles.js.map +1 -0
  97. package/dist/tool-wire-name.d.ts +8 -0
  98. package/dist/tool-wire-name.d.ts.map +1 -0
  99. package/dist/tool-wire-name.js +26 -0
  100. package/dist/tool-wire-name.js.map +1 -0
  101. package/package.json +1 -1
  102. package/dist/env-alias.d.ts +0 -38
  103. package/dist/env-alias.d.ts.map +0 -1
  104. package/dist/env-alias.js +0 -82
  105. package/dist/env-alias.js.map +0 -1
package/dist/plugin.js CHANGED
@@ -1,186 +1,5 @@
1
- import { PLUGIN_EXPORT_NAME } from "./brand.js";
2
- import { defineMcpClientConnection, defineMcpRelayConnection, defineMcpStdioConnection, defineOpenAPIConnection, defineSandboxCliConnection } from "./definitions.js";
3
- export function definePlugin(module) {
4
- return module;
5
- }
6
- /** Reads the `assemblyLinePlugin` export from a dynamically imported module namespace. */
7
- export function pluginModuleFromImport(imported) {
8
- const candidates = [imported, imported?.default];
9
- for (const candidate of candidates) {
10
- if (!candidate || typeof candidate !== "object")
11
- continue;
12
- const value = candidate[PLUGIN_EXPORT_NAME];
13
- if (isPluginModule(value))
14
- return value;
15
- }
16
- return undefined;
17
- }
18
- /**
19
- * Provider packages use this factory instead of implementing transport or
20
- * credential plumbing. The developer still owns the provider application,
21
- * token/OAuth grant, and any required MCP bridge.
22
- */
23
- export function defineMcpPluginConnection(plugin, options) {
24
- if (plugin.protocol !== "mcp") {
25
- throw new Error(`${plugin.helper}: ${plugin.provider} uses OpenAPI; call defineOpenAPIPluginConnection instead.`);
26
- }
27
- if ((plugin.transport ?? "http") !== "http") {
28
- throw new Error(`${plugin.helper}: ${plugin.provider} uses stdio; call defineStdioMcpPluginConnection instead.`);
29
- }
30
- validatePluginAccess(plugin, options.access);
31
- const url = options.url ?? environmentValue(plugin.urlEnv) ?? plugin.defaultUrl;
32
- if (!url)
33
- throw new Error(`${plugin.helper}: set ${plugin.urlEnv ?? "a connection URL"} or pass url.`);
34
- const definition = {
35
- transport: "http",
36
- url,
37
- description: options.description ?? plugin.description,
38
- access: pluginAccessDefinition(plugin, options.access),
39
- required: options.required ?? true,
40
- subject: options.subject ?? plugin.subject ?? "user",
41
- metadata: {
42
- provider: plugin.provider,
43
- plugin: plugin.packageName ?? plugin.provider,
44
- ...(options.metadata ?? {})
45
- }
46
- };
47
- const auth = options.auth === false || plugin.tokenHeader
48
- ? (options.auth === false ? undefined : options.auth)
49
- : options.auth ?? (plugin.tokenRequired === false ? undefined : tokenAuth(plugin.tokenEnv));
50
- if (auth)
51
- definition.auth = auth;
52
- const tokenHeaders = options.auth === undefined && plugin.tokenHeader
53
- ? tokenHeader(plugin.tokenHeader, plugin.tokenEnv)
54
- : undefined;
55
- const headers = mergeHeaders(tokenHeaders, options.headers);
56
- if (headers)
57
- definition.headers = headers;
58
- const tools = options.tools ?? cloneToolFilter(plugin.tools);
59
- if (tools)
60
- definition.tools = tools;
61
- return defineMcpClientConnection(definition);
62
- }
63
- export function defineStdioMcpPluginConnection(plugin, options) {
64
- if (plugin.protocol !== "mcp" || plugin.transport !== "stdio") {
65
- throw new Error(`${plugin.helper}: ${plugin.provider} uses HTTP; call defineMcpPluginConnection instead.`);
66
- }
67
- validatePluginAccess(plugin, options.access);
68
- const definition = {
69
- transport: "stdio",
70
- command: options.command,
71
- ...(options.args ? { args: [...options.args] } : {}),
72
- ...(options.cwd ? { cwd: options.cwd } : {}),
73
- ...(options.env ? { env: { ...options.env } } : {}),
74
- description: options.description ?? plugin.description,
75
- access: pluginAccessDefinition(plugin, options.access),
76
- required: options.required ?? true,
77
- subject: options.subject ?? plugin.subject ?? "environment",
78
- metadata: {
79
- provider: plugin.provider,
80
- plugin: plugin.packageName ?? plugin.provider,
81
- ...(options.metadata ?? {})
82
- }
83
- };
84
- const tools = options.tools ?? cloneToolFilter(plugin.tools);
85
- if (tools)
86
- definition.tools = tools;
87
- return defineMcpStdioConnection(definition);
88
- }
89
- export function defineRelayMcpPluginConnection(plugin, options) {
90
- if (plugin.protocol !== "mcp" || plugin.transport !== "relay") {
91
- throw new Error(`${plugin.helper}: ${plugin.provider} does not use the OpenEve relay transport.`);
92
- }
93
- validatePluginAccess(plugin, options.access);
94
- const url = options.url ?? environmentValue(plugin.urlEnv) ?? plugin.defaultUrl;
95
- if (!url)
96
- throw new Error(`${plugin.helper}: set ${plugin.urlEnv ?? "a relay URL"} or pass url.`);
97
- const credentialEnv = options.credentialEnv ?? plugin.credentialEnv;
98
- if (!credentialEnv)
99
- throw new Error(`${plugin.helper}: relay metadata must declare credentialEnv.`);
100
- const definition = {
101
- transport: "relay",
102
- url,
103
- credentialEnv,
104
- ...(options.timeoutMs !== undefined ? { timeoutMs: options.timeoutMs } : {}),
105
- description: options.description ?? plugin.description,
106
- access: pluginAccessDefinition(plugin, options.access),
107
- required: options.required ?? true,
108
- subject: options.subject ?? plugin.subject ?? "environment",
109
- metadata: {
110
- provider: plugin.provider,
111
- plugin: plugin.packageName ?? plugin.provider,
112
- ...(options.metadata ?? {})
113
- }
114
- };
115
- const tools = options.tools ?? cloneToolFilter(plugin.tools);
116
- if (tools)
117
- definition.tools = tools;
118
- return defineMcpRelayConnection(definition);
119
- }
120
- /** Build a direct HTTP API connection from a provider's reviewed OpenAPI metadata. */
121
- export function defineOpenAPIPluginConnection(plugin, options) {
122
- if (plugin.protocol !== "openapi") {
123
- throw new Error(`${plugin.helper}: ${plugin.provider} uses MCP; call defineMcpPluginConnection instead.`);
124
- }
125
- validatePluginAccess(plugin, options.access);
126
- const spec = options.spec ?? environmentValue(plugin.specEnv) ?? plugin.defaultSpec;
127
- if (!spec)
128
- throw new Error(`${plugin.helper}: set ${plugin.specEnv ?? "an OpenAPI specification"} or pass spec.`);
129
- const baseUrl = options.baseUrl ?? environmentValue(plugin.baseUrlEnv) ?? plugin.defaultBaseUrl;
130
- const definition = {
131
- spec,
132
- ...(baseUrl ? { baseUrl } : {}),
133
- description: options.description ?? plugin.description,
134
- access: pluginAccessDefinition(plugin, options.access),
135
- required: options.required ?? true,
136
- subject: options.subject ?? plugin.subject ?? "user",
137
- metadata: {
138
- provider: plugin.provider,
139
- plugin: plugin.packageName ?? plugin.provider,
140
- ...(options.metadata ?? {})
141
- }
142
- };
143
- const auth = options.auth === false
144
- ? undefined
145
- : options.auth ?? (plugin.tokenRequired === false ? undefined : tokenAuth(plugin.tokenEnv));
146
- if (auth)
147
- definition.auth = auth;
148
- if (options.headers)
149
- definition.headers = options.headers;
150
- const operations = options.operations ?? cloneToolFilter(plugin.tools);
151
- if (operations)
152
- definition.operations = operations;
153
- return defineOpenAPIConnection(definition);
154
- }
155
- /**
156
- * Build a connection whose reviewed operations run through a provider CLI in
157
- * the agent sandbox rather than on the OpenEve gateway host.
158
- */
159
- export function defineSandboxCliPluginConnection(plugin, options) {
160
- if (plugin.protocol !== "cli" || plugin.transport !== "sandbox") {
161
- throw new Error(`${plugin.helper}: ${plugin.provider} does not use the sandbox CLI transport.`);
162
- }
163
- validatePluginAccess(plugin, options.access);
164
- const command = options.command ?? plugin.command;
165
- if (!command)
166
- throw new Error(`${plugin.helper}: sandbox CLI metadata must declare command.`);
167
- return defineSandboxCliConnection({
168
- transport: "sandbox",
169
- command,
170
- description: options.description ?? plugin.description,
171
- tools: options.tools,
172
- access: pluginAccessDefinition(plugin, options.access),
173
- ...(options.auth ? { auth: options.auth } : {}),
174
- ...(options.maxOutputChars !== undefined ? { maxOutputChars: options.maxOutputChars } : {}),
175
- required: options.required ?? true,
176
- subject: options.subject ?? plugin.subject ?? "environment",
177
- metadata: {
178
- provider: plugin.provider,
179
- plugin: plugin.packageName ?? plugin.provider,
180
- ...(options.metadata ?? {})
181
- }
182
- });
183
- }
1
+ export * from "./plugin-contract.js";
2
+ export * from "./plugin-connection-factories.js";
184
3
  export function connectionPluginMetadata(kind) {
185
4
  return CONNECTION_PLUGIN_CATALOG.find((entry) => entry.kind === kind);
186
5
  }
@@ -190,6 +9,55 @@ export function connectionPluginMetadataForHelper(helper) {
190
9
  export function allConnectionPluginMetadata() {
191
10
  return CONNECTION_PLUGIN_CATALOG.map(cloneMetadata);
192
11
  }
12
+ export function toolPackPluginMetadata(kind) {
13
+ const metadata = TOOL_PACK_PLUGIN_CATALOG.find((entry) => entry.kind === kind);
14
+ return metadata ? cloneToolPackMetadata(metadata) : undefined;
15
+ }
16
+ export function allToolPackPluginMetadata() {
17
+ return TOOL_PACK_PLUGIN_CATALOG.map(cloneToolPackMetadata);
18
+ }
19
+ const TOOL_PACK_PLUGIN_CATALOG = [
20
+ {
21
+ kind: "openui",
22
+ role: "tools",
23
+ packageName: "@assemblyline-agents/openui",
24
+ description: "Full OpenUI component packs with developer policy, immutable revisions, and storage-issued publication links.",
25
+ tools: [
26
+ {
27
+ name: "openui_create",
28
+ helper: "defineOpenUiCreateTool",
29
+ description: "Create an immutable artifact revision from developer-approved OpenUI components. Raw HTML is not accepted.",
30
+ needsApproval: false
31
+ },
32
+ {
33
+ name: "openui_update",
34
+ helper: "defineOpenUiUpdateTool",
35
+ description: "Create a new immutable revision of an existing OpenUI artifact. Raw HTML is not accepted.",
36
+ needsApproval: false
37
+ },
38
+ {
39
+ name: "openui_publish",
40
+ helper: "defineOpenUiPublishTool",
41
+ description: "Publish one OpenUI artifact revision to an unlisted, storage-issued HTTPS link.",
42
+ needsApproval: false
43
+ }
44
+ ],
45
+ config: {
46
+ path: "tool-config/openui.ts",
47
+ helper: "defineOpenUiConfig",
48
+ options: {}
49
+ },
50
+ skills: ["openui-artifacts"],
51
+ requiredEnv: [],
52
+ optionalEnv: ["R2_PUBLIC_BASE_URL", "S3_PUBLIC_BASE_URL"],
53
+ setup: [{
54
+ kind: "tools",
55
+ name: "openui-public-blob-origin",
56
+ required: true,
57
+ message: "Configure an HTTPS public base URL on the blob adapter, then review the generated OpenUI component and brand policy before publishing."
58
+ }]
59
+ }
60
+ ];
193
61
  const READ_PATTERNS = [
194
62
  "regex:(^|[-_])(search|read|list|fetch|get|retrieve|query|lookup|find|describe|details?|discover)([-_]|$)"
195
63
  ];
@@ -226,12 +94,18 @@ function catalogEntry(input) {
226
94
  optionalEnv,
227
95
  capabilities: ["mcp", "live-tools", input.transport === "stdio" ? "stdio" : input.transport === "relay" ? "e2ee-device-relay" : "streamable-http"],
228
96
  scopes: [...(input.scopes ?? [])],
229
- subject: input.subject ?? "user",
97
+ // Plugins with user-scoped grants declare subject: "user" explicitly; an
98
+ // unannotated plugin gets a deployment credential usable on every surface.
99
+ subject: input.subject ?? "workspace",
230
100
  ...(input.tools ? { tools: cloneToolFilter(input.tools) } : {}),
231
101
  ...(input.hostRequirements ? { hostRequirements: cloneHostRequirements(input.hostRequirements) } : {}),
232
102
  readToolPatterns: input.readToolPatterns ?? READ_PATTERNS,
233
103
  writeToolPatterns: input.writeToolPatterns ?? (input.write ? WRITE_PATTERNS : []),
234
- skill: input.kind,
104
+ ...(input.eventCatalog ? { eventCatalog: [...input.eventCatalog] } : {}),
105
+ ...(input.defaultEvents ? { defaultEvents: [...input.defaultEvents] } : {}),
106
+ ...(input.eventMode ? { eventMode: input.eventMode } : {}),
107
+ ...(input.eventScope ? { eventScope: input.eventScope } : {}),
108
+ ...(input.eventRequiredEnv ? { eventRequiredEnv: [...input.eventRequiredEnv] } : {}),
235
109
  setup: [{
236
110
  kind: "connection",
237
111
  name: `${input.kind}-developer-configuration`,
@@ -257,11 +131,6 @@ const HIGGSFIELD_PLUGIN = {
257
131
  subject: "user",
258
132
  readToolPatterns: ["read"],
259
133
  writeToolPatterns: ["write"],
260
- skills: [
261
- "higgsfield-generate",
262
- "higgsfield-soul-id",
263
- "higgsfield-product-photoshoot"
264
- ],
265
134
  setup: [{
266
135
  kind: "sandbox",
267
136
  name: "higgsfield-cli",
@@ -269,6 +138,30 @@ const HIGGSFIELD_PLUGIN = {
269
138
  message: "Install the official Higgsfield CLI in the sandbox image with `curl -fsSL https://raw.githubusercontent.com/higgsfield-ai/cli/main/install.sh | sh`, then run `higgsfield auth login` interactively inside each persistent, user-scoped sandbox. Do not bake account credentials into a shared image. Higgsfield generation and editing consume account credits."
270
139
  }]
271
140
  };
141
+ const REMOTION_PLUGIN = {
142
+ kind: "remotion",
143
+ role: "connection",
144
+ packageName: "@assemblyline-agents/remotion",
145
+ helper: "defineRemotionConnection",
146
+ protocol: "cli",
147
+ transport: "sandbox",
148
+ provider: "remotion",
149
+ description: "Remotion composition discovery and rendering through the project CLI inside the active agent sandbox.",
150
+ command: "npx",
151
+ requiredEnv: [],
152
+ optionalEnv: [],
153
+ capabilities: ["sandbox-cli", "media-rendering", "workspace-artifacts"],
154
+ scopes: [],
155
+ subject: "environment",
156
+ readToolPatterns: ["list_compositions", "check_versions"],
157
+ writeToolPatterns: ["render_video", "render_still"],
158
+ setup: [{
159
+ kind: "sandbox",
160
+ name: "remotion-cli",
161
+ required: true,
162
+ message: "Install Remotion and @remotion/cli in the sandbox project. Composition discovery and rendering execute inside the active run sandbox and write artifacts under /workspace."
163
+ }]
164
+ };
272
165
  const MIRROR_PLUGIN = {
273
166
  kind: "mirror",
274
167
  role: "connection",
@@ -291,11 +184,13 @@ const MIRROR_PLUGIN = {
291
184
  "mirror.connected_provider_call",
292
185
  "mirror.create_connections_link",
293
186
  "mirror.query_records",
187
+ "mirror.list_changes",
294
188
  "mirror.get_source",
295
189
  "mirror.live_read",
296
190
  "mirror.sync_now",
297
191
  "mirror.request_action",
298
192
  "mirror.get_pending_approvals",
193
+ "mirror.get_skill",
299
194
  "mirror.approve_code",
300
195
  "mirror.agentcash_wallet_export",
301
196
  "mirror.register_agent",
@@ -305,9 +200,11 @@ const MIRROR_PLUGIN = {
305
200
  readToolPatterns: [
306
201
  "mirror.connected_providers",
307
202
  "mirror.query_records",
203
+ "mirror.list_changes",
308
204
  "mirror.get_source",
309
205
  "mirror.live_read",
310
206
  "mirror.get_pending_approvals",
207
+ "mirror.get_skill",
311
208
  "mirror.whoami"
312
209
  ],
313
210
  writeToolPatterns: [
@@ -319,12 +216,15 @@ const MIRROR_PLUGIN = {
319
216
  "mirror.agentcash_wallet_export",
320
217
  "mirror.register_agent"
321
218
  ],
322
- skill: "mirror",
219
+ eventCatalog: ["source.changed"],
220
+ defaultEvents: ["source.changed"],
221
+ eventMode: "api",
222
+ eventScope: "principal",
323
223
  setup: [{
324
224
  kind: "connection",
325
225
  name: "mirror-oauth-configuration",
326
226
  required: true,
327
- message: "Choose a stable public client id for this agent, set MIRROR_OAUTH_CLIENT_ID, and deploy with a reachable OpenEve connection callback URL. Mirror uses OAuth Authorization Code + PKCE and stores provider credentials behind the user's Mirror account."
227
+ message: "Choose a stable public client id for this agent, set MIRROR_OAUTH_CLIENT_ID, and deploy with a reachable Assembly Line connection callback URL. Mirror uses OAuth Authorization Code + PKCE and stores provider credentials behind the user's Mirror account."
328
228
  }]
329
229
  };
330
230
  const MARGINS_PLUGIN = {
@@ -388,7 +288,6 @@ const MARGINS_PLUGIN = {
388
288
  "margins_edit",
389
289
  "margins_suggest"
390
290
  ],
391
- skill: "margins",
392
291
  setup: [{
393
292
  kind: "connection",
394
293
  name: "margins-binding-packet",
@@ -451,11 +350,6 @@ const PROVENANCE_PLUGIN = {
451
350
  "provenance.agent_activity"
452
351
  ],
453
352
  writeToolPatterns: ["provenance.register_agent"],
454
- skills: [
455
- "provenance-reconstruction",
456
- "provenance-handoff-bundle",
457
- "provenance-ambient-capture"
458
- ],
459
353
  setup: [{
460
354
  kind: "connection",
461
355
  name: "provenance-oauth-configuration",
@@ -464,6 +358,53 @@ const PROVENANCE_PLUGIN = {
464
358
  }]
465
359
  };
466
360
  const CONNECTION_PLUGIN_CATALOG = [
361
+ {
362
+ kind: "1password",
363
+ role: "connection",
364
+ packageName: "@assemblyline-agents/1password",
365
+ helper: "defineOnePasswordConnection",
366
+ protocol: "sdk",
367
+ provider: "1password",
368
+ description: "1Password vault discovery, item search and retrieval, and secret resolution through the official SDK.",
369
+ requiredEnv: ["OP_SERVICE_ACCOUNT_TOKEN"],
370
+ optionalEnv: [],
371
+ capabilities: ["sdk", "direct-api", "live-tools", "service-account", "vaults", "items", "secrets"],
372
+ scopes: [],
373
+ subject: "environment",
374
+ tools: {
375
+ allow: ["list_vaults", "list_items", "search_items", "get_item", "resolve_secret"]
376
+ },
377
+ readToolPatterns: ["list_vaults", "list_items", "search_items", "get_item", "resolve_secret"],
378
+ writeToolPatterns: [],
379
+ setup: [{
380
+ kind: "connection",
381
+ name: "onepassword-service-account",
382
+ required: true,
383
+ message: "Create a 1Password service account for this agent, share only the vaults the agent should be able to use, and set its token in OP_SERVICE_ACCOUNT_TOKEN. Every readable item and concealed field in those vaults is available to the agent."
384
+ }]
385
+ },
386
+ {
387
+ kind: "a2a",
388
+ role: "connection",
389
+ packageName: "@assemblyline-agents/a2a",
390
+ helper: "defineA2AConnection",
391
+ protocol: "a2a",
392
+ provider: "a2a",
393
+ description: "Discover and delegate work to an independently deployed agent through the A2A v1.0 protocol.",
394
+ requiredEnv: [],
395
+ optionalEnv: [],
396
+ capabilities: ["a2a", "agent-card-discovery", "remote-agent-tasks", "json-rpc"],
397
+ scopes: [],
398
+ subject: "environment",
399
+ readToolPatterns: ["regex:^(?!cancel_task$).+"],
400
+ writeToolPatterns: ["cancel_task"],
401
+ setup: [{
402
+ kind: "connection",
403
+ name: "a2a-peer-configuration",
404
+ required: true,
405
+ message: "Configure an allowlisted Agent Card URL and a peer-scoped service credential for the remote agent."
406
+ }]
407
+ },
467
408
  HIGGSFIELD_PLUGIN,
468
409
  MARGINS_PLUGIN,
469
410
  MIRROR_PLUGIN,
@@ -490,78 +431,310 @@ const CONNECTION_PLUGIN_CATALOG = [
490
431
  "arcads_get_upload_url",
491
432
  "regex:^arcads_(?!get_(?!upload_url$)|list|search|watch).+"
492
433
  ],
493
- skill: "arcads",
494
434
  setup: [{
495
435
  kind: "connection",
496
436
  name: "arcads-oauth-configuration",
497
437
  required: true,
498
- message: "Register an OAuth client with https://api.arcads.ai/oauth/register, set ARCADS_MCP_CLIENT_ID, and register the OpenEve connection callback URL. Arcads generation and editing consume account credits."
438
+ message: "Register an OAuth client with https://api.arcads.ai/oauth/register, set ARCADS_MCP_CLIENT_ID, and register the Assembly Line connection callback URL. Arcads generation and editing consume account credits."
499
439
  }]
500
440
  },
501
- catalogEntry({
441
+ {
442
+ kind: "attio",
443
+ role: "connection",
444
+ packageName: "@assemblyline-agents/attio",
445
+ helper: "defineAttioConnection",
446
+ protocol: "mcp",
447
+ transport: "http",
448
+ provider: "attio",
449
+ description: "Attio CRM records, lists, notes, tasks, comments, email and meeting intelligence, and reporting through Attio's official hosted MCP server.",
450
+ defaultUrl: "https://mcp.attio.com/mcp",
451
+ urlEnv: "ATTIO_MCP_URL",
452
+ requiredEnv: ["ATTIO_MCP_CLIENT_ID"],
453
+ optionalEnv: ["ATTIO_MCP_URL", "ATTIO_MCP_REDIRECT_URI"],
454
+ capabilities: ["mcp", "oauth", "pkce", "refresh-token", "live-tools", "streamable-http", "crm", "semantic-search", "reporting"],
455
+ scopes: ["mcp", "offline_access", "openid"],
456
+ subject: "user",
457
+ tools: {
458
+ allow: [
459
+ "search-records",
460
+ "list-records",
461
+ "get-records-by-ids",
462
+ "create-record",
463
+ "upsert-record",
464
+ "update-record",
465
+ "merge-records",
466
+ "list-attribute-definitions",
467
+ "list-lists",
468
+ "list-list-attribute-definitions",
469
+ "list-records-in-list",
470
+ "add-record-to-list",
471
+ "update-list",
472
+ "update-list-entry-by-id",
473
+ "update-list-entry-by-record-id",
474
+ "create-comment",
475
+ "list-comments",
476
+ "list-comment-replies",
477
+ "delete-comment",
478
+ "create-note",
479
+ "search-notes-by-metadata",
480
+ "semantic-search-notes",
481
+ "get-note-body",
482
+ "update-note",
483
+ "list-tasks",
484
+ "create-task",
485
+ "update-task",
486
+ "search-meetings",
487
+ "search-call-recordings-by-metadata",
488
+ "semantic-search-call-recordings",
489
+ "get-call-recording",
490
+ "search-emails-by-metadata",
491
+ "semantic-search-emails",
492
+ "get-email-content",
493
+ "list-workspace-members",
494
+ "list-workspace-teams",
495
+ "whoami",
496
+ "run-basic-report",
497
+ "query-particle-sql"
498
+ ]
499
+ },
500
+ readToolPatterns: [
501
+ "search-records",
502
+ "list-records",
503
+ "get-records-by-ids",
504
+ "list-attribute-definitions",
505
+ "list-lists",
506
+ "list-list-attribute-definitions",
507
+ "list-records-in-list",
508
+ "list-comments",
509
+ "list-comment-replies",
510
+ "search-notes-by-metadata",
511
+ "semantic-search-notes",
512
+ "get-note-body",
513
+ "list-tasks",
514
+ "search-meetings",
515
+ "search-call-recordings-by-metadata",
516
+ "semantic-search-call-recordings",
517
+ "get-call-recording",
518
+ "search-emails-by-metadata",
519
+ "semantic-search-emails",
520
+ "get-email-content",
521
+ "list-workspace-members",
522
+ "list-workspace-teams",
523
+ "whoami",
524
+ "run-basic-report",
525
+ "query-particle-sql"
526
+ ],
527
+ writeToolPatterns: [
528
+ "create-record",
529
+ "upsert-record",
530
+ "update-record",
531
+ "merge-records",
532
+ "add-record-to-list",
533
+ "update-list",
534
+ "update-list-entry-by-id",
535
+ "update-list-entry-by-record-id",
536
+ "create-comment",
537
+ "delete-comment",
538
+ "create-note",
539
+ "update-note",
540
+ "create-task",
541
+ "update-task"
542
+ ],
543
+ setup: [{
544
+ kind: "connection",
545
+ name: "attio-mcp-oauth",
546
+ required: true,
547
+ message: "Register a public OAuth client at https://app.attio.com/oauth/register for the Assembly Line connection callback, set ATTIO_MCP_CLIENT_ID, then let each user authorize Attio. For a shared company agent, explicitly set subject: \"workspace\" and preauthorize a dedicated Attio member through the protected operator connection flow."
548
+ }]
549
+ },
550
+ {
502
551
  kind: "gmail",
503
- displayName: "Gmail",
552
+ role: "connection",
553
+ packageName: "@assemblyline-agents/gmail",
504
554
  helper: "defineGmailConnection",
505
- description: "Gmail threads, messages, attachments, drafts, and sends through an independently authorized MCP connection.",
506
- urlEnv: "GMAIL_MCP_URL",
507
- tokenEnv: "GMAIL_MCP_TOKEN",
555
+ protocol: "http",
556
+ provider: "gmail",
557
+ description: "Gmail threads, messages, attachments, drafts, and sends through the Gmail REST API.",
558
+ defaultBaseUrl: "https://gmail.googleapis.com/gmail/v1",
559
+ baseUrlEnv: "GMAIL_API_BASE_URL",
560
+ requiredEnv: ["GOOGLE_CLIENT_ID", "GOOGLE_CLIENT_SECRET"],
561
+ optionalEnv: ["GOOGLE_REDIRECT_URI", "GMAIL_API_BASE_URL"],
562
+ capabilities: ["http-api", "oauth", "pkce", "refresh-token", "live-tools"],
508
563
  scopes: [
509
- "openid",
510
- "email",
511
- "profile",
512
564
  "https://www.googleapis.com/auth/gmail.readonly",
513
565
  "https://www.googleapis.com/auth/gmail.compose",
514
566
  "https://www.googleapis.com/auth/gmail.send"
515
567
  ],
516
- readToolPatterns: ["rest_get", ...READ_PATTERNS],
517
- writeToolPatterns: ["rest_request", ...WRITE_PATTERNS],
518
- write: true,
519
- setupMessage: "Configure a Gmail-only OAuth grant or MCP bridge for this deployment. Do not reuse an umbrella Google grant that also exposes Calendar or Drive."
520
- }),
521
- catalogEntry({
568
+ subject: "user",
569
+ tools: { allow: [
570
+ "gmail_get_profile", "gmail_list_messages", "gmail_get_message", "gmail_get_attachment",
571
+ "gmail_list_threads", "gmail_get_thread", "gmail_list_labels", "gmail_get_label",
572
+ "gmail_list_drafts", "gmail_get_draft", "gmail_create_draft", "gmail_update_draft",
573
+ "gmail_delete_draft", "gmail_send_draft", "gmail_send_message"
574
+ ] },
575
+ readToolPatterns: [
576
+ "gmail_get_profile", "gmail_list_messages", "gmail_get_message", "gmail_get_attachment",
577
+ "gmail_list_threads", "gmail_get_thread", "gmail_list_labels", "gmail_get_label",
578
+ "gmail_list_drafts", "gmail_get_draft"
579
+ ],
580
+ writeToolPatterns: ["gmail_create_draft", "gmail_update_draft", "gmail_delete_draft", "gmail_send_draft", "gmail_send_message"],
581
+ eventCatalog: ["email.received"],
582
+ defaultEvents: ["email.received"],
583
+ eventMode: "watch",
584
+ eventScope: "principal",
585
+ eventRequiredEnv: ["GOOGLE_CLOUD_PROJECT", "GMAIL_PUBSUB_TOPIC", "GMAIL_PUBSUB_VERIFICATION_TOKEN"],
586
+ setup: [{
587
+ kind: "connection",
588
+ name: "gmail-oauth-configuration",
589
+ required: true,
590
+ message: "Create a Google OAuth web client, enable the Gmail API, set GOOGLE_CLIENT_ID and GOOGLE_CLIENT_SECRET, and register the Assembly Line connection callback URL. Gmail authorization is stored as its own connection grant."
591
+ }]
592
+ },
593
+ {
522
594
  kind: "google-calendar",
523
- displayName: "Google Calendar",
595
+ role: "connection",
596
+ packageName: "@assemblyline-agents/google-calendar",
524
597
  helper: "defineGoogleCalendarConnection",
598
+ protocol: "http",
525
599
  provider: "google_calendar",
526
- description: "Google Calendar events, availability, and event changes through an independently authorized MCP connection.",
527
- urlEnv: "GOOGLE_CALENDAR_MCP_URL",
528
- tokenEnv: "GOOGLE_CALENDAR_MCP_TOKEN",
600
+ description: "Google Calendar lists, events, availability, and scheduling through the Google Calendar REST API.",
601
+ defaultBaseUrl: "https://www.googleapis.com/calendar/v3",
602
+ baseUrlEnv: "GOOGLE_CALENDAR_API_BASE_URL",
603
+ requiredEnv: ["GOOGLE_CLIENT_ID", "GOOGLE_CLIENT_SECRET"],
604
+ optionalEnv: ["GOOGLE_REDIRECT_URI", "GOOGLE_CALENDAR_API_BASE_URL"],
605
+ capabilities: ["http-api", "oauth", "pkce", "refresh-token", "live-tools"],
529
606
  scopes: [
530
- "openid",
531
- "email",
532
- "profile",
533
607
  "https://www.googleapis.com/auth/calendar.readonly",
534
608
  "https://www.googleapis.com/auth/calendar.events"
535
609
  ],
536
- readToolPatterns: ["rest_get", ...READ_PATTERNS],
537
- writeToolPatterns: ["rest_request", ...WRITE_PATTERNS],
538
- write: true,
539
- setupMessage: "Configure a Google Calendar-only OAuth grant or MCP bridge for this deployment. Do not reuse an umbrella Google grant that also exposes Gmail or Drive."
540
- }),
541
- catalogEntry({
610
+ subject: "user",
611
+ tools: { allow: [
612
+ "google_calendar_list_calendars", "google_calendar_get_calendar", "google_calendar_list_events",
613
+ "google_calendar_get_event", "google_calendar_list_instances", "google_calendar_query_freebusy",
614
+ "google_calendar_create_event", "google_calendar_update_event", "google_calendar_delete_event", "google_calendar_move_event"
615
+ ] },
616
+ readToolPatterns: [
617
+ "google_calendar_list_calendars", "google_calendar_get_calendar", "google_calendar_list_events",
618
+ "google_calendar_get_event", "google_calendar_list_instances", "google_calendar_query_freebusy"
619
+ ],
620
+ writeToolPatterns: ["google_calendar_create_event", "google_calendar_update_event", "google_calendar_delete_event", "google_calendar_move_event"],
621
+ eventCatalog: ["calendar.changed"],
622
+ defaultEvents: ["calendar.changed"],
623
+ eventMode: "watch",
624
+ eventScope: "principal",
625
+ setup: [{
626
+ kind: "connection",
627
+ name: "google-calendar-oauth-configuration",
628
+ required: true,
629
+ message: "Create a Google OAuth web client, enable the Google Calendar API, set GOOGLE_CLIENT_ID and GOOGLE_CLIENT_SECRET, and register the Assembly Line connection callback URL. Calendar authorization is stored as its own connection grant."
630
+ }]
631
+ },
632
+ {
542
633
  kind: "google-drive",
543
- displayName: "Google Drive",
634
+ role: "connection",
635
+ packageName: "@assemblyline-agents/google-drive",
544
636
  helper: "defineGoogleDriveConnection",
637
+ protocol: "http",
545
638
  provider: "google_drive",
546
- description: "Google Drive file search, downloads, uploads, organization, and sharing through an independently authorized MCP connection.",
547
- urlEnv: "GOOGLE_DRIVE_MCP_URL",
548
- tokenEnv: "GOOGLE_DRIVE_MCP_TOKEN",
639
+ description: "Google Drive file search, downloads, uploads, organization, and sharing through the Google Drive REST API.",
640
+ defaultBaseUrl: "https://www.googleapis.com",
641
+ baseUrlEnv: "GOOGLE_DRIVE_API_BASE_URL",
642
+ requiredEnv: ["GOOGLE_CLIENT_ID", "GOOGLE_CLIENT_SECRET"],
643
+ optionalEnv: ["GOOGLE_REDIRECT_URI", "GOOGLE_DRIVE_API_BASE_URL"],
644
+ capabilities: ["http-api", "oauth", "pkce", "refresh-token", "binary-transfer", "live-tools"],
549
645
  scopes: [
550
- "openid",
551
- "email",
552
- "profile",
646
+ "https://www.googleapis.com/auth/drive.readonly",
553
647
  "https://www.googleapis.com/auth/drive"
554
648
  ],
555
- readToolPatterns: ["rest_get", ...READ_PATTERNS],
556
- writeToolPatterns: ["rest_request", ...WRITE_PATTERNS],
557
- write: true,
558
- setupMessage: "Configure a Google Drive-only OAuth grant or MCP bridge for this deployment. Do not reuse an umbrella Google grant that also exposes Gmail or Calendar."
559
- }),
649
+ subject: "user",
650
+ tools: { allow: [
651
+ "google_drive_get_about", "google_drive_list_shared_drives", "google_drive_get_shared_drive",
652
+ "google_drive_list_files", "google_drive_get_file", "google_drive_download_file", "google_drive_export_file",
653
+ "google_drive_list_permissions", "google_drive_get_permission", "google_drive_create_file",
654
+ "google_drive_update_file", "google_drive_upload_file_content", "google_drive_copy_file", "google_drive_delete_file",
655
+ "google_drive_create_permission", "google_drive_update_permission", "google_drive_delete_permission"
656
+ ] },
657
+ readToolPatterns: [
658
+ "google_drive_get_about", "google_drive_list_shared_drives", "google_drive_get_shared_drive",
659
+ "google_drive_list_files", "google_drive_get_file", "google_drive_download_file", "google_drive_export_file",
660
+ "google_drive_list_permissions", "google_drive_get_permission"
661
+ ],
662
+ writeToolPatterns: [
663
+ "google_drive_create_file", "google_drive_update_file", "google_drive_upload_file_content", "google_drive_copy_file",
664
+ "google_drive_delete_file", "google_drive_create_permission", "google_drive_update_permission", "google_drive_delete_permission"
665
+ ],
666
+ eventCatalog: ["drive.changed"],
667
+ defaultEvents: ["drive.changed"],
668
+ eventMode: "watch",
669
+ eventScope: "principal",
670
+ setup: [{
671
+ kind: "connection",
672
+ name: "google-drive-oauth-configuration",
673
+ required: true,
674
+ message: "Create a Google OAuth web client, enable the Google Drive API, set GOOGLE_CLIENT_ID and GOOGLE_CLIENT_SECRET, and register the Assembly Line connection callback URL. Drive authorization is stored as its own connection grant."
675
+ }]
676
+ },
560
677
  catalogEntry({ kind: "github", displayName: "GitHub", helper: "defineGitHubMcpConnection", packageName: "@assemblyline-agents/github", description: "GitHub repositories, issues, pull requests, and Actions through GitHub MCP.", defaultUrl: "https://api.githubcopilot.com/mcp/", urlEnv: "GITHUB_MCP_URL", tokenEnv: "GITHUB_MCP_TOKEN", write: true }),
678
+ {
679
+ kind: "github-app",
680
+ role: "connection",
681
+ packageName: "@assemblyline-agents/github",
682
+ helper: "defineGitHubAppConnection",
683
+ protocol: "credential",
684
+ provider: "github",
685
+ description: "Host-only GitHub App installation credentials for Git and the GitHub CLI inside an agent sandbox.",
686
+ requiredEnv: [
687
+ "GITHUB_APP_ID",
688
+ "GITHUB_APP_PRIVATE_KEY"
689
+ ],
690
+ optionalEnv: [
691
+ "GITHUB_APP_INSTALLATION_ID",
692
+ "GITHUB_APP_SLUG",
693
+ "GITHUB_APP_CLIENT_ID",
694
+ "GITHUB_APP_CLIENT_SECRET",
695
+ "GITHUB_APP_WEBHOOK_SECRET",
696
+ "GITHUB_API_URL",
697
+ "GITHUB_OAUTH_URL"
698
+ ],
699
+ capabilities: ["sandbox-credentials", "github-app", "git", "github-cli"],
700
+ scopes: [],
701
+ subject: "user",
702
+ readToolPatterns: [],
703
+ writeToolPatterns: [],
704
+ eventCatalog: [
705
+ "issues.opened", "issues.edited", "issues.closed", "issue_comment.created",
706
+ "pull_request.opened", "pull_request.synchronize", "pull_request.closed",
707
+ "pull_request_review.submitted", "push", "workflow_run.completed",
708
+ "installation.created", "installation.deleted", "installation_repositories.added",
709
+ "installation_repositories.removed"
710
+ ],
711
+ defaultEvents: ["issues.opened", "issue_comment.created", "pull_request.opened", "pull_request_review.submitted", "push", "workflow_run.completed"],
712
+ eventMode: "manual",
713
+ eventScope: "connection",
714
+ eventRequiredEnv: ["GITHUB_APP_WEBHOOK_SECRET"],
715
+ setup: [{
716
+ kind: "connection",
717
+ name: "github-app-developer-configuration",
718
+ required: true,
719
+ message: "Create and install a GitHub App, choose its repository access and permissions in GitHub, then store its credentials in the Assembly Line host secret store."
720
+ }]
721
+ },
561
722
  catalogEntry({ kind: "slack", displayName: "Slack", helper: "defineSlackConnection", packageName: "@assemblyline-agents/slack", description: "Slack workspace search, channels, messages, files, and users through Slack MCP.", defaultUrl: "https://mcp.slack.com/mcp", urlEnv: "SLACK_MCP_URL", tokenEnv: "SLACK_MCP_TOKEN", write: true }),
562
723
  catalogEntry({ kind: "telegram", displayName: "Telegram", helper: "defineTelegramConnection", packageName: "@assemblyline-agents/telegram", description: "Telegram account tools through a developer-operated MCP bridge.", urlEnv: "TELEGRAM_MCP_URL", tokenEnv: "TELEGRAM_MCP_TOKEN" }),
563
- catalogEntry({ kind: "strava", displayName: "Strava", helper: "defineStravaConnection", description: "Strava profile and fitness activity tools through a developer-configured MCP server.", urlEnv: "STRAVA_MCP_URL", tokenEnv: "STRAVA_MCP_TOKEN" }),
564
- catalogEntry({ kind: "polar", displayName: "Polar", helper: "definePolarConnection", description: "Polar workout and heart-rate tools through a developer-configured MCP server.", urlEnv: "POLAR_MCP_URL", tokenEnv: "POLAR_MCP_TOKEN" }),
724
+ catalogEntry({
725
+ kind: "strava", displayName: "Strava", helper: "defineStravaConnection",
726
+ description: "Strava profile and fitness activity tools through a developer-configured MCP server.", urlEnv: "STRAVA_MCP_URL", tokenEnv: "STRAVA_MCP_TOKEN",
727
+ eventCatalog: ["activity.create", "activity.update", "activity.delete", "athlete.update"],
728
+ defaultEvents: ["activity.create", "activity.update", "activity.delete", "athlete.update"], eventMode: "api", eventScope: "connection",
729
+ eventRequiredEnv: ["STRAVA_CLIENT_ID", "STRAVA_CLIENT_SECRET", "STRAVA_WEBHOOK_SIGNING_SECRET"]
730
+ }),
731
+ catalogEntry({
732
+ kind: "polar", displayName: "Polar", helper: "definePolarConnection",
733
+ description: "Polar workout and heart-rate tools through a developer-configured MCP server.", urlEnv: "POLAR_MCP_URL", tokenEnv: "POLAR_MCP_TOKEN",
734
+ eventCatalog: ["EXERCISE", "SLEEP", "CONTINUOUS_HEART_RATE", "SLEEP_WISE_CIRCADIAN_BEDTIME", "SLEEP_WISE_ALERTNESS", "ACTIVITY_SUMMARY", "PHYSICAL_INFORMATION"],
735
+ defaultEvents: ["EXERCISE", "SLEEP", "CONTINUOUS_HEART_RATE"], eventMode: "api", eventScope: "connection",
736
+ eventRequiredEnv: ["POLAR_CLIENT_ID", "POLAR_CLIENT_SECRET"]
737
+ }),
565
738
  catalogEntry({ kind: "spotify", displayName: "Spotify", helper: "defineSpotifyConnection", description: "Spotify library, playlist, and playback tools through a developer-configured MCP server.", urlEnv: "SPOTIFY_MCP_URL", tokenEnv: "SPOTIFY_MCP_TOKEN", write: true }),
566
739
  catalogEntry({ kind: "xai", displayName: "xAI", helper: "defineXaiConnection", description: "xAI and X search tools through a developer-configured MCP server.", urlEnv: "XAI_MCP_URL", tokenEnv: "XAI_MCP_TOKEN" }),
567
740
  catalogEntry({
@@ -586,24 +759,203 @@ const CONNECTION_PLUGIN_CATALOG = [
586
759
  "web_fetch_exa",
587
760
  "web_search_advanced_exa"
588
761
  ],
589
- setupMessage: "Exa's hosted MCP works without credentials. Optionally set EXA_API_KEY to raise production rate limits; OpenEve sends it only as the x-api-key header."
762
+ setupMessage: "Exa's hosted MCP works without credentials. Optionally set EXA_API_KEY to raise production rate limits; Assembly Line sends it only as the x-api-key header."
763
+ }),
764
+ catalogEntry({
765
+ kind: "plaid", displayName: "Plaid", helper: "definePlaidConnection",
766
+ description: "Read-only Plaid financial tools through a developer-configured MCP bridge.", urlEnv: "PLAID_MCP_URL", tokenEnv: "PLAID_MCP_TOKEN",
767
+ eventCatalog: ["transactions.changed", "item.changed", "auth.changed", "identity.changed", "assets.changed", "holdings.changed", "investments.changed", "liabilities.changed", "payment.changed", "transfer.changed", "income.changed"],
768
+ defaultEvents: ["transactions.changed", "item.changed"], eventMode: "api", eventScope: "connection",
769
+ eventRequiredEnv: ["PLAID_CLIENT_ID", "PLAID_SECRET"]
590
770
  }),
591
- catalogEntry({ kind: "plaid", displayName: "Plaid", helper: "definePlaidConnection", description: "Read-only Plaid financial tools through a developer-configured MCP bridge.", urlEnv: "PLAID_MCP_URL", tokenEnv: "PLAID_MCP_TOKEN" }),
592
771
  catalogEntry({ kind: "granola", displayName: "Granola", helper: "defineGranolaConnection", description: "Granola meeting notes, transcripts, and action items through Granola MCP.", defaultUrl: "https://mcp.granola.ai/mcp", urlEnv: "GRANOLA_MCP_URL", tokenEnv: "GRANOLA_MCP_TOKEN" }),
593
- catalogEntry({ kind: "linear", displayName: "Linear", helper: "defineLinearConnection", description: "Linear issues, projects, cycles, and teams through Linear MCP.", defaultUrl: "https://mcp.linear.app/mcp", urlEnv: "LINEAR_MCP_URL", tokenEnv: "LINEAR_MCP_TOKEN", write: true }),
594
- catalogEntry({ kind: "notion", displayName: "Notion", helper: "defineNotionConnection", description: "Notion pages, databases, comments, and workspace search through Notion MCP.", defaultUrl: "https://mcp.notion.com/mcp", urlEnv: "NOTION_MCP_URL", tokenEnv: "NOTION_MCP_TOKEN", write: true }),
595
- catalogEntry({ kind: "monday", displayName: "monday.com", helper: "defineMondayConnection", description: "monday.com boards, items, workspaces, and docs through Platform MCP.", defaultUrl: "https://mcp.monday.com/mcp", urlEnv: "MONDAY_MCP_URL", tokenEnv: "MONDAY_MCP_TOKEN", write: true }),
596
- catalogEntry({ kind: "jira", displayName: "Jira", helper: "defineJiraConnection", description: "Jira issues, projects, transitions, and JQL search through Atlassian MCP.", defaultUrl: "https://mcp.atlassian.com/v1/mcp/authv2", urlEnv: "JIRA_MCP_URL", tokenEnv: "JIRA_MCP_TOKEN", write: true }),
597
- catalogEntry({ kind: "hubspot", displayName: "HubSpot", helper: "defineHubSpotConnection", description: "HubSpot CRM records and associations through HubSpot MCP.", defaultUrl: "https://mcp.hubspot.com", urlEnv: "HUBSPOT_MCP_URL", tokenEnv: "HUBSPOT_MCP_TOKEN" }),
598
- catalogEntry({ kind: "figma", displayName: "Figma", helper: "defineFigmaConnection", description: "Figma design, FigJam, Slides, and Dev Mode context through Figma MCP.", defaultUrl: "https://mcp.figma.com/mcp", urlEnv: "FIGMA_MCP_URL", tokenEnv: "FIGMA_MCP_TOKEN", write: true }),
772
+ {
773
+ kind: "grata",
774
+ role: "connection",
775
+ packageName: "@assemblyline-agents/grata",
776
+ helper: "defineGrataConnection",
777
+ protocol: "mcp",
778
+ transport: "http",
779
+ provider: "grata",
780
+ description: "Private-company, ownership, funding, transaction, filing, contact, conference, and deal intelligence through Grata's official hosted MCP server.",
781
+ defaultUrl: "https://mcp.grata.com",
782
+ urlEnv: "GRATA_MCP_URL",
783
+ requiredEnv: ["GRATA_MCP_CLIENT_ID", "GRATA_MCP_CLIENT_SECRET"],
784
+ optionalEnv: ["GRATA_MCP_URL", "GRATA_MCP_REDIRECT_URI"],
785
+ capabilities: ["mcp", "oauth", "pkce", "refresh-token", "live-tools", "streamable-http", "private-market-intelligence"],
786
+ scopes: ["openid", "profile", "email", "offline_access"],
787
+ subject: "user",
788
+ readToolPatterns: READ_PATTERNS,
789
+ writeToolPatterns: [
790
+ ...WRITE_PATTERNS,
791
+ "regex:(^|[-_])export([-_]|$)"
792
+ ],
793
+ setup: [{
794
+ kind: "connection",
795
+ name: "grata-mcp-oauth",
796
+ required: true,
797
+ message: "Register an OAuth client using client_secret_post with the selected Grata MCP region's /register endpoint for the Assembly Line connection callback, set GRATA_MCP_CLIENT_ID and GRATA_MCP_CLIENT_SECRET, then let each user authorize their Grata seat. Set GRATA_MCP_URL=https://eu-mcp.grata.com/ for European users."
798
+ }]
799
+ },
800
+ catalogEntry({
801
+ kind: "linear", displayName: "Linear", helper: "defineLinearConnection",
802
+ description: "Linear issues, projects, cycles, and teams through Linear MCP.", defaultUrl: "https://mcp.linear.app/mcp", urlEnv: "LINEAR_MCP_URL", tokenEnv: "LINEAR_MCP_TOKEN", write: true,
803
+ eventCatalog: ["issue.create", "issue.update", "issue.remove", "comment.create", "comment.update", "comment.remove", "project.create", "project.update", "project.remove", "cycle.create", "cycle.update", "cycle.remove", "document.create", "document.update", "document.remove", "customer.create", "customer.update", "customer.remove", "user.create", "user.update", "user.remove", "agentSessionEvent.created", "agentSessionEvent.prompted", "linear.changed"],
804
+ defaultEvents: ["issue.create", "issue.update", "comment.create", "comment.update", "project.update", "agentSessionEvent.created", "agentSessionEvent.prompted", "linear.changed"],
805
+ eventMode: "manual", eventScope: "principal", eventRequiredEnv: ["LINEAR_WEBHOOK_SECRET"]
806
+ }),
807
+ catalogEntry({
808
+ kind: "notion", displayName: "Notion", helper: "defineNotionConnection",
809
+ description: "Notion pages, databases, comments, and workspace search through Notion MCP.", defaultUrl: "https://mcp.notion.com/mcp", urlEnv: "NOTION_MCP_URL", tokenEnv: "NOTION_MCP_TOKEN", write: true,
810
+ eventCatalog: [
811
+ "page.content_updated", "page.created", "page.deleted", "page.locked", "page.moved", "page.properties_updated", "page.undeleted", "page.unlocked",
812
+ "database.content_updated", "database.created", "database.deleted", "database.moved", "database.schema_updated", "database.undeleted",
813
+ "data_source.content_updated", "data_source.created", "data_source.deleted", "data_source.moved", "data_source.schema_updated", "data_source.undeleted",
814
+ "comment.created", "comment.deleted", "comment.updated"
815
+ ],
816
+ defaultEvents: ["page.content_updated", "page.created", "page.deleted", "page.properties_updated", "data_source.schema_updated", "comment.created"],
817
+ eventMode: "manual", eventScope: "principal"
818
+ }),
819
+ catalogEntry({
820
+ kind: "monday", displayName: "monday.com", helper: "defineMondayConnection",
821
+ description: "monday.com boards, items, workspaces, and docs through Platform MCP.", defaultUrl: "https://mcp.monday.com/mcp", urlEnv: "MONDAY_MCP_URL", tokenEnv: "MONDAY_MCP_TOKEN", write: true,
822
+ eventCatalog: ["create_item", "change_column_value", "change_status_column_value", "change_name", "item_moved_to_any_group", "item_deleted", "item_archived", "create_update"],
823
+ defaultEvents: ["create_item", "change_column_value", "change_status_column_value", "item_deleted", "create_update"], eventMode: "api", eventScope: "principal",
824
+ eventRequiredEnv: ["MONDAY_SIGNING_SECRET"]
825
+ }),
826
+ catalogEntry({
827
+ kind: "jira", displayName: "Jira", helper: "defineJiraConnection",
828
+ description: "Jira issues, projects, transitions, and JQL search through Atlassian MCP.", defaultUrl: "https://mcp.atlassian.com/v1/mcp/authv2", urlEnv: "JIRA_MCP_URL", tokenEnv: "JIRA_MCP_TOKEN", write: true,
829
+ eventCatalog: ["jira:issue_created", "jira:issue_updated", "jira:issue_deleted", "comment_created", "comment_updated", "comment_deleted", "issue_property_set", "issue_property_deleted"],
830
+ defaultEvents: ["jira:issue_created", "jira:issue_updated", "comment_created", "comment_updated"], eventMode: "api", eventScope: "principal"
831
+ }),
832
+ catalogEntry({
833
+ kind: "hubspot", displayName: "HubSpot", helper: "defineHubSpotConnection",
834
+ description: "HubSpot CRM records and associations through HubSpot MCP.", defaultUrl: "https://mcp.hubspot.com", urlEnv: "HUBSPOT_MCP_URL", tokenEnv: "HUBSPOT_MCP_TOKEN",
835
+ eventCatalog: ["contact.creation", "contact.deletion", "contact.propertyChange", "company.creation", "company.deletion", "company.propertyChange", "deal.creation", "deal.deletion", "deal.propertyChange", "ticket.creation", "ticket.deletion", "ticket.propertyChange"],
836
+ defaultEvents: ["contact.creation", "contact.deletion", "company.creation", "company.deletion", "deal.creation", "deal.deletion", "ticket.creation", "ticket.deletion"],
837
+ eventMode: "api", eventScope: "connection", eventRequiredEnv: ["HUBSPOT_APP_ID", "HUBSPOT_DEVELOPER_API_KEY", "HUBSPOT_CLIENT_SECRET"]
838
+ }),
839
+ catalogEntry({
840
+ kind: "figma", displayName: "Figma", helper: "defineFigmaConnection",
841
+ description: "Figma design, FigJam, Slides, and Dev Mode context through Figma MCP.",
842
+ defaultUrl: "https://mcp.figma.com/mcp", urlEnv: "FIGMA_MCP_URL", tokenEnv: "FIGMA_MCP_TOKEN", write: true,
843
+ eventCatalog: ["FILE_UPDATE", "FILE_DELETE", "FILE_VERSION_UPDATE", "LIBRARY_PUBLISH"],
844
+ defaultEvents: ["FILE_UPDATE", "FILE_DELETE"], eventMode: "api", eventScope: "principal"
845
+ }),
599
846
  catalogEntry({ kind: "paper", displayName: "Paper", helper: "definePaperConnection", description: "Paper design tools through a developer-exposed local MCP bridge.", urlEnv: "PAPER_MCP_URL", tokenEnv: "PAPER_MCP_TOKEN", tokenRequired: false, write: true }),
600
- catalogEntry({ kind: "sentry", displayName: "Sentry", helper: "defineSentryConnection", description: "Sentry issues, events, projects, and teams through Sentry MCP.", defaultUrl: "https://mcp.sentry.dev/mcp", urlEnv: "SENTRY_MCP_URL", tokenEnv: "SENTRY_MCP_TOKEN", write: true }),
601
- catalogEntry({ kind: "supabase", displayName: "Supabase", helper: "defineSupabaseConnection", description: "Supabase projects, databases, docs, and Edge Functions through Supabase MCP.", defaultUrl: "https://mcp.supabase.com/mcp", urlEnv: "SUPABASE_MCP_URL", tokenEnv: "SUPABASE_MCP_TOKEN", write: true }),
602
- catalogEntry({ kind: "metabase", displayName: "Metabase", helper: "defineMetabaseConnection", description: "Metabase semantic-layer queries, questions, and dashboards through an instance MCP endpoint.", urlEnv: "METABASE_MCP_URL", tokenEnv: "METABASE_MCP_TOKEN", tokenRequired: false, write: true }),
603
- catalogEntry({ kind: "cloudflare", displayName: "Cloudflare", helper: "defineCloudflareConnection", description: "Cloudflare API and account tools through Cloudflare MCP.", defaultUrl: "https://mcp.cloudflare.com/mcp", urlEnv: "CLOUDFLARE_MCP_URL", tokenEnv: "CLOUDFLARE_MCP_TOKEN", write: true }),
604
- catalogEntry({ kind: "vercel", displayName: "Vercel", helper: "defineVercelConnection", description: "Vercel projects, deployments, logs, and teams through Vercel MCP.", defaultUrl: "https://mcp.vercel.com", urlEnv: "VERCEL_MCP_URL", tokenEnv: "VERCEL_MCP_TOKEN", write: true }),
605
- catalogEntry({ kind: "railway", displayName: "Railway", helper: "defineRailwayConnection", packageName: "@assemblyline-agents/railway", description: "Railway projects, services, variables, and deployments through Railway MCP.", defaultUrl: "https://mcp.railway.com", urlEnv: "RAILWAY_MCP_URL", tokenEnv: "RAILWAY_MCP_TOKEN", write: true }),
847
+ catalogEntry({
848
+ kind: "sentry", displayName: "Sentry", helper: "defineSentryConnection",
849
+ description: "Sentry issues, events, projects, and teams through Sentry MCP.", defaultUrl: "https://mcp.sentry.dev/mcp", urlEnv: "SENTRY_MCP_URL", tokenEnv: "SENTRY_MCP_TOKEN", write: true,
850
+ eventCatalog: ["event.created", "event.alert"], defaultEvents: ["event.created", "event.alert"], eventMode: "api", eventScope: "principal"
851
+ }),
852
+ catalogEntry({
853
+ kind: "supabase", displayName: "Supabase", helper: "defineSupabaseConnection",
854
+ description: "Supabase projects, databases, docs, and Edge Functions through Supabase MCP.", defaultUrl: "https://mcp.supabase.com/mcp", urlEnv: "SUPABASE_MCP_URL", tokenEnv: "SUPABASE_MCP_TOKEN", write: true,
855
+ eventCatalog: ["row.inserted", "row.updated", "row.deleted"], defaultEvents: ["row.inserted", "row.updated", "row.deleted"], eventMode: "api", eventScope: "principal",
856
+ eventRequiredEnv: ["SUPABASE_WEBHOOK_SECRET"]
857
+ }),
858
+ catalogEntry({
859
+ kind: "metabase", displayName: "Metabase", helper: "defineMetabaseConnection",
860
+ description: "Metabase semantic-layer queries, questions, and dashboards through an instance MCP endpoint.", urlEnv: "METABASE_MCP_URL", tokenEnv: "METABASE_MCP_TOKEN", tokenRequired: false, write: true,
861
+ eventCatalog: ["alert.triggered"], defaultEvents: ["alert.triggered"], eventMode: "manual", eventScope: "connection",
862
+ eventRequiredEnv: ["METABASE_WEBHOOK_SECRET"]
863
+ }),
864
+ catalogEntry({
865
+ kind: "cloudflare", displayName: "Cloudflare", helper: "defineCloudflareConnection",
866
+ description: "Cloudflare API and account tools through Cloudflare MCP.", defaultUrl: "https://mcp.cloudflare.com/mcp", urlEnv: "CLOUDFLARE_MCP_URL", tokenEnv: "CLOUDFLARE_MCP_TOKEN", write: true,
867
+ eventCatalog: ["notification.received"], defaultEvents: ["notification.received"], eventMode: "api", eventScope: "principal",
868
+ eventRequiredEnv: ["CLOUDFLARE_WEBHOOK_SECRET"]
869
+ }),
870
+ catalogEntry({
871
+ kind: "vercel", displayName: "Vercel", helper: "defineVercelConnection",
872
+ description: "Vercel projects, deployments, logs, and teams through Vercel MCP.", defaultUrl: "https://mcp.vercel.com", urlEnv: "VERCEL_MCP_URL", tokenEnv: "VERCEL_MCP_TOKEN", write: true,
873
+ eventCatalog: ["deployment.created", "deployment.succeeded", "deployment.promoted", "deployment.error", "deployment.cancelled", "project.created", "project.removed", "project.renamed", "project.env.created", "project.env.updated", "project.env.deleted", "firewall.attack.detected"],
874
+ defaultEvents: ["deployment.created", "deployment.succeeded", "deployment.error", "deployment.cancelled"], eventMode: "api", eventScope: "principal"
875
+ }),
876
+ catalogEntry({
877
+ kind: "railway", displayName: "Railway", helper: "defineRailwayConnection", packageName: "@assemblyline-agents/railway",
878
+ description: "Railway projects, services, variables, and deployments through Railway MCP.", defaultUrl: "https://mcp.railway.com", urlEnv: "RAILWAY_MCP_URL", tokenEnv: "RAILWAY_MCP_TOKEN", write: true,
879
+ eventCatalog: ["deployment.changed", "alert.triggered"], defaultEvents: ["deployment.changed", "alert.triggered"], eventMode: "manual", eventScope: "connection"
880
+ }),
606
881
  catalogEntry({ kind: "refero", displayName: "Refero", helper: "defineReferoConnection", description: "Refero design references, screens, and product flows through Refero MCP.", defaultUrl: "https://api.refero.design/mcp", urlEnv: "REFERO_MCP_URL", tokenEnv: "REFERO_MCP_BEARER_TOKEN" }),
882
+ catalogEntry({
883
+ kind: "agentmail",
884
+ displayName: "AgentMail",
885
+ helper: "defineAgentMailConnection",
886
+ description: "AgentMail inboxes, threads, messages, drafts, and attachments through the official hosted MCP server.",
887
+ defaultUrl: "https://mcp.agentmail.to/mcp",
888
+ urlEnv: "AGENTMAIL_MCP_URL",
889
+ tokenEnv: "AGENTMAIL_API_KEY",
890
+ tokenHeader: "x-api-key",
891
+ subject: "environment",
892
+ tools: {
893
+ allow: [
894
+ "list_inboxes",
895
+ "get_inbox",
896
+ "create_inbox",
897
+ "update_inbox",
898
+ "delete_inbox",
899
+ "list_threads",
900
+ "search_threads",
901
+ "get_thread",
902
+ "update_thread",
903
+ "delete_thread",
904
+ "list_messages",
905
+ "search_messages",
906
+ "send_message",
907
+ "reply_to_message",
908
+ "forward_message",
909
+ "update_message",
910
+ "create_draft",
911
+ "list_drafts",
912
+ "get_draft",
913
+ "update_draft",
914
+ "send_draft",
915
+ "delete_draft",
916
+ "get_attachment",
917
+ "auth_me"
918
+ ]
919
+ },
920
+ readToolPatterns: [
921
+ "list_inboxes",
922
+ "get_inbox",
923
+ "list_threads",
924
+ "search_threads",
925
+ "get_thread",
926
+ "list_messages",
927
+ "search_messages",
928
+ "list_drafts",
929
+ "get_draft",
930
+ "get_attachment",
931
+ "auth_me"
932
+ ],
933
+ writeToolPatterns: [
934
+ "create_inbox",
935
+ "update_inbox",
936
+ "delete_inbox",
937
+ "update_thread",
938
+ "delete_thread",
939
+ "send_message",
940
+ "reply_to_message",
941
+ "forward_message",
942
+ "update_message",
943
+ "create_draft",
944
+ "update_draft",
945
+ "send_draft",
946
+ "delete_draft"
947
+ ],
948
+ write: true,
949
+ eventCatalog: [
950
+ "message.received", "message.received.spam", "message.received.blocked",
951
+ "message.received.unauthenticated", "message.sent", "message.delivered",
952
+ "message.bounced", "message.complained", "message.rejected", "domain.verified"
953
+ ],
954
+ defaultEvents: ["message.received"],
955
+ eventMode: "api",
956
+ eventScope: "connection",
957
+ setupMessage: "Create an AgentMail API key, set AGENTMAIL_API_KEY on the Assembly Line runtime host, and keep inbox and sender scope owned by the provider account."
958
+ }),
607
959
  catalogEntry({
608
960
  kind: "resend",
609
961
  displayName: "Resend",
@@ -627,9 +979,134 @@ const CONNECTION_PLUGIN_CATALOG = [
627
979
  "regex:^(add|batch-add|batch-remove|cancel|compose|create|disconnect|duplicate|manage|publish|remove|revoke|send|update|verify)-"
628
980
  ],
629
981
  write: true,
982
+ eventCatalog: [
983
+ "email.sent", "email.delivered", "email.delivery_delayed", "email.failed",
984
+ "email.opened", "email.clicked", "email.bounced", "email.complained",
985
+ "email.received", "email.scheduled", "email.suppressed",
986
+ "domain.created", "domain.updated", "domain.deleted",
987
+ "contact.created", "contact.updated", "contact.deleted"
988
+ ],
989
+ defaultEvents: ["email.received", "email.delivered", "email.failed", "email.bounced"],
990
+ eventMode: "api",
991
+ eventScope: "connection",
630
992
  setupMessage: "Create a team-scoped Resend API key, set RESEND_API_KEY on the Assembly Line runtime host, and verify the sending domain. Full-platform reads require a full_access key; restrict the connection's visible tools when using a sending_access key."
631
993
  }),
632
994
  catalogEntry({ kind: "agentcash", displayName: "AgentCash", helper: "defineAgentCashConnection", description: "Paid API discovery, schema, balance, and request tools through an AgentCash MCP bridge.", urlEnv: "AGENTCASH_MCP_URL", tokenEnv: "AGENTCASH_MCP_BRIDGE_TOKEN", write: true }),
995
+ catalogEntry({
996
+ kind: "treg",
997
+ displayName: "Treg",
998
+ helper: "defineTregConnection",
999
+ description: "External API discovery, pricing, balance, team inventory, and credential-injected calls through Treg's hosted tool catalog.",
1000
+ defaultUrl: "https://treg.to/mcp/",
1001
+ urlEnv: "TREG_MCP_URL",
1002
+ tokenEnv: "TREG_TOKEN",
1003
+ tools: {
1004
+ allow: [
1005
+ "catalog_search",
1006
+ "catalog_get",
1007
+ "catalog_request",
1008
+ "call",
1009
+ "balance",
1010
+ "my_tools"
1011
+ ]
1012
+ },
1013
+ readToolPatterns: ["catalog_search", "catalog_get", "balance", "my_tools"],
1014
+ writeToolPatterns: ["catalog_request", "call"],
1015
+ write: true,
1016
+ setupMessage: "Create an organization-scoped or agent token in Treg, set TREG_TOKEN on the Assembly Line runtime, and review whether Treg writes require approval. The call tool can spend prepaid balance or mutate an upstream service."
1017
+ }),
1018
+ {
1019
+ kind: "x",
1020
+ role: "connection",
1021
+ packageName: "@assemblyline-agents/x",
1022
+ helper: "defineXConnection",
1023
+ protocol: "http",
1024
+ provider: "x",
1025
+ description: "Connected X account identity, private bookmarks, and reviewed post or reply publishing through X API v2.",
1026
+ defaultBaseUrl: "https://api.x.com/2",
1027
+ baseUrlEnv: "X_API_BASE_URL",
1028
+ requiredEnv: ["X_API_CLIENT_ID", "X_API_CLIENT_SECRET"],
1029
+ optionalEnv: ["X_API_REDIRECT_URI", "X_API_BASE_URL"],
1030
+ capabilities: ["http-api", "oauth", "pkce", "refresh-token", "live-tools", "bookmarks", "publishing"],
1031
+ scopes: ["bookmark.read", "tweet.read", "tweet.write", "users.read", "offline.access"],
1032
+ subject: "user",
1033
+ tools: {
1034
+ allow: ["x_get_authenticated_user", "x_list_bookmarks", "x_create_post"]
1035
+ },
1036
+ readToolPatterns: ["x_get_authenticated_user", "x_list_bookmarks"],
1037
+ writeToolPatterns: ["x_create_post"],
1038
+ setup: [{
1039
+ kind: "connection",
1040
+ name: "x-developer-configuration",
1041
+ required: true,
1042
+ message: "Create a confidential X OAuth 2.0 App, enable the reviewed bookmark and post scopes, set X_API_CLIENT_ID and X_API_CLIENT_SECRET, and register the Assembly Line connection callback URL. Authorization Code + PKCE stores a refreshable per-user grant; X API usage and costs remain developer-owned."
1043
+ }]
1044
+ },
1045
+ {
1046
+ kind: "dropbox",
1047
+ role: "connection",
1048
+ packageName: "@assemblyline-agents/dropbox",
1049
+ helper: "defineDropboxConnection",
1050
+ protocol: "http",
1051
+ provider: "dropbox",
1052
+ description: "Dropbox account, file and folder metadata, search, temporary content links, and reviewed file operations through the Dropbox API.",
1053
+ defaultBaseUrl: "https://api.dropboxapi.com/2",
1054
+ baseUrlEnv: "DROPBOX_API_BASE_URL",
1055
+ requiredEnv: ["DROPBOX_APP_KEY", "DROPBOX_APP_SECRET"],
1056
+ optionalEnv: ["DROPBOX_REDIRECT_URI", "DROPBOX_API_BASE_URL"],
1057
+ capabilities: ["http-api", "oauth", "pkce", "refresh-token", "live-tools"],
1058
+ scopes: [
1059
+ "account_info.read",
1060
+ "files.metadata.read",
1061
+ "files.content.read",
1062
+ "files.content.write",
1063
+ "sharing.read",
1064
+ "sharing.write"
1065
+ ],
1066
+ subject: "user",
1067
+ tools: {
1068
+ allow: [
1069
+ "users_get_current_account",
1070
+ "users_get_space_usage",
1071
+ "files_get_metadata",
1072
+ "files_list_folder",
1073
+ "files_list_folder_continue",
1074
+ "files_search_v2",
1075
+ "files_search_continue_v2",
1076
+ "files_get_temporary_link",
1077
+ "sharing_list_shared_links",
1078
+ "files_create_folder_v2",
1079
+ "files_copy_v2",
1080
+ "files_move_v2",
1081
+ "files_delete_v2",
1082
+ "sharing_create_shared_link_with_settings"
1083
+ ]
1084
+ },
1085
+ readToolPatterns: [
1086
+ "users_get_current_account",
1087
+ "users_get_space_usage",
1088
+ "files_get_metadata",
1089
+ "files_list_folder",
1090
+ "files_list_folder_continue",
1091
+ "files_search_v2",
1092
+ "files_search_continue_v2",
1093
+ "files_get_temporary_link",
1094
+ "sharing_list_shared_links"
1095
+ ],
1096
+ writeToolPatterns: [
1097
+ "files_create_folder_v2",
1098
+ "files_copy_v2",
1099
+ "files_move_v2",
1100
+ "files_delete_v2",
1101
+ "sharing_create_shared_link_with_settings"
1102
+ ],
1103
+ setup: [{
1104
+ kind: "connection",
1105
+ name: "dropbox-developer-configuration",
1106
+ required: true,
1107
+ message: "Register one Dropbox API app, enable the scopes required by this connection, set DROPBOX_APP_KEY and DROPBOX_APP_SECRET, and register the Assembly Line connection callback URL. OAuth Authorization Code + PKCE requests offline access for refreshable user grants."
1108
+ }]
1109
+ },
633
1110
  {
634
1111
  kind: "soundcloud",
635
1112
  role: "connection",
@@ -648,12 +1125,11 @@ const CONNECTION_PLUGIN_CATALOG = [
648
1125
  tools: { block: ["post_tracks"] },
649
1126
  readToolPatterns: ["regex:^get_"],
650
1127
  writeToolPatterns: ["regex:^(post|put|patch|delete)_"],
651
- skill: "soundcloud",
652
1128
  setup: [{
653
1129
  kind: "connection",
654
1130
  name: "soundcloud-developer-configuration",
655
1131
  required: true,
656
- message: "Register a SoundCloud application and set SOUNDCLOUD_CLIENT_ID and SOUNDCLOUD_CLIENT_SECRET. OpenEve handles OAuth 2.1 PKCE; the developer owns the app and redirect URI."
1132
+ message: "Register a SoundCloud application and set SOUNDCLOUD_CLIENT_ID and SOUNDCLOUD_CLIENT_SECRET. Assembly Line handles OAuth 2.1 PKCE; the developer owns the app and redirect URI."
657
1133
  }]
658
1134
  },
659
1135
  catalogEntry({
@@ -668,7 +1144,12 @@ const CONNECTION_PLUGIN_CATALOG = [
668
1144
  tools: { allow: ["get_session", "get_session_messages", "list_sessions", "list_browser_profiles", "run_session", "send_task", "stop_session"] },
669
1145
  readToolPatterns: ["get_session", "get_session_messages", "list_sessions", "list_browser_profiles"],
670
1146
  writeToolPatterns: ["run_session", "send_task", "stop_session"],
671
- setupMessage: "Set BROWSER_USE_API_KEY for the OpenEve host. Browser profiles, cost limits, and write authority remain developer-controlled."
1147
+ eventCatalog: ["agent.task.status_update"],
1148
+ defaultEvents: ["agent.task.status_update"],
1149
+ eventMode: "manual",
1150
+ eventScope: "connection",
1151
+ eventRequiredEnv: ["BROWSER_USE_WEBHOOK_SECRET"],
1152
+ setupMessage: "Set BROWSER_USE_API_KEY for the Assembly Line host. Browser profiles, cost limits, and write authority remain developer-controlled."
672
1153
  }),
673
1154
  catalogEntry({
674
1155
  kind: "orgo",
@@ -723,7 +1204,7 @@ const CONNECTION_PLUGIN_CATALOG = [
723
1204
  "execute_python"
724
1205
  ],
725
1206
  optionalEnv: ["ORGO_API_BASE_URL"],
726
- setupMessage: "Set ORGO_API_KEY on the OpenEve runtime host. The developer owns Orgo workspaces, account limits, auto-stop policy, login state, and billing; the packaged bridge strips VNC credentials from results."
1207
+ setupMessage: "Set ORGO_API_KEY on the Assembly Line runtime host. The developer owns Orgo workspaces, account limits, auto-stop policy, login state, and billing; the packaged bridge strips VNC credentials from results."
727
1208
  }),
728
1209
  catalogEntry({
729
1210
  kind: "peekaboo",
@@ -740,22 +1221,22 @@ const CONNECTION_PLUGIN_CATALOG = [
740
1221
  },
741
1222
  readToolPatterns: ["inspect_ui", "list", "permissions"],
742
1223
  writeToolPatterns: ["click", "type", "hotkey", "scroll", "drag", "swipe", "move", "set_value", "perform_action", "app", "window", "menu", "dock", "dialog", "space"],
743
- setupMessage: "Local deployment only: install Peekaboo on the OpenEve Mac (macOS 15+), grant that host process Accessibility and Screen Recording permissions, and use the local deploy target. Hosted targets are rejected."
1224
+ setupMessage: "Local deployment only: install Peekaboo on the Assembly Line Mac (macOS 15+), grant that host process Accessibility and Screen Recording permissions, and use the local deploy target. Hosted targets are rejected."
744
1225
  }),
745
1226
  catalogEntry({
746
1227
  kind: "computer-use",
747
- displayName: "OpenEve Computer Use",
1228
+ displayName: "Assembly Line Computer Use",
748
1229
  helper: "defineComputerUseConnection",
749
- description: "End-to-end encrypted accessibility and input automation on a paired Mac through the OpenEve device relay.",
1230
+ description: "End-to-end encrypted accessibility and input automation on a paired Mac through the Assembly Line device relay.",
750
1231
  transport: "relay",
751
- defaultUrl: "https://computer-use.openeve.dev/v1",
752
- urlEnv: "OPENEVE_COMPUTER_USE_RELAY_URL",
753
- credentialEnv: "OPENEVE_COMPUTER_USE_BINDING",
1232
+ defaultUrl: "https://computer-use.artificialillumination.co/v1",
1233
+ urlEnv: "ASSEMBLY_LINE_COMPUTER_USE_RELAY_URL",
1234
+ credentialEnv: "ASSEMBLY_LINE_COMPUTER_USE_BINDING",
754
1235
  subject: "environment",
755
1236
  tools: { allow: ["inspect_ui", "list", "permissions", "click", "type", "hotkey", "scroll", "drag", "swipe", "move", "set_value", "perform_action", "app", "window", "menu", "dock", "dialog", "space"] },
756
1237
  readToolPatterns: ["inspect_ui", "list", "permissions"],
757
1238
  writeToolPatterns: ["click", "type", "hotkey", "scroll", "drag", "swipe", "move", "set_value", "perform_action", "app", "window", "menu", "dock", "dialog", "space"],
758
- setupMessage: "Install OpenEve Agent Builder on the Mac, enable Computer Host, pair this deployment, and set the generated OPENEVE_COMPUTER_USE_BINDING secret on the remote runtime. The binding is device-scoped and must not be placed in prompts or source control."
1239
+ setupMessage: "Install Assembly Line Agent Builder on the Mac, enable Computer Host, pair this deployment, and set the generated ASSEMBLY_LINE_COMPUTER_USE_BINDING secret on the remote runtime. The binding is device-scoped and must not be placed in prompts or source control."
759
1240
  }),
760
1241
  catalogEntry({
761
1242
  kind: "ffmpeg",
@@ -784,101 +1265,18 @@ const CONNECTION_PLUGIN_CATALOG = [
784
1265
  "extract_frames",
785
1266
  "reframe_vertical"
786
1267
  ],
787
- setupMessage: "Install ffmpeg and ffprobe on the OpenEve runtime host. The plugin keeps all media paths inside its configured workspace root and exposes typed operations instead of arbitrary FFmpeg flags."
1268
+ setupMessage: "Install ffmpeg and ffprobe on the Assembly Line runtime host. The plugin keeps all media paths inside its configured workspace root and exposes typed operations instead of arbitrary FFmpeg flags."
788
1269
  }),
789
- catalogEntry({
790
- kind: "remotion",
791
- displayName: "Remotion",
792
- helper: "defineRemotionConnection",
793
- description: "Workspace-scoped Remotion composition discovery, version checks, video renders, and still renders through the project CLI.",
794
- transport: "stdio",
795
- subject: "environment",
796
- tools: {
797
- allow: [
798
- "list_compositions",
799
- "check_versions",
800
- "render_video",
801
- "render_still"
802
- ]
803
- },
804
- readToolPatterns: ["list_compositions", "check_versions"],
805
- writeToolPatterns: ["render_video", "render_still"],
806
- setupMessage: "Install Remotion and @remotion/cli in the configured project. OpenEve uses Remotion's supported CLI and Agent Skills workflow; it does not depend on Remotion's deprecated hosted MCP server."
807
- })
1270
+ REMOTION_PLUGIN
808
1271
  ];
809
- function validatePluginAccess(plugin, access) {
810
- if (!access)
811
- throw new Error(`${plugin.helper}: access must explicitly select read and write authority.`);
812
- if (access.write !== false && plugin.writeToolPatterns.length === 0) {
813
- throw new Error(`${plugin.helper}: ${plugin.provider} is a read-only plugin and cannot enable writes.`);
814
- }
815
- }
816
- function pluginAccessDefinition(plugin, access) {
817
- return {
818
- read: { tools: [...plugin.readToolPatterns] },
819
- write: access.write === false
820
- ? false
821
- : {
822
- tools: [...plugin.writeToolPatterns],
823
- approval: normalizePluginApproval(access.write.approval)
824
- }
825
- };
826
- }
827
- function tokenAuth(tokenEnv) {
828
- if (!tokenEnv)
829
- return undefined;
830
- return ({ env }) => ({
831
- principalType: "user",
832
- displayName: `${tokenEnv} bearer token`,
833
- getToken: async () => {
834
- const token = env[tokenEnv]?.trim();
835
- if (!token)
836
- throw new Error(`Missing ${tokenEnv}. Configure the provider credential or pass a custom auth definition.`);
837
- return { token };
838
- }
839
- });
840
- }
841
- function environmentValue(name) {
842
- if (!name || typeof process === "undefined")
843
- return undefined;
844
- return process.env[name]?.trim() || undefined;
845
- }
846
- function tokenHeader(name, tokenEnv) {
847
- if (!tokenEnv)
848
- return undefined;
849
- return ({ env }) => {
850
- const token = env[tokenEnv]?.trim();
851
- if (!token)
852
- throw new Error(`Missing ${tokenEnv}. Configure the provider credential or pass custom headers.`);
853
- return { [name]: token };
854
- };
855
- }
856
- function mergeHeaders(first, second) {
857
- if (!first)
858
- return second;
859
- if (!second)
860
- return first;
861
- return async (context) => ({
862
- ...(await resolveHeaders(first, context)),
863
- ...(await resolveHeaders(second, context))
864
- });
865
- }
866
- async function resolveHeaders(definition, context) {
867
- if (typeof definition === "function")
868
- return definition(context);
869
- const resolved = {};
870
- for (const [name, value] of Object.entries(definition)) {
871
- resolved[name] = await resolveHeaderValue(value, context);
872
- }
873
- return resolved;
874
- }
875
- async function resolveHeaderValue(value, context) {
876
- return typeof value === "function" ? value(context) : value;
877
- }
878
1272
  function cloneToolFilter(filter) {
879
1273
  if (!filter)
880
1274
  return undefined;
881
- return "allow" in filter ? { allow: [...filter.allow] } : { block: [...filter.block] };
1275
+ if ("allow" in filter)
1276
+ return { allow: [...filter.allow] };
1277
+ if ("block" in filter)
1278
+ return { block: [...filter.block] };
1279
+ return { allOf: filter.allOf.map((child) => cloneToolFilter(child)) };
882
1280
  }
883
1281
  function cloneHostRequirements(requirements) {
884
1282
  return {
@@ -887,11 +1285,6 @@ function cloneHostRequirements(requirements) {
887
1285
  ...(requirements.platforms ? { platforms: [...requirements.platforms] } : {})
888
1286
  };
889
1287
  }
890
- function normalizePluginApproval(approval) {
891
- if (approval === "always" || approval === "once" || approval === "never")
892
- return { mode: approval };
893
- return approval;
894
- }
895
1288
  function cloneMetadata(entry) {
896
1289
  return {
897
1290
  ...entry,
@@ -901,18 +1294,24 @@ function cloneMetadata(entry) {
901
1294
  scopes: [...(entry.scopes ?? [])],
902
1295
  readToolPatterns: [...entry.readToolPatterns],
903
1296
  writeToolPatterns: [...entry.writeToolPatterns],
904
- ...(entry.skills ? { skills: [...entry.skills] } : {}),
905
1297
  ...(entry.tools ? { tools: cloneToolFilter(entry.tools) } : {}),
906
1298
  ...(entry.hostRequirements ? { hostRequirements: cloneHostRequirements(entry.hostRequirements) } : {})
907
1299
  };
908
1300
  }
909
- function isPluginModule(value) {
910
- if (!value || typeof value !== "object")
911
- return false;
912
- const connections = value.connections;
913
- return connections === undefined || (Array.isArray(connections) && connections.every((entry) => Boolean(entry) && entry.role === "connection" && typeof entry.kind === "string" && typeof entry.helper === "string"));
914
- }
915
- export function connectionPluginBinding(metadata) {
916
- return { kind: metadata.kind };
1301
+ function cloneToolPackMetadata(entry) {
1302
+ return {
1303
+ ...entry,
1304
+ tools: entry.tools.map((tool) => ({ ...tool })),
1305
+ ...(entry.config ? {
1306
+ config: {
1307
+ ...entry.config,
1308
+ ...(entry.config.options ? { options: structuredClone(entry.config.options) } : {})
1309
+ }
1310
+ } : {}),
1311
+ ...(entry.skills ? { skills: [...entry.skills] } : {}),
1312
+ ...(entry.requiredEnv ? { requiredEnv: [...entry.requiredEnv] } : {}),
1313
+ ...(entry.optionalEnv ? { optionalEnv: [...entry.optionalEnv] } : {}),
1314
+ ...(entry.setup ? { setup: entry.setup.map((step) => ({ ...step })) } : {})
1315
+ };
917
1316
  }
918
1317
  //# sourceMappingURL=plugin.js.map