@knocklabs/agent-toolkit 0.1.13 → 0.2.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +42 -0
- package/dist/ai-sdk/index.d.ts +2 -1
- package/dist/ai-sdk/index.js +3 -2
- package/dist/ai-sdk/index.js.map +1 -1
- package/dist/{chunk-6O7VMHBN.js → chunk-IGJSMDBC.js} +8 -1
- package/dist/chunk-IGJSMDBC.js.map +1 -0
- package/dist/{chunk-RMUYOYLN.js → chunk-QG5UJT76.js} +185 -63
- package/dist/chunk-QG5UJT76.js.map +1 -0
- package/dist/{chunk-CCMSCN5A.js → chunk-ZUE3BSAZ.js} +3 -3
- package/dist/{chunk-CCMSCN5A.js.map → chunk-ZUE3BSAZ.js.map} +1 -1
- package/dist/human-in-the-loop.d.ts +3 -2
- package/dist/human-in-the-loop.js +1 -1
- package/dist/langchain/index.js +2 -2
- package/dist/langchain/index.js.map +1 -1
- package/dist/mastra/index.d.ts +18 -0
- package/dist/mastra/index.js +74 -0
- package/dist/mastra/index.js.map +1 -0
- package/dist/modelcontextprotocol/index.js +2 -2
- package/dist/modelcontextprotocol/local-server.js +7 -4
- package/dist/modelcontextprotocol/local-server.js.map +1 -1
- package/dist/openai/index.js +1 -1
- package/dist/{types-CrTRlRnE.d.ts → types-D6xiNyB2.d.ts} +15 -2
- package/dist/types.d.ts +1 -0
- package/package.json +9 -4
- package/dist/chunk-6O7VMHBN.js.map +0 -1
- package/dist/chunk-RMUYOYLN.js.map +0 -1
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
import { Tool } from '@mastra/core/tools';
|
|
2
|
+
import { z } from 'zod';
|
|
3
|
+
import { ToolkitConfig, ToolCategory } from '../types.js';
|
|
4
|
+
|
|
5
|
+
type KnockToolkit = {
|
|
6
|
+
getAllTools: () => Tool<z.ZodObject<any, any>>[];
|
|
7
|
+
getTools: (category: ToolCategory) => Tool<z.ZodObject<any, any>>[];
|
|
8
|
+
getToolMap: () => Record<string, Tool<z.ZodObject<any, any>>>;
|
|
9
|
+
};
|
|
10
|
+
/**
|
|
11
|
+
* Create a toolkit for use with the LangChain framework.
|
|
12
|
+
*
|
|
13
|
+
* @param config - The configuration to use for the toolkit
|
|
14
|
+
* @returns A toolkit for use with the LangChain framework
|
|
15
|
+
*/
|
|
16
|
+
declare const createKnockToolkit: (config: ToolkitConfig) => Promise<KnockToolkit>;
|
|
17
|
+
|
|
18
|
+
export { createKnockToolkit };
|
|
@@ -0,0 +1,74 @@
|
|
|
1
|
+
import {
|
|
2
|
+
createKnockClient
|
|
3
|
+
} from "../chunk-TRLABEB7.js";
|
|
4
|
+
import {
|
|
5
|
+
getToolMap,
|
|
6
|
+
getToolsByPermissionsInCategories
|
|
7
|
+
} from "../chunk-QG5UJT76.js";
|
|
8
|
+
import "../chunk-G3PMV62Z.js";
|
|
9
|
+
|
|
10
|
+
// src/mastra/tool-converter.ts
|
|
11
|
+
import { createTool } from "@mastra/core/tools";
|
|
12
|
+
import { z } from "zod";
|
|
13
|
+
function knockToolToMastraTool(knockClient, config, knockTool) {
|
|
14
|
+
return createTool({
|
|
15
|
+
id: knockTool.method,
|
|
16
|
+
inputSchema: knockTool.parameters ?? z.object({}),
|
|
17
|
+
description: knockTool.description,
|
|
18
|
+
execute: knockTool.bindExecute(knockClient, config)
|
|
19
|
+
});
|
|
20
|
+
}
|
|
21
|
+
|
|
22
|
+
// src/mastra/index.ts
|
|
23
|
+
var createKnockToolkit = async (config) => {
|
|
24
|
+
const knockClient = createKnockClient({
|
|
25
|
+
serviceToken: config.serviceToken ?? process.env.KNOCK_SERVICE_TOKEN
|
|
26
|
+
});
|
|
27
|
+
const allowedToolsByCategory = await getToolsByPermissionsInCategories(
|
|
28
|
+
knockClient,
|
|
29
|
+
config
|
|
30
|
+
);
|
|
31
|
+
const allTools = Object.values(allowedToolsByCategory).flat();
|
|
32
|
+
const toolsByMethod = getToolMap(allTools);
|
|
33
|
+
return Promise.resolve({
|
|
34
|
+
/**
|
|
35
|
+
* Get all tools as list.
|
|
36
|
+
*
|
|
37
|
+
* @returns A list of all tools
|
|
38
|
+
*/
|
|
39
|
+
getAllTools: () => {
|
|
40
|
+
return allTools.map(
|
|
41
|
+
(tool) => knockToolToMastraTool(knockClient, config, tool)
|
|
42
|
+
);
|
|
43
|
+
},
|
|
44
|
+
/**
|
|
45
|
+
* Get all tools for a specific category.
|
|
46
|
+
*
|
|
47
|
+
* @param category - The category of tools to get
|
|
48
|
+
* @returns A list of tools for the given category
|
|
49
|
+
*/
|
|
50
|
+
getTools: (category) => {
|
|
51
|
+
return allowedToolsByCategory[category].map(
|
|
52
|
+
(tool) => knockToolToMastraTool(knockClient, config, tool)
|
|
53
|
+
);
|
|
54
|
+
},
|
|
55
|
+
/**
|
|
56
|
+
* Get a map of all tools by method name.
|
|
57
|
+
*
|
|
58
|
+
* @returns A map of all tools by method name
|
|
59
|
+
*/
|
|
60
|
+
getToolMap: () => {
|
|
61
|
+
return Object.entries(toolsByMethod).reduce(
|
|
62
|
+
(acc, [method, tool]) => ({
|
|
63
|
+
...acc,
|
|
64
|
+
[method]: knockToolToMastraTool(knockClient, config, tool)
|
|
65
|
+
}),
|
|
66
|
+
{}
|
|
67
|
+
);
|
|
68
|
+
}
|
|
69
|
+
});
|
|
70
|
+
};
|
|
71
|
+
export {
|
|
72
|
+
createKnockToolkit
|
|
73
|
+
};
|
|
74
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../../src/mastra/tool-converter.ts","../../src/mastra/index.ts"],"sourcesContent":["import { createTool, Tool as MastraTool } from \"@mastra/core/tools\";\nimport { z } from \"zod\";\n\nimport { KnockClient } from \"../lib/knock-client.js\";\nimport { KnockTool } from \"../lib/knock-tool.js\";\nimport { Config } from \"../types.js\";\n\n/**\n * Convert a KnockTool to a ChatCompletionTool, ready to be used with the OpenAI API.\n *\n * @param knockTool - The KnockTool to convert\n * @returns The converted ChatCompletionTool\n */\nexport function knockToolToMastraTool(\n knockClient: KnockClient,\n config: Config,\n knockTool: KnockTool\n): MastraTool<z.ZodObject<any, any>> {\n return createTool({\n id: knockTool.method,\n inputSchema: knockTool.parameters ?? z.object({}),\n description: knockTool.description,\n execute: knockTool.bindExecute(knockClient, config),\n });\n}\n","import { Tool as MastraTool } from \"@mastra/core/tools\";\nimport { z } from \"zod\";\n\nimport { createKnockClient } from \"@/lib/knock-client\";\nimport { getToolsByPermissionsInCategories, getToolMap } from \"@/lib/utils\";\nimport { ToolCategory, ToolkitConfig } from \"@/types\";\n\nimport { knockToolToMastraTool } from \"./tool-converter\";\n\ntype KnockToolkit = {\n getAllTools: () => MastraTool<z.ZodObject<any, any>>[];\n getTools: (category: ToolCategory) => MastraTool<z.ZodObject<any, any>>[];\n getToolMap: () => Record<string, MastraTool<z.ZodObject<any, any>>>;\n};\n\n/**\n * Create a toolkit for use with the LangChain framework.\n *\n * @param config - The configuration to use for the toolkit\n * @returns A toolkit for use with the LangChain framework\n */\nconst createKnockToolkit = async (\n config: ToolkitConfig\n): Promise<KnockToolkit> => {\n const knockClient = createKnockClient({\n serviceToken: config.serviceToken ?? process.env.KNOCK_SERVICE_TOKEN!,\n });\n\n const allowedToolsByCategory = await getToolsByPermissionsInCategories(\n knockClient,\n config\n );\n\n const allTools = Object.values(allowedToolsByCategory).flat();\n const toolsByMethod = getToolMap(allTools);\n\n return Promise.resolve({\n /**\n * Get all tools as list.\n *\n * @returns A list of all tools\n */\n getAllTools: (): MastraTool<z.ZodObject<any, any>>[] => {\n return allTools.map((tool) =>\n knockToolToMastraTool(knockClient, config, tool)\n );\n },\n\n /**\n * Get all tools for a specific category.\n *\n * @param category - The category of tools to get\n * @returns A list of tools for the given category\n */\n getTools: (category: ToolCategory): MastraTool<z.ZodObject<any, any>>[] => {\n return allowedToolsByCategory[category].map((tool) =>\n knockToolToMastraTool(knockClient, config, tool)\n );\n },\n\n /**\n * Get a map of all tools by method name.\n *\n * @returns A map of all tools by method name\n */\n getToolMap: (): Record<string, MastraTool<z.ZodObject<any, any>>> => {\n return Object.entries(toolsByMethod).reduce(\n (acc, [method, tool]) => ({\n ...acc,\n [method]: knockToolToMastraTool(knockClient, config, tool),\n }),\n {} as Record<string, MastraTool<z.ZodObject<any, any>>>\n );\n },\n });\n};\n\nexport { createKnockToolkit };\n"],"mappings":";;;;;;;;;;AAAA,SAAS,kBAAsC;AAC/C,SAAS,SAAS;AAYX,SAAS,sBACd,aACA,QACA,WACmC;AACnC,SAAO,WAAW;AAAA,IAChB,IAAI,UAAU;AAAA,IACd,aAAa,UAAU,cAAc,EAAE,OAAO,CAAC,CAAC;AAAA,IAChD,aAAa,UAAU;AAAA,IACvB,SAAS,UAAU,YAAY,aAAa,MAAM;AAAA,EACpD,CAAC;AACH;;;ACHA,IAAM,qBAAqB,OACzB,WAC0B;AAC1B,QAAM,cAAc,kBAAkB;AAAA,IACpC,cAAc,OAAO,gBAAgB,QAAQ,IAAI;AAAA,EACnD,CAAC;AAED,QAAM,yBAAyB,MAAM;AAAA,IACnC;AAAA,IACA;AAAA,EACF;AAEA,QAAM,WAAW,OAAO,OAAO,sBAAsB,EAAE,KAAK;AAC5D,QAAM,gBAAgB,WAAW,QAAQ;AAEzC,SAAO,QAAQ,QAAQ;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,IAMrB,aAAa,MAA2C;AACtD,aAAO,SAAS;AAAA,QAAI,CAAC,SACnB,sBAAsB,aAAa,QAAQ,IAAI;AAAA,MACjD;AAAA,IACF;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,IAQA,UAAU,CAAC,aAAgE;AACzE,aAAO,uBAAuB,QAAQ,EAAE;AAAA,QAAI,CAAC,SAC3C,sBAAsB,aAAa,QAAQ,IAAI;AAAA,MACjD;AAAA,IACF;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,IAOA,YAAY,MAAyD;AACnE,aAAO,OAAO,QAAQ,aAAa,EAAE;AAAA,QACnC,CAAC,KAAK,CAAC,QAAQ,IAAI,OAAO;AAAA,UACxB,GAAG;AAAA,UACH,CAAC,MAAM,GAAG,sBAAsB,aAAa,QAAQ,IAAI;AAAA,QAC3D;AAAA,QACA,CAAC;AAAA,MACH;AAAA,IACF;AAAA,EACF,CAAC;AACH;","names":[]}
|
|
@@ -1,14 +1,14 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
2
|
import {
|
|
3
3
|
createKnockMcpServer
|
|
4
|
-
} from "../chunk-
|
|
4
|
+
} from "../chunk-ZUE3BSAZ.js";
|
|
5
5
|
import {
|
|
6
6
|
createKnockClient
|
|
7
7
|
} from "../chunk-TRLABEB7.js";
|
|
8
8
|
import {
|
|
9
9
|
filterTools,
|
|
10
10
|
tools
|
|
11
|
-
} from "../chunk-
|
|
11
|
+
} from "../chunk-QG5UJT76.js";
|
|
12
12
|
import "../chunk-G3PMV62Z.js";
|
|
13
13
|
|
|
14
14
|
// src/modelcontextprotocol/local-server.ts
|
|
@@ -37,7 +37,8 @@ var main = async () => {
|
|
|
37
37
|
}).option("service-token", {
|
|
38
38
|
alias: "st",
|
|
39
39
|
type: "string",
|
|
40
|
-
description: `Knock service token
|
|
40
|
+
description: `Knock service token. Only supply this if you're not passing it via the \`KNOCK_SERVICE_TOKEN\` environment variable.`,
|
|
41
|
+
demandOption: false
|
|
41
42
|
}).option("environment", {
|
|
42
43
|
alias: "e",
|
|
43
44
|
type: "string",
|
|
@@ -51,7 +52,9 @@ var main = async () => {
|
|
|
51
52
|
}).parse();
|
|
52
53
|
const SERVICE_TOKEN = serviceToken || process.env.KNOCK_SERVICE_TOKEN;
|
|
53
54
|
if (!SERVICE_TOKEN) {
|
|
54
|
-
throw new Error(
|
|
55
|
+
throw new Error(
|
|
56
|
+
"Knock service token is required. You should set it via the `KNOCK_SERVICE_TOKEN` environment variable."
|
|
57
|
+
);
|
|
55
58
|
}
|
|
56
59
|
const config = {
|
|
57
60
|
serviceToken: SERVICE_TOKEN,
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../../src/modelcontextprotocol/local-server.ts"],"sourcesContent":["#!/usr/bin/env node\n\nimport { StdioServerTransport } from \"@modelcontextprotocol/sdk/server/stdio.js\";\nimport { default as yargs } from \"yargs\";\nimport { hideBin } from \"yargs/helpers\";\n\nimport { createKnockClient } from \"../lib/knock-client.js\";\nimport { tools } from \"../lib/tools/index.js\";\nimport { filterTools } from \"../lib/utils.js\";\nimport { Config } from \"../types.js\";\n\nimport { createKnockMcpServer } from \"./index.js\";\n\n/**\n * Main entry point for the Knock MCP server.\n * Runs as a standalone process, as defined in package.json#bin.\n * An entrypoint for this file exists in the tsup configuration of the package.\n */\nconst main = async () => {\n const {\n serviceToken,\n environment,\n userId,\n tenantId,\n tools: patterns,\n workflows: workflowsAsTools,\n } = await yargs(hideBin(process.argv))\n .version(\"0.1.0\")\n .option(\"tools\", {\n alias: \"t\",\n type: \"string\",\n array: true,\n description: `List of tools to enable. Use \"*\" to enable all tools. Use \"category\" or \"category.*\" to enable all tools from a category. Use \"category.toolName\" to pick a single tool. Available categories: ${Object.keys(\n tools\n )}`,\n })\n .option(\"workflows\", {\n type: \"string\",\n array: true,\n description: `List of workflows to enable as tools in the MCP server. By default no workflows are enabled. Pass a list of workflow keys to enable those workflows as tools.`,\n })\n .option(\"service-token\", {\n alias: \"st\",\n type: \"string\",\n description: `Knock service token
|
|
1
|
+
{"version":3,"sources":["../../src/modelcontextprotocol/local-server.ts"],"sourcesContent":["#!/usr/bin/env node\n\nimport { StdioServerTransport } from \"@modelcontextprotocol/sdk/server/stdio.js\";\nimport { default as yargs } from \"yargs\";\nimport { hideBin } from \"yargs/helpers\";\n\nimport { createKnockClient } from \"../lib/knock-client.js\";\nimport { tools } from \"../lib/tools/index.js\";\nimport { filterTools } from \"../lib/utils.js\";\nimport { Config } from \"../types.js\";\n\nimport { createKnockMcpServer } from \"./index.js\";\n\n/**\n * Main entry point for the Knock MCP server.\n * Runs as a standalone process, as defined in package.json#bin.\n * An entrypoint for this file exists in the tsup configuration of the package.\n */\nconst main = async () => {\n const {\n serviceToken,\n environment,\n userId,\n tenantId,\n tools: patterns,\n workflows: workflowsAsTools,\n } = await yargs(hideBin(process.argv))\n .version(\"0.1.0\")\n .option(\"tools\", {\n alias: \"t\",\n type: \"string\",\n array: true,\n description: `List of tools to enable. Use \"*\" to enable all tools. Use \"category\" or \"category.*\" to enable all tools from a category. Use \"category.toolName\" to pick a single tool. Available categories: ${Object.keys(\n tools\n )}`,\n })\n .option(\"workflows\", {\n type: \"string\",\n array: true,\n description: `List of workflows to enable as tools in the MCP server. By default no workflows are enabled. Pass a list of workflow keys to enable those workflows as tools.`,\n })\n .option(\"service-token\", {\n alias: \"st\",\n type: \"string\",\n description: `Knock service token. Only supply this if you're not passing it via the \\`KNOCK_SERVICE_TOKEN\\` environment variable.`,\n demandOption: false,\n })\n .option(\"environment\", {\n alias: \"e\",\n type: \"string\",\n description: `The environment to operate in from your Knock account`,\n })\n .option(\"user-id\", {\n type: \"string\",\n description: `The user id to operate as`,\n })\n .option(\"tenant-id\", {\n type: \"string\",\n description: `The tenant id to operate as`,\n })\n .parse();\n\n const SERVICE_TOKEN = serviceToken || process.env.KNOCK_SERVICE_TOKEN;\n\n if (!SERVICE_TOKEN) {\n throw new Error(\n \"Knock service token is required. You should set it via the `KNOCK_SERVICE_TOKEN` environment variable.\"\n );\n }\n\n const config: Config = {\n serviceToken: SERVICE_TOKEN,\n userId,\n tenantId,\n environment,\n };\n\n const knockClient = createKnockClient(config);\n\n const filteredTools = patterns\n ? patterns.map((pattern) => filterTools(tools, pattern)).flat()\n : undefined;\n\n const mcpServer = await createKnockMcpServer({\n config,\n knockClient,\n tools: filteredTools,\n workflows: workflowsAsTools,\n });\n\n const transport = new StdioServerTransport();\n await mcpServer.connect(transport);\n};\n\nmain().catch((error) => {\n console.error(\"\\nKnock: Error initializing MCP server:\\n\", error.message);\n});\n"],"mappings":";;;;;;;;;;;;;;AAEA,SAAS,4BAA4B;AACrC,SAAS,WAAW,aAAa;AACjC,SAAS,eAAe;AAcxB,IAAM,OAAO,YAAY;AACvB,QAAM;AAAA,IACJ;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA,OAAO;AAAA,IACP,WAAW;AAAA,EACb,IAAI,MAAM,MAAM,QAAQ,QAAQ,IAAI,CAAC,EAClC,QAAQ,OAAO,EACf,OAAO,SAAS;AAAA,IACf,OAAO;AAAA,IACP,MAAM;AAAA,IACN,OAAO;AAAA,IACP,aAAa,kMAAkM,OAAO;AAAA,MACpN;AAAA,IACF,CAAC;AAAA,EACH,CAAC,EACA,OAAO,aAAa;AAAA,IACnB,MAAM;AAAA,IACN,OAAO;AAAA,IACP,aAAa;AAAA,EACf,CAAC,EACA,OAAO,iBAAiB;AAAA,IACvB,OAAO;AAAA,IACP,MAAM;AAAA,IACN,aAAa;AAAA,IACb,cAAc;AAAA,EAChB,CAAC,EACA,OAAO,eAAe;AAAA,IACrB,OAAO;AAAA,IACP,MAAM;AAAA,IACN,aAAa;AAAA,EACf,CAAC,EACA,OAAO,WAAW;AAAA,IACjB,MAAM;AAAA,IACN,aAAa;AAAA,EACf,CAAC,EACA,OAAO,aAAa;AAAA,IACnB,MAAM;AAAA,IACN,aAAa;AAAA,EACf,CAAC,EACA,MAAM;AAET,QAAM,gBAAgB,gBAAgB,QAAQ,IAAI;AAElD,MAAI,CAAC,eAAe;AAClB,UAAM,IAAI;AAAA,MACR;AAAA,IACF;AAAA,EACF;AAEA,QAAM,SAAiB;AAAA,IACrB,cAAc;AAAA,IACd;AAAA,IACA;AAAA,IACA;AAAA,EACF;AAEA,QAAM,cAAc,kBAAkB,MAAM;AAE5C,QAAM,gBAAgB,WAClB,SAAS,IAAI,CAAC,YAAY,YAAY,OAAO,OAAO,CAAC,EAAE,KAAK,IAC5D;AAEJ,QAAM,YAAY,MAAM,qBAAqB;AAAA,IAC3C;AAAA,IACA;AAAA,IACA,OAAO;AAAA,IACP,WAAW;AAAA,EACb,CAAC;AAED,QAAM,YAAY,IAAI,qBAAqB;AAC3C,QAAM,UAAU,QAAQ,SAAS;AACnC;AAEA,KAAK,EAAE,MAAM,CAAC,UAAU;AACtB,UAAQ,MAAM,6CAA6C,MAAM,OAAO;AAC1E,CAAC;","names":[]}
|
package/dist/openai/index.js
CHANGED
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import { Message } from '@knocklabs/node/dist/src/resources/messages/interfaces';
|
|
2
|
+
import { WorkflowRun } from '@knocklabs/node/dist/src/resources/workflows/interfaces';
|
|
2
3
|
|
|
3
4
|
type Metadata = Record<string, unknown> | undefined;
|
|
4
5
|
interface DeferredToolCallWorkflowData {
|
|
@@ -20,7 +21,7 @@ interface DeferredToolCallConfig {
|
|
|
20
21
|
/**
|
|
21
22
|
* The recipients to trigger the workflow for.
|
|
22
23
|
*/
|
|
23
|
-
recipients: string[];
|
|
24
|
+
recipients: string[] | Record<string, unknown>[];
|
|
24
25
|
/**
|
|
25
26
|
* Any extra data to pass to the workflow as context.
|
|
26
27
|
*/
|
|
@@ -32,9 +33,21 @@ interface DeferredToolCallConfig {
|
|
|
32
33
|
/**
|
|
33
34
|
* The actor to trigger the workflow for.
|
|
34
35
|
*/
|
|
35
|
-
actor?: string
|
|
36
|
+
actor?: string | Record<string, unknown>;
|
|
37
|
+
/**
|
|
38
|
+
* A function to call before calling the Knock API.
|
|
39
|
+
*/
|
|
40
|
+
onBeforeCallKnock?: (toolCall: DeferredToolCall) => Promise<void>;
|
|
41
|
+
/**
|
|
42
|
+
* A function to call after calling the Knock API.
|
|
43
|
+
*/
|
|
44
|
+
onAfterCallKnock?: (toolCall: DeferredToolCall, result: WorkflowRun) => Promise<void>;
|
|
36
45
|
}
|
|
37
46
|
type DeferredToolCall = {
|
|
47
|
+
/**
|
|
48
|
+
* The ID of the tool call. Should be automatically generated by the SDK.
|
|
49
|
+
*/
|
|
50
|
+
id: string;
|
|
38
51
|
/**
|
|
39
52
|
* The method of the tool that was called.
|
|
40
53
|
*/
|
package/dist/types.d.ts
CHANGED
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@knocklabs/agent-toolkit",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.2.0",
|
|
4
4
|
"description": "A toolkit for working with Knock in Agent workflows.",
|
|
5
5
|
"main": "src/index.js",
|
|
6
6
|
"scripts": {
|
|
@@ -33,6 +33,10 @@
|
|
|
33
33
|
"types": "./dist/langchain/index.d.ts",
|
|
34
34
|
"default": "./dist/langchain/index.js"
|
|
35
35
|
},
|
|
36
|
+
"./mastra": {
|
|
37
|
+
"types": "./dist/mastra/index.d.ts",
|
|
38
|
+
"default": "./dist/mastra/index.js"
|
|
39
|
+
},
|
|
36
40
|
"./modelcontextprotocol": {
|
|
37
41
|
"types": "./dist/modelcontextprotocol/index.d.ts",
|
|
38
42
|
"default": "./dist/modelcontextprotocol/index.js"
|
|
@@ -52,8 +56,8 @@
|
|
|
52
56
|
"dist"
|
|
53
57
|
],
|
|
54
58
|
"dependencies": {
|
|
55
|
-
"@knocklabs/mgmt": "^0.1.0
|
|
56
|
-
"@knocklabs/node": "^0.6.
|
|
59
|
+
"@knocklabs/mgmt": "^0.1.0",
|
|
60
|
+
"@knocklabs/node": "^0.6.19",
|
|
57
61
|
"@modelcontextprotocol/sdk": "^1.7.0",
|
|
58
62
|
"json-schema-to-zod": "^2.6.1",
|
|
59
63
|
"uuid": "^11.1.0",
|
|
@@ -86,7 +90,8 @@
|
|
|
86
90
|
},
|
|
87
91
|
"peerDependencies": {
|
|
88
92
|
"ai": "^4.0.0",
|
|
89
|
-
"openai": "^4.0.0"
|
|
93
|
+
"openai": "^4.0.0",
|
|
94
|
+
"@mastra/core": "^0.10.3"
|
|
90
95
|
},
|
|
91
96
|
"peerDependenciesMeta": {
|
|
92
97
|
"ai": {
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/lib/human-in-the-loop/index.ts"],"sourcesContent":["import { Config } from \"@/types\";\n\nimport { KnockClient } from \"../knock-client\";\n\nimport {\n DeferredToolCallWorkflowData,\n DeferredToolCallConfig,\n KnockOutboundWebhookEvent,\n DeferredToolCall,\n DeferredToolCallInteractionResult,\n} from \"./types\";\n\nfunction wrapToolDescription(description: string) {\n return `${description}\\n\\nThis tool call is deferred. You will NOT receive a result from this tool but this is NOT an error. Do NOT retry the tool call as the result will be the same. The tool call result will be provided to you in the future.`;\n}\n\n/**\n * Triggers a human in the loop workflow.\n *\n * @param knockClient - The Knock client to use.\n * @param toolCall - The tool call to trigger.\n * @param config - The configuration to use.\n */\nasync function triggerHumanInTheLoopWorkflow({\n knockClient,\n config,\n toolCall,\n inputConfig,\n}: {\n knockClient: KnockClient;\n config: Config;\n toolCall: DeferredToolCall;\n inputConfig: DeferredToolCallConfig;\n}) {\n const knock = await knockClient.publicApi(config.environment);\n\n const result = await knock.workflows.trigger(inputConfig.workflow, {\n data: {\n type: \"deferred_tool_call\",\n tool_call: toolCall,\n metadata: inputConfig.metadata,\n } as DeferredToolCallWorkflowData,\n recipients: inputConfig.recipients,\n tenant: inputConfig.tenant,\n actor: inputConfig.actor,\n });\n\n return result;\n}\n\n/**\n * Given an outboundwebhook event, this function will parse the event into a normalized format.\n *\n * If the event is not associated with a deferred tool call, this function will return null.\n *\n * @param event - The outbound webhook event\n * @returns A deferred tool call interaction result, or null if the event is not a deferred tool call\n */\nfunction handleMessageInteraction(\n event: KnockOutboundWebhookEvent\n): DeferredToolCallInteractionResult | null {\n const { data: message } = event;\n\n // We only care about message.interacted events\n if (event.type !== \"message.interacted\") {\n return null;\n }\n\n // We only care about messages that contain a tool call\n if (message.data.type !== \"deferred_tool_call\" || !message.data.tool_call) {\n return null;\n }\n\n const messageData = message.data as DeferredToolCallWorkflowData;\n\n return {\n workflow: message.source.key,\n interaction: event.event_data,\n toolCall: {\n method: messageData.tool_call.method,\n args: messageData.tool_call.args,\n extra: messageData.tool_call.extra,\n },\n metadata: messageData.metadata,\n context: {\n messageId: message.id,\n channelId: message.channel_id,\n timestamp: event.created_at,\n },\n };\n}\n\nexport {\n handleMessageInteraction,\n triggerHumanInTheLoopWorkflow,\n wrapToolDescription,\n};\n"],"mappings":";AAYA,SAAS,oBAAoB,aAAqB;AAChD,SAAO,GAAG,WAAW;AAAA;AAAA;AACvB;AASA,eAAe,8BAA8B;AAAA,EAC3C;AAAA,EACA;AAAA,EACA;AAAA,EACA;AACF,GAKG;AACD,QAAM,QAAQ,MAAM,YAAY,UAAU,OAAO,WAAW;AAE5D,QAAM,SAAS,MAAM,MAAM,UAAU,QAAQ,YAAY,UAAU;AAAA,IACjE,MAAM;AAAA,MACJ,MAAM;AAAA,MACN,WAAW;AAAA,MACX,UAAU,YAAY;AAAA,IACxB;AAAA,IACA,YAAY,YAAY;AAAA,IACxB,QAAQ,YAAY;AAAA,IACpB,OAAO,YAAY;AAAA,EACrB,CAAC;AAED,SAAO;AACT;AAUA,SAAS,yBACP,OAC0C;AAC1C,QAAM,EAAE,MAAM,QAAQ,IAAI;AAG1B,MAAI,MAAM,SAAS,sBAAsB;AACvC,WAAO;AAAA,EACT;AAGA,MAAI,QAAQ,KAAK,SAAS,wBAAwB,CAAC,QAAQ,KAAK,WAAW;AACzE,WAAO;AAAA,EACT;AAEA,QAAM,cAAc,QAAQ;AAE5B,SAAO;AAAA,IACL,UAAU,QAAQ,OAAO;AAAA,IACzB,aAAa,MAAM;AAAA,IACnB,UAAU;AAAA,MACR,QAAQ,YAAY,UAAU;AAAA,MAC9B,MAAM,YAAY,UAAU;AAAA,MAC5B,OAAO,YAAY,UAAU;AAAA,IAC/B;AAAA,IACA,UAAU,YAAY;AAAA,IACtB,SAAS;AAAA,MACP,WAAW,QAAQ;AAAA,MACnB,WAAW,QAAQ;AAAA,MACnB,WAAW,MAAM;AAAA,IACnB;AAAA,EACF;AACF;","names":[]}
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/lib/knock-tool.ts","../src/lib/tools/channels.ts","../src/lib/tools/commits.ts","../src/lib/tools/documentation.ts","../src/lib/tools/email-layouts.ts","../src/lib/tools/environments.ts","../src/lib/tools/message-types.ts","../src/lib/tools/messages.ts","../src/lib/tools/objects.ts","../src/lib/tools/partials.ts","../src/lib/tools/tenants.ts","../src/lib/tools/users.ts","../src/lib/tools/workflows-as-tools.ts","../src/lib/tools/shared.ts","../src/lib/utils.ts","../src/lib/tools/workflows.ts","../src/lib/tools/workflow-steps.ts","../src/lib/tools/index.ts"],"sourcesContent":["import type { ZodObject } from \"zod\";\nimport { z } from \"zod\";\n\nimport { Config } from \"../types.js\";\n\nimport { KnockClient } from \"./knock-client.js\";\n\nexport interface KnockToolDefinition {\n /**\n * The method name of the tool. This is a machine-readable string.\n */\n method: string;\n /**\n * The name of the tool. This can be used to reference the tool in the code.\n * A descriptive LLM-readable string.\n */\n name: string;\n\n /**\n * A descriptive prompt explaining the tool's purpose, including examples where useful.\n */\n description: string;\n\n /**\n * A descriptive prompt explaining the tool's purpose, usage and input parameters.\n * Ths is intended to be used by the underlying LLM.\n */\n fullDescription: string;\n\n /**\n * The Zod schema for the input parameters of the tool\n */\n parameters?: ZodObject<any>;\n /**\n * The actual implementation of the tool.\n */\n execute: (\n knockClient: KnockClient,\n config: Config\n ) => (input: any) => Promise<unknown>;\n}\n\nexport interface KnockTool extends Omit<KnockToolDefinition, \"execute\"> {\n bindExecute: (\n knockClient: KnockClient,\n config: Config\n ) => (input: any) => Promise<unknown>;\n}\n\nconst trimLines = (text: string) =>\n text\n .split(\"\\n\")\n .map((l) => l.trim())\n .filter(Boolean)\n .join(\"\\n\");\n\nexport const KnockTool = (\n args: Omit<KnockToolDefinition, \"fullDescription\">\n): KnockTool => {\n const { execute, ...restOfArgs } = args;\n const parameters = restOfArgs.parameters\n ? restOfArgs.parameters\n : z.object({});\n\n const schemaEntries = Object.entries(parameters.shape);\n\n const argsStr =\n schemaEntries.length === 0\n ? \"Takes no arguments\"\n : schemaEntries\n .map(([key, value]) => {\n return `- ${key}: ${(value as any).description || \"\"}`;\n })\n .join(\"\\n\");\n\n const fullDescription = trimLines(`\n Tool name:\n ${args.name}\n Description:\n ${args.description}.\n Arguments:\n ${argsStr}\n `);\n\n return {\n ...restOfArgs,\n parameters,\n fullDescription,\n bindExecute: (knockClient: KnockClient, config: Config) =>\n execute(knockClient, config),\n };\n};\n","import { Channel } from \"@knocklabs/mgmt/resources/channels.js\";\n\nimport { KnockTool } from \"../knock-tool.js\";\n\n/**\n * A slimmed down version of the Channel resource that is easier to work with in the LLM.\n */\ntype SerializedChannel = {\n key: string;\n name: string;\n type: string;\n provider: string;\n};\n\nfunction serializeChannelResponse(channel: Channel): SerializedChannel {\n return {\n key: channel.key,\n name: channel.name,\n type: channel.type,\n provider: channel.provider,\n };\n}\n\nconst listChannels = KnockTool({\n method: \"list_channels\",\n name: \"List channels\",\n description: `\n Returns a list of all of the channels configured in the account. Each channel returns information about the type of channel it is (email, sms, push, etc), and the provider that's used to power the channel. Channels can be used across all environments.\n\n Use this tool when you need to know about the channels configured in the Knock account, like when configuring a workflow.\n `,\n execute: (knockClient) => async (_params) => {\n const allChannels: SerializedChannel[] = [];\n for await (const channel of knockClient.channels.list()) {\n allChannels.push(serializeChannelResponse(channel));\n }\n return allChannels;\n },\n});\n\nexport const channels = {\n listChannels,\n};\n\nexport const permissions = {\n read: [\"listChannels\"],\n};\n","import { z } from \"zod\";\n\nimport { KnockTool } from \"../knock-tool.js\";\n\nconst listCommits = KnockTool({\n method: \"list_commits\",\n name: \"List commits\",\n description: `\n Returns all commits available in the environment. Use this tool when you are asked to see what changes are available to be deployed.\n `,\n parameters: z.object({\n environment: z\n .string()\n .optional()\n .describe(\n \"(string): The environment to list commits for. Defaults to `development`.\"\n ),\n promoted: z\n .boolean()\n .describe(\n \"(boolean): Whether to only return promoted commits. Defaults to `false`.\"\n ),\n }),\n execute: (knockClient, config) => async (params) => {\n return await knockClient.commits.list({\n environment: params.environment ?? config.environment ?? \"development\",\n promoted: params.promoted ?? false,\n });\n },\n});\n\nconst commitAllChanges = KnockTool({\n method: \"commit_all_changes\",\n name: \"Commit all changes\",\n description: `\n Commit all pending changes. This can only be used in the development environment.\n `,\n parameters: z.object({\n environment: z\n .string()\n .optional()\n .describe(\n \"(string): The environment to commit all changes to. Defaults to `development`.\"\n ),\n message: z\n .string()\n .optional()\n .describe(\"(string): The message to include in the commit.\"),\n }),\n execute: (knockClient, config) => async (params) => {\n return await knockClient.commits.commitAll({\n environment: params.environment ?? config.environment ?? \"development\",\n commit_message: params.message,\n });\n },\n});\n\nconst promoteAllCommits = KnockTool({\n method: \"promote_all_commits\",\n name: \"Promote all commits\",\n description: `\n Promote all commits to the next environment. Use this tool when you are asked to deploy all changes.\n `,\n parameters: z.object({\n toEnvironment: z\n .string()\n .describe(\"(string): The environment to promote all commits to.\"),\n }),\n execute: (knockClient, _config) => async (params) => {\n return await knockClient.put(\"/v1/commits/promote\", {\n body: { to_environment: params.toEnvironment },\n });\n },\n});\n\nexport const commits = {\n listCommits,\n commitAllChanges,\n promoteAllCommits,\n};\n\nexport const permissions = {\n read: [\"listCommits\"],\n manage: [\"commitAllChanges\", \"promoteAllCommits\"],\n};\n","import { z } from \"zod\";\n\nimport { KnockTool } from \"../knock-tool.js\";\n\nconst searchDocumentation = KnockTool({\n method: \"search_documentation\",\n name: \"Search documentation\",\n description: \"Search the Knock documentation for a given query\",\n parameters: z.object({\n query: z.string().describe(\"The query to search the documentation for\"),\n }),\n execute: () => async (params) => {\n const response = await fetch(`https://docs.knock.app/api/search`, {\n method: \"POST\",\n headers: {\n \"Content-Type\": \"application/json\",\n },\n body: JSON.stringify({ query: params.query }),\n });\n\n const data = await response.json();\n return data;\n },\n});\n\nexport const documentation = {\n searchDocumentation,\n};\n\nexport const permissions = {\n read: [\"searchDocumentation\"],\n};\n","import { EmailLayout } from \"@knocklabs/mgmt/resources/email-layouts.js\";\nimport { z } from \"zod\";\n\nimport { KnockTool } from \"../knock-tool.js\";\n\n/**\n * A slimmed down version of the EmailLayout resource that is easier to work with in the LLM.\n */\ntype SerializedEmailLayout = {\n key: string;\n name: string;\n};\n\nfunction serializeEmailLayoutResponse(\n emailLayout: EmailLayout\n): SerializedEmailLayout {\n return {\n key: emailLayout.key,\n name: emailLayout.name,\n };\n}\n\nconst listEmailLayouts = KnockTool({\n method: \"list_email_layouts\",\n name: \"List email layouts\",\n description: `List all email layouts within the environment given. Returns information about the email layout, including the name and the key. \n \n Use this tool when building a workflow that is building an email notification when you need to know the available email layouts.`,\n parameters: z.object({\n environment: z\n .string()\n .optional()\n .describe(\n \"(string): The environment to list email layouts for. Defaults to `development`.\"\n ),\n }),\n execute: (knockClient, config) => async (params) => {\n const allEmailLayouts: SerializedEmailLayout[] = [];\n for await (const emailLayout of knockClient.emailLayouts.list({\n environment: params.environment ?? config.environment ?? \"development\",\n })) {\n allEmailLayouts.push(serializeEmailLayoutResponse(emailLayout));\n }\n return allEmailLayouts;\n },\n});\n\nexport const emailLayouts = {\n listEmailLayouts,\n};\n\nexport const permissions = {\n read: [\"listEmailLayouts\"],\n};\n","import { Environment } from \"@knocklabs/mgmt/resources/environments.js\";\n\nimport { KnockTool } from \"../knock-tool.js\";\n\n/**\n * A slimmed down version of the Environment resource that is easier to work with in the LLM.\n */\ntype SerializedEnvironment = {\n slug: string;\n name: string;\n};\n\nfunction serializeEnvironmentResponse(\n environment: Environment\n): SerializedEnvironment {\n return {\n slug: environment.slug,\n name: environment.name,\n };\n}\n\nconst listEnvironments = KnockTool({\n method: \"list_environments\",\n name: \"List environments\",\n description: `\n Lists all environments available, returning the slug and name of each environment. Use this tool when you need to see what environments are available.\n `,\n execute: (knockClient) => async (_params) => {\n const allEnvironments: SerializedEnvironment[] = [];\n for await (const environment of knockClient.environments.list()) {\n allEnvironments.push(serializeEnvironmentResponse(environment));\n }\n return allEnvironments;\n },\n});\n\nexport const environments = {\n listEnvironments,\n};\n\nexport const permissions = {\n read: [\"listEnvironments\"],\n};\n","import { MessageType } from \"@knocklabs/mgmt/resources/message-types.js\";\nimport { z } from \"zod\";\n\nimport { KnockTool } from \"../knock-tool.js\";\n\n/**\n * A slimmed down version of the MessageType resource that is easier to work with in the LLM.\n */\ntype SerializedMessageType = {\n key: string;\n name: string;\n description?: string | null;\n variants: string[];\n};\n\nfunction serializeMessageTypeResponse(\n messageType: MessageType\n): SerializedMessageType {\n return {\n key: messageType.key,\n name: messageType.name,\n description: messageType.description,\n variants: messageType.variants.map((variant) => variant.key),\n };\n}\nconst listMessageTypes = KnockTool({\n method: \"list_message_types\",\n name: \"List message types\",\n description:\n \"List all message types available for the environment. Each message type returns the schema, which includes information about the variants and the fields available per-variant. Use this tool when you need to understand the different message types that are available for the environment for use in Guides.\",\n parameters: z.object({\n environment: z\n .string()\n .optional()\n .describe(\n \"(string): The environment to list message types for. Defaults to `development`.\"\n ),\n }),\n execute: (knockClient, config) => async (params) => {\n const allMessageTypes: SerializedMessageType[] = [];\n for await (const messageType of knockClient.messageTypes.list({\n environment: params.environment ?? config.environment ?? \"development\",\n })) {\n allMessageTypes.push(serializeMessageTypeResponse(messageType));\n }\n return allMessageTypes;\n },\n});\n\nconst createOrUpdateMessageType = KnockTool({\n method: \"create_or_update_message_type\",\n name: \"Create or update message type\",\n description: `\n Create or update a message type. A message type is a schema that defines fields available to an editor within Knock. Message types always have at least one variant, that MUST be named \"default\". Use this tool when you need to create a new message type, or update an existing message type.\n\n ## Schema and fields\n\n The schema defines the fields available to an editor within Knock. A variant should have at least one field. Fields can be of different types, including: text, markdown, select, multi-select, image, and button.\n\n Each field must have a key, label, and type. Some fields like \\`select\\` and \\`multi_select\\` have additional settings that can be used to configure the field.\n\n <example>\n {\n \"key\": \"text\",\n \"label\": \"Text\",\n \"type\": \"text\",\n </example>\n\n <example>\n {\n \"key\": \"select\",\n \"label\": \"Select\",\n \"type\": \"select\",\n \"settings\": {\n \"options\": [\n {\n \"value\": \"option1\",\n \"label\": \"Option 1\",\n },\n ],\n },\n }\n </example>\n\n ## Preview templates\n\n The preview is a string of HTML that will be rendered in the Knock UI as a representation of the message type. It is shared across all variants. It supports liquid, where the field name is available as a variable, so a field named \"text\" will be rendered as {{ text }}. All fields should be included in the preview.\n\n You can make an educated guess as to what the preview template should look like based on the name of the message type and the fields. You can use plain CSS to style the preview by supplying a style tag in the preview. Use simple selectors like .class-name to style elements.\n\n <example>\n {\n \"preview\": \"<style>div { color: red; }</style>\\n<div>Hello there, {{ text }}</div>\"\n }\n </example>\n `,\n parameters: z.object({\n environment: z\n .string()\n .optional()\n .describe(\n \"(string): The environment to create or update the message type in. Defaults to `development`.\"\n ),\n messageTypeKey: z\n .string()\n .describe(\"(string): The key of the message type to create or update.\"),\n name: z.string().describe(\"(string): The name of the message type.\"),\n description: z\n .string()\n .optional()\n .describe(\"(string): The description of the message type.\"),\n preview: z\n .string()\n .optional()\n .describe(\n \"(string): The preview of the variant. This is a string of HTML that will be rendered in the preview of the message type. There is a single preview shared by all variants.\"\n ),\n variants: z\n .array(\n z.object({\n key: z.string().describe(\"(string): The key of the variant.\"),\n name: z.string().describe(\"(string): The name of the variant.\"),\n description: z\n .string()\n .optional()\n .describe(\"(string): The description of the variant.\"),\n fields: z\n .array(\n z.object({\n key: z.string().describe(\"(string): The key of the field.\"),\n type: z\n .string()\n .describe(\n \"(string): The type of the field. One of `text`, `textarea`, `button`, `markdown`, `select`, `multi_select`, `image`.\"\n ),\n label: z.string().describe(\"(string): The label of the field.\"),\n settings: z\n .object({})\n .optional()\n .describe(\"(object): The settings of the field.\"),\n })\n )\n .describe(\"(array): The fields of the variant.\"),\n })\n )\n .describe(\"(array): The variants of the message type.\"),\n }),\n execute: (knockClient, config) => async (params) => {\n return await knockClient.messageTypes.upsert(params.messageTypeKey, {\n message_type: {\n name: params.name,\n variants: params.variants,\n description: params.description ?? \"\",\n preview: params.preview ?? \"<div></div>\",\n },\n environment: params.environment ?? config.environment ?? \"development\",\n });\n },\n});\n\nexport const messageTypes = {\n listMessageTypes,\n createOrUpdateMessageType,\n};\n\nexport const permissions = {\n read: [\"listMessageTypes\"],\n manage: [\"createOrUpdateMessageType\"],\n};\n","import { z } from \"zod\";\n\nimport { KnockTool } from \"../knock-tool.js\";\n\nconst getMessageContent = KnockTool({\n method: \"get_message_content\",\n name: \"Get message content\",\n description: `\n Retrieves the complete contents of a single message, specified by the messageId. The message contents includes the rendered template that was sent to the recipient. Use this tool when you want to surface information about the emails, SMS, and push notifications that were sent to a user.\n `,\n parameters: z.object({\n environment: z\n .string()\n .optional()\n .describe(\n \"(string): The environment to retrieve the message from. Defaults to `development`.\"\n ),\n messageId: z\n .string()\n .describe(\"(string): The messageId of the message to retrieve.\"),\n }),\n execute: (knockClient) => async (params) => {\n const publicClient = await knockClient.publicApi(params.environment);\n return await publicClient.messages.getContent(params.messageId);\n },\n});\n\nexport const messages = {\n getMessageContent,\n};\n\nexport const permissions = {\n read: [\"getMessageContent\"],\n};\n","import { z } from \"zod\";\n\nimport { KnockTool } from \"../knock-tool.js\";\n\nconst listObjects = KnockTool({\n method: \"list_objects\",\n name: \"List objects\",\n description:\n \"List all objects in a single collection. Objects are used to model custom collections in Knock that are NOT users or tenants. Use this tool when you need to return a paginated list of objects in a single collection.\",\n parameters: z.object({\n environment: z\n .string()\n .optional()\n .describe(\n \"(string): The environment to list objects from. Defaults to `development`.\"\n ),\n collection: z\n .string()\n .describe(\"(string): The collection to list objects from.\"),\n }),\n execute: (knockClient, _config) => async (params) => {\n const publicClient = await knockClient.publicApi(params.environment);\n return await publicClient.objects.list(params.collection);\n },\n});\n\nconst getObject = KnockTool({\n method: \"get_object\",\n name: \"Get object\",\n description:\n \"Get an object wihin a collection. Returns information about the object including any custom properties. Use this tool when you need to retrieve an object to understand it's properties.\",\n parameters: z.object({\n environment: z\n .string()\n .optional()\n .describe(\n \"(string): The environment to get the object from. Defaults to `development`.\"\n ),\n collection: z\n .string()\n .describe(\"(string): The collection to get the object from.\"),\n objectId: z.string().describe(\"(string): The ID of the object to get.\"),\n }),\n execute: (knockClient, _config) => async (params) => {\n const publicClient = await knockClient.publicApi(params.environment);\n return await publicClient.objects.get(params.collection, params.objectId);\n },\n});\n\nconst createOrUpdateObject = KnockTool({\n method: \"create_or_update_object\",\n name: \"Create or update object\",\n description: `Create or update an object in a specific collection. Objects are used to model custom collections in Knock that are NOT users or tenants. If the object does not exist, it will be created. If the object exists, it will be updated with the provided properties. The update will always perform an upsert operation, so you do not need to provide the full properties each time.\n \n Use this tool when you need to create a new object, or update an existing custom-object. Custom objects can be used to subscribe users' to as lists, and also send non-user facing notifications to.`,\n parameters: z.object({\n environment: z\n .string()\n .optional()\n .describe(\n \"(string): The environment to create or update the object in. Defaults to `development`.\"\n ),\n collection: z\n .string()\n .describe(\"(string): The collection to create or update the object in.\"),\n objectId: z\n .string()\n .describe(\"(string): The ID of the object to create or update.\"),\n properties: z\n .record(z.string(), z.any())\n .optional()\n .describe(\"(object): The properties to set on the object.\"),\n }),\n execute: (knockClient, _config) => async (params) => {\n const publicClient = await knockClient.publicApi(params.environment);\n return await publicClient.objects.set(\n params.collection,\n params.objectId,\n params.properties\n );\n },\n});\n\nconst subscribeUsersToObject = KnockTool({\n method: \"subscribe_users_to_object\",\n name: \"Subscribe users to object\",\n description: `\n Subscribe a list of users to an object in a specific collection. We use this to model lists of users, for pub-sub use cases.\n \n Use this tool when you need to subscribe one or more users to an object where you will then trigger workflows for those lists of users to send notifications to.\n\n Before using this tool, you should create the object in the collection using the createOrUpdateObject tool.\n `,\n parameters: z.object({\n environment: z\n .string()\n .optional()\n .describe(\n \"(string): The environment to subscribe the user to. Defaults to `development`.\"\n ),\n collection: z\n .string()\n .describe(\"(string): The collection to subscribe the user to.\"),\n objectId: z\n .string()\n .describe(\"(string): The ID of the object to subscribe the user to.\"),\n userIds: z\n .array(z.string())\n .describe(\n \"(array): The IDs of the users to subscribe to the object. If not provided, the current user will be subscribed.\"\n ),\n }),\n execute: (knockClient, config) => async (params) => {\n const publicClient = await knockClient.publicApi(params.environment);\n return await publicClient.objects.addSubscriptions(\n params.collection,\n params.objectId,\n {\n recipients: params.userIds ?? [config.userId],\n }\n );\n },\n});\n\nconst unsubscribeUsersFromObject = KnockTool({\n method: \"unsubscribe_users_from_object\",\n name: \"Unsubscribe users from object\",\n description: `Unsubscribe a list of users from an object in a specific collection. We use this to model lists of users, for pub-sub use cases.\n \n Use this tool when you need to unsubscribe one or more users from an object where you will then trigger workflows for those lists of users to send notifications to.`,\n parameters: z.object({\n environment: z\n .string()\n .optional()\n .describe(\n \"(string): The environment to unsubscribe the user from. Defaults to `development`.\"\n ),\n collection: z\n .string()\n .describe(\"(string): The collection to unsubscribe the user from.\"),\n objectId: z\n .string()\n .describe(\"(string): The ID of the object to unsubscribe the user from.\"),\n userIds: z\n .array(z.string())\n .describe(\n \"(array): The IDs of the users to unsubscribe from the object.\"\n ),\n }),\n execute: (knockClient, config) => async (params) => {\n const publicClient = await knockClient.publicApi(params.environment);\n return await publicClient.objects.deleteSubscriptions(\n params.collection,\n params.objectId,\n {\n recipients: params.userIds ?? [config.userId],\n }\n );\n },\n});\n\nexport const objects = {\n listObjects,\n getObject,\n createOrUpdateObject,\n subscribeUsersToObject,\n unsubscribeUsersFromObject,\n};\n\nexport const permissions = {\n read: [\"listObjects\", \"getObject\"],\n manage: [\n \"createOrUpdateObject\",\n \"subscribeUsersToObject\",\n \"unsubscribeUsersFromObject\",\n ],\n};\n","import { Partial } from \"@knocklabs/mgmt/resources/partials.js\";\nimport { z } from \"zod\";\n\nimport { KnockTool } from \"@/lib/knock-tool.js\";\n\n/**\n * A slimmed down version of the Partial resource that is easier to work with in the LLM.\n */\ntype SerializedPartial = {\n key: string;\n type: Partial[\"type\"];\n name: string;\n description?: string;\n};\n\nfunction serializePartial(partial: Partial): SerializedPartial {\n return {\n key: partial.key,\n type: partial.type,\n name: partial.name,\n description: partial.description,\n };\n}\n\nconst listPartials = KnockTool({\n method: \"list_partials\",\n name: \"List partials\",\n description: `\n List all partials within the environment given. Partials provide common building blocks for notification templates. Returns information about the partial, including the name and the key. \n Use this tool when you need to know the available partials for the environment, like when building a notification template and wanting to use a partial to build the template.`,\n parameters: z.object({\n environment: z\n .string()\n .optional()\n .describe(\n \"(string): The environment to list partials for. Defaults to `development`.\"\n ),\n }),\n execute: (knockClient, config) => async (params) => {\n const allPartials: SerializedPartial[] = [];\n for await (const partial of knockClient.partials.list({\n environment: params.environment ?? config.environment ?? \"development\",\n })) {\n allPartials.push(serializePartial(partial));\n }\n return allPartials;\n },\n});\n\nconst getPartial = KnockTool({\n method: \"get_partial\",\n name: \"Get partial\",\n description: `\n Get a partial by its key. Use this tool when you need to know if a specific partial exists by key.\n `,\n parameters: z.object({\n environment: z\n .string()\n .optional()\n .describe(\n \"(string): The environment to get the partial for. Defaults to `development`.\"\n ),\n key: z.string().describe(\"(string): The key of the partial to get.\"),\n }),\n execute: (knockClient, config) => async (params) => {\n const partial = await knockClient.partials.retrieve(params.key, {\n environment: params.environment ?? config.environment ?? \"development\",\n });\n\n return serializePartial(partial);\n },\n});\n\nconst createOrUpdatePartial = KnockTool({\n method: \"upsert_partial\",\n name: \"Upsert partial\",\n description: `\n Create or update a partial. A partial is a reusable piece of content that can be used in a template. Use this tool when you need to create a new partial or update an existing one.\n\n When working with a partial you must chose the type of the partial. The type determines the format of the content. If you're working with an email template, you should use the \"html\" or \"markdown\" type.\n\n If you need to work with dynamic content in your partial you can use liquid syntax. Liquid is a templating language that is supported in Knock. You can supply a variable like {{ some_variable }} in the content and it will be replaced with the actual value when the partial is used in a template.\n\n <example>\n {\n \"name\": \"Greeting\",\n \"key\": \"greeting\",\n \"type\": \"html\",\n \"content\": \"<div>Hello, {{ recipient_name }}</div>\"\n }\n </example>\n\n Changes to a partial MUST be committed before they can be used in a template.\n `,\n parameters: z.object({\n environment: z\n .string()\n .optional()\n .describe(\n \"(string): The environment to upsert the partial for. Defaults to `development`.\"\n ),\n key: z.string().describe(\"(string): The key of the partial to upsert.\"),\n name: z.string().describe(\"(string): The name of the partial.\"),\n description: z\n .string()\n .optional()\n .describe(\"(string): The description of the partial.\"),\n content: z.string().describe(\"(string): The content of the partial.\"),\n type: z\n .enum([\"html\", \"text\", \"json\", \"markdown\"])\n .describe(\"(string): The type of the partial.\"),\n }),\n execute: (knockClient, config) => async (params) => {\n const partial = await knockClient.partials.upsert(params.key, {\n environment: params.environment ?? config.environment ?? \"development\",\n partial: {\n name: params.name,\n description: params.description,\n content: params.content,\n type: params.type,\n },\n });\n return serializePartial(partial.partial);\n },\n});\n\nexport const partials = {\n getPartial,\n listPartials,\n createOrUpdatePartial,\n};\n\nexport const permissions = {\n read: [\"getPartial\", \"listPartials\"],\n manage: [\"createOrUpdatePartial\"],\n};\n","import { z } from \"zod\";\n\nimport { KnockTool } from \"../knock-tool.js\";\n\nconst getTenant = KnockTool({\n method: \"get_tenant\",\n name: \"Get tenant\",\n description: `\n Retrieves a tenant by their ID. Tenants in Knock are used to model organizations, teams, and other groups of users. They are a special type of object.\n \n Use this tool when you need to lookup the information about a tenant, including name, and if there are any custom properties set.\n `,\n parameters: z.object({\n environment: z\n .string()\n .optional()\n .describe(\n \"(string): The environment to retrieve the tenant from. Defaults to `development`.\"\n ),\n tenantId: z\n .string()\n .describe(\"(string): The ID of the tenant to retrieve.\"),\n }),\n execute: (knockClient) => async (params) => {\n const publicClient = await knockClient.publicApi(params.environment);\n return await publicClient.tenants.get(params.tenantId);\n },\n});\n\nconst listTenants = KnockTool({\n method: \"list_tenants\",\n name: \"List tenants\",\n description: `\n Retrieves a list of tenants. Tenants in Knock are used to model organizations, teams, and other groups of users. They are a special type of object. \n \n Use this tool when you need to list all tenants in an environment.\n `,\n parameters: z.object({\n environment: z\n .string()\n .optional()\n .describe(\n \"(string): The environment to retrieve the tenants from. Defaults to `development`.\"\n ),\n }),\n execute: (knockClient) => async (params) => {\n const publicClient = await knockClient.publicApi(params.environment);\n return await publicClient.tenants.list();\n },\n});\n\nconst setTenant = KnockTool({\n method: \"set_tenant\",\n name: \"Set tenant\",\n description: `\n Creates or updates a tenant using the properties provided. Tenants in Knock are used to model organizations, teams, and other groups of users. They are a special type of object.\n \n Use this tool when you need to create a new tenant, or update an existing tenant's properties.\n `,\n parameters: z.object({\n environment: z\n .string()\n .optional()\n .describe(\n \"(string): The environment to set the tenant in. Defaults to `development`.\"\n ),\n tenantId: z.string().describe(\"(string): The ID of the tenant to update.\"),\n name: z.string().optional().describe(\"(string): The name of the tenant.\"),\n properties: z\n .record(z.string(), z.any())\n .optional()\n .describe(\"(object): The properties to set on the tenant.\"),\n }),\n execute: (knockClient) => async (params) => {\n const publicClient = await knockClient.publicApi(params.environment);\n return await publicClient.tenants.set(params.tenantId, {\n name: params.name,\n ...params.properties,\n });\n },\n});\n\nexport const tenants = {\n getTenant,\n listTenants,\n setTenant,\n};\n\nexport const permissions = {\n read: [\"getTenant\", \"listTenants\"],\n manage: [\"setTenant\"],\n};\n","import { User } from \"@knocklabs/node\";\nimport { z } from \"zod\";\n\nimport { KnockTool } from \"../knock-tool.js\";\nimport { serializeMessageResponse } from \"../utils.js\";\nfunction maybeHideUserData(user: User, hideUserData: boolean = false) {\n if (hideUserData) {\n return { id: user.id };\n }\n return user;\n}\n\nconst getUser = KnockTool({\n method: \"get_user\",\n name: \"Get user\",\n description: `\n Retrieves the complete user object for the given userId, including email, name, phone number, and any custom properties. Use this tool when you need to retrieve a user's complete profile.\n\n If the userId is not provided, it will use the userId from the config.\n `,\n parameters: z.object({\n environment: z\n .string()\n .optional()\n .describe(\n \"(string): The environment to retrieve the user from. Defaults to `development`.\"\n ),\n userId: z\n .string()\n .optional()\n .describe(\"(string): The userId of the User to retrieve.\"),\n }),\n execute: (knockClient, config) => async (params) => {\n const publicClient = await knockClient.publicApi(params.environment);\n\n const user = await publicClient.users.get(params.userId ?? config.userId);\n\n return maybeHideUserData(user, config.hideUserData);\n },\n});\n\nconst createOrUpdateUser = KnockTool({\n method: \"create_or_update_user\",\n name: \"Create or update user\",\n description: `\n Creates a new user if they don't exist, or updates the user object for the given userId, including email, name, phone number, and any custom properties.\n \n Use this tool when you need to update a user's profile.\n\n If the userId is not provided, it will use the userId from the config.\n `,\n parameters: z.object({\n environment: z\n .string()\n .optional()\n .describe(\n \"(string): The environment to create or update the user in. Defaults to `development`.\"\n ),\n userId: z\n .string()\n .optional()\n .describe(\"(string): The userId of the User to update.\"),\n email: z\n .string()\n .optional()\n .describe(\"(string): The email of the User to update.\"),\n name: z\n .string()\n .optional()\n .describe(\"(string): The name of the User to update.\"),\n phoneNumber: z\n .string()\n .optional()\n .describe(\"(string): The phone number of the User to update.\"),\n customProperties: z\n .record(z.string(), z.any())\n .optional()\n .describe(\n \"(object): A dictionary of custom properties to update for the User.\"\n ),\n }),\n execute: (knockClient, config) => async (params) => {\n const publicClient = await knockClient.publicApi(params.environment);\n\n const user = await publicClient.users.identify(\n params.userId ?? config.userId,\n {\n email: params.email,\n name: params.name,\n phone_number: params.phoneNumber,\n ...(params.customProperties ?? {}),\n }\n );\n\n return maybeHideUserData(user, config.hideUserData);\n },\n});\n\nconst getUserPreferences = KnockTool({\n method: \"get_user_preferences\",\n name: \"Get user preferences\",\n description: `\n Retrieves the user's notification preferences for the given userId.\n\n If the userId is not provided, it will use the userId from the config. \n `,\n parameters: z.object({\n environment: z\n .string()\n .optional()\n .describe(\n \"(string): The environment to retrieve the user preferences from. Defaults to `development`.\"\n ),\n userId: z\n .string()\n .optional()\n .describe(\n \"(string): The userId of the User to retrieve Preferences for.\"\n ),\n preferenceSetId: z\n .string()\n .optional()\n .describe(\n \"(string): The preferenceSetId of the User to retrieve preferences for. Defaults to `default`.\"\n ),\n }),\n execute: (knockClient, config) => async (params) => {\n const publicClient = await knockClient.publicApi(params.environment);\n\n return await publicClient.users.getPreferences(\n params.userId ?? config.userId,\n {\n preferenceSet: params.preferenceSetId ?? \"default\",\n }\n );\n },\n});\n\nconst setUserPreferences = KnockTool({\n method: \"set_user_preferences\",\n name: \"Set user preferences\",\n description: `\n Overwrites the user's notification preferences for the given userId. Allows setting per-workflow, per-category, or per-channel notification preferences. Use this tool when you are asked to update a user's notification preferences.\n\n If the userId is not provided, it will use the userId from the config.\n\n Instructions:\n\n - You must ALWAYS provide a full preference set to this tool.\n - When setting per-workflow preferences, the key in the object should be the workflow key.\n - Workflow and category preferences should always have channel types underneath.\n - The channel types available to you are: email, sms, push, chat, and in_app_feed.\n - To turn OFF a preference, you must set it to false.\n - To turn ON a preference, you must set it to true.\n\n <examples>\n <example>\n <description>\n Update the user's preferences to turn off email notifications for the \"welcome\" workflow.\n </description>\n <input>\n {\n \"workflows\": {\n \"welcome\": {\n \"channel_types\": {\n \"email\": false\n }\n }\n }\n }\n </example>\n </examples>\n `,\n parameters: z.object({\n environment: z\n .string()\n .optional()\n .describe(\n \"(string): The environment to set the user preferences in. Defaults to `development`.\"\n ),\n userId: z\n .string()\n .optional()\n .describe(\"(string): The userId of the User to update preferences for.\"),\n workflows: z\n .record(z.string(), z.any())\n .optional()\n .describe(\n \"(object): The workflows to update where the key is the workflow key, and the value of the object is an object that contains a `channel_types` key with a boolean value for each channel type.\"\n ),\n categories: z\n .record(z.string(), z.any())\n .optional()\n .describe(\n \"(object): The categories to update where the key is the category key, and the value of the object is an object that contains a `channel_types` key with a boolean value for each channel type.\"\n ),\n channel_types: z\n .record(z.string(), z.boolean())\n .optional()\n .describe(\n \"(object): The channel types to update where the key is the channel type, and the value of the object is a boolean value.\"\n ),\n }),\n execute: (knockClient, config) => async (params) => {\n const publicClient = await knockClient.publicApi(params.environment);\n\n const existingPreferences = await publicClient.users.getPreferences(\n params.userId ?? config.userId,\n {\n preferenceSet: \"default\",\n }\n );\n\n const updatedPreferences = {\n ...existingPreferences,\n workflows: {\n ...existingPreferences.workflows,\n ...params.workflows,\n },\n categories: {\n ...existingPreferences.categories,\n ...params.categories,\n },\n channel_types: {\n ...existingPreferences.channel_types,\n ...params.channel_types,\n },\n };\n\n return await publicClient.users.setPreferences(\n params.userId ?? config.userId,\n updatedPreferences\n );\n },\n});\n\nconst getUserMessages = KnockTool({\n method: \"get_user_messages\",\n name: \"Get user messages\",\n description: `\n Retrieves the messages that this user has received from the service. Use this tool when you need information about the notifications that the user has received, including if the message has been read, seen, or interacted with. This will return a list of messages across all of the channels.\n\n If the userId is not provided, it will use the userId from the config.\n `,\n parameters: z.object({\n environment: z\n .string()\n .optional()\n .describe(\n \"(string): The environment to retrieve the user messages from. Defaults to `development`.\"\n ),\n userId: z\n .string()\n .optional()\n .describe(\"(string): The userId of the User to retrieve messages for.\"),\n workflowRunId: z\n .string()\n .optional()\n .describe(\n \"(string): The workflowRunId of the User to retrieve. Use this when you want to retrieve messages sent from a workflow trigger.\"\n ),\n }),\n execute: (knockClient, config) => async (params) => {\n const publicClient = await knockClient.publicApi(params.environment);\n\n const messages = await publicClient.users.getMessages(\n params.userId ?? config.userId,\n {\n workflow_run_id: params.workflowRunId,\n }\n );\n\n return messages.items.map(serializeMessageResponse);\n },\n});\n\nexport const users = {\n getUser,\n createOrUpdateUser,\n getUserPreferences,\n setUserPreferences,\n getUserMessages,\n};\n\nexport const permissions = {\n read: [\"getUser\", \"getUserMessages\", \"getUserPreferences\"],\n manage: [\"createOrUpdateUser\", \"setUserPreferences\"],\n};\n","import { Workflow } from \"@knocklabs/mgmt/resources/index.mjs\";\nimport jsonSchemaToZod from \"json-schema-to-zod\";\nimport { z } from \"zod\";\n\nimport { Config } from \"../../types\";\nimport { KnockClient } from \"../knock-client\";\nimport { KnockTool } from \"../knock-tool\";\n\nimport { recipientSchema } from \"./shared\";\n\n/**\n * Converts a workflow into a tool that can be used to trigger the workflow.\n *\n * @param workflow - The workflow to convert to a tool.\n *\n * @returns A `KnockTool` that can be used to trigger the workflow.\n */\nfunction workflowAsTool(workflow: Workflow) {\n return KnockTool({\n method: `trigger_${workflow.key.replace(\"-\", \"_\")}_workflow`,\n name: `Trigger ${workflow.name} workflow`,\n description: `Triggers the ${workflow.name} workflow. Use this tool when you're asked to notify, send, or trigger for ${workflow.name} or ${workflow.key}.\n\n ${workflow.description ? `Additional information to consider on when to use this tool: ${workflow.description}` : \"\"}\n \n Returns the workflow run ID, which can be used to lookup messages produced by the workflow.`,\n parameters: z.object({\n environment: z.string().optional(),\n actor: recipientSchema\n .optional()\n .describe(\"An optional actor to trigger the workflow with.\"),\n recipients: z\n .array(recipientSchema)\n .describe(\n \"An optional array of recipients to trigger the workflow with.\"\n )\n .optional(),\n // Here we dynamically generate a zod schema from the workflow's `trigger_data_json_schema`\n // This allows us to validate the data passed to the workflow\n data: workflow.trigger_data_json_schema\n ? eval(jsonSchemaToZod(workflow.trigger_data_json_schema)).describe(\n \"The data to pass to the workflow.\"\n )\n : z\n .record(z.string(), z.any())\n .optional()\n .describe(\"The data to pass to the workflow.\"),\n tenant: z\n .string()\n .optional()\n .describe(\"The tenant ID to trigger the workflow for.\"),\n }),\n execute: (knockClient, config) => async (params) => {\n const publicClient = await knockClient.publicApi(params.environment);\n\n const result = await publicClient.workflows.trigger(workflow.key, {\n recipients: params.recipients ?? [config.userId],\n actor: params.actor,\n data: params.data,\n tenant: params.tenant ?? config.tenantId,\n });\n\n return result.workflow_run_id;\n },\n });\n}\n\n/**\n * Creates a tool for each workflow in the given environment.\n *\n * @param knockClient - The Knock client to use to list workflows.\n * @param config - The config to use to list workflows.\n *\n * @returns An array of `KnockTool`s that can be used to trigger the workflows.\n */\nasync function createWorkflowTools(\n knockClient: KnockClient,\n config: Config,\n workflowKeysToInclude?: string[]\n) {\n const workflows: Workflow[] = [];\n\n for await (const workflow of knockClient.workflows.list({\n environment: config.environment ?? \"development\",\n })) {\n // If we have a list of workflow keys to include, and the current workflow is not in the list, skip it\n if (\n workflowKeysToInclude &&\n !workflowKeysToInclude.includes(workflow.key)\n ) {\n continue;\n }\n\n workflows.push(workflow);\n }\n\n // Build a tool for each workflow\n return workflows.map((workflow) => workflowAsTool(workflow));\n}\n\nexport { createWorkflowTools, workflowAsTool };\n","import { z } from \"zod\";\n\nconst recipientSchema = z\n .union([\n z.string().describe(\"A user ID (string).\"),\n z\n .object({ id: z.string(), collection: z.string() })\n .describe(\"A reference to an object in a collection.\"),\n ])\n .describe(\n \"A recipient can be a user ID or a reference to an object in a collection.\"\n );\n\nexport { recipientSchema };\n","import { toolPermissions, tools } from \"../lib/tools/index.js\";\nimport { ToolkitConfig, ToolCategory } from \"../types.js\";\n\nimport { KnockClient } from \"./knock-client.js\";\nimport { KnockTool } from \"./knock-tool.js\";\nimport { createWorkflowTools } from \"./tools/workflows-as-tools.js\";\n\n/**\n * Given a list of tools, and some config may describe the tools that should be provided to the LLM,\n * returns a filtered list of tools that match the config.\n *\n * Options:\n * `*` - All tools\n * `users.*` - All tools that start with `users.`\n * `users.getUser` - A specific tool\n *\n */\nexport function filterTools(\n tools: Record<string, Record<string, KnockTool>>,\n pattern: string | undefined\n): KnockTool[] {\n if (!pattern) {\n throw new Error(\"No pattern provided\");\n }\n\n // If the pattern is `*`, return all tools\n if (pattern === \"*\") {\n return Object.values(tools).flatMap((category) => Object.values(category));\n }\n\n const [category, tool] = pattern.split(\".\");\n\n // If the pattern is `*.*`, return all tools\n if (category === \"*\" && tool === \"*\") {\n return Object.values(tools).flatMap((category) => Object.values(category));\n }\n\n if (category && !tools[category]) {\n throw new Error(`Tool category ${category} not found`);\n }\n\n // If the pattern is `users.*`, return all tools that start with `users.`\n if (category && tool === \"*\") {\n return Object.values(tools[category]);\n }\n\n // If the pattern is `users.getUser`, return the `getUser` tool\n if (category && tool && !tools[category][tool]) {\n throw new Error(`Tool ${pattern} not found`);\n }\n\n return [tools[category][tool]];\n}\n\n/**\n * Given a category and a list of permissions, return a list of tools that the user has permission to use.\n *\n * @param category - The category to get tools for\n * @param categoryPermissions - The permissions to use\n * @returns A list of tools that the user has permission to use\n */\nexport function getToolsWithPermissions(\n category: keyof typeof toolPermissions,\n categoryPermissions: Record<string, boolean | string[] | undefined>\n) {\n // Return all of the tools for the category that have permission\n const toolsInCategory = tools[category] as Record<string, KnockTool>;\n const toolPermissionsInCategory = toolPermissions[category] as Record<\n string,\n string[]\n >;\n\n // Look over each permission type, like `read: true`\n // If it's `true`, then find all of the tools that have that permission\n return Object.entries(categoryPermissions).reduce(\n (acc: KnockTool[], [permissionType, hasPermission]) => {\n if (\n (Array.isArray(hasPermission) && hasPermission.length > 0) ||\n hasPermission === true\n ) {\n return acc.concat(\n toolPermissionsInCategory[permissionType].map(\n (toolName) => toolsInCategory[toolName]\n )\n );\n }\n return acc;\n },\n []\n );\n}\n\n/**\n * Given a config, return a list of tools for each category that the user has permission to use.\n *\n * If the user has run permissions for workflows, then we need to get the workflow triggers tools,\n * and add them to the list of tools for the workflows category.\n *\n * @param config - The config to use\n * @returns A list of tools for each category that the user has permission to use\n */\nexport async function getToolsByPermissionsInCategories(\n knockClient: KnockClient,\n config: ToolkitConfig\n): Promise<Record<ToolCategory, KnockTool[]>> {\n const toolsByCategory = Object.keys(config.permissions).reduce(\n (acc, category) => {\n const categoryKey = category as ToolCategory;\n const categoryPermissions = config.permissions[categoryKey];\n\n if (tools[categoryKey] && categoryPermissions) {\n const tools = getToolsWithPermissions(categoryKey, categoryPermissions);\n\n return { ...acc, [categoryKey]: tools };\n }\n\n return acc;\n },\n {} as Record<ToolCategory, KnockTool[]>\n );\n\n // If the user has run permissions for workflows, then we need to get the workflow triggers tools,\n // and add them to the list of tools for the workflows category.\n if (\n config.permissions.workflows &&\n config.permissions.workflows.trigger &&\n Array.isArray(config.permissions.workflows.trigger)\n ) {\n const workflowTools = await createWorkflowTools(\n knockClient,\n config,\n config.permissions.workflows.trigger\n );\n toolsByCategory.workflows = [\n ...toolsByCategory.workflows,\n ...workflowTools,\n ];\n }\n\n return toolsByCategory;\n}\n\n/**\n * Given a list of tools, return a map of tools by method name.\n *\n * @param tools - The tools to serialize\n * @returns A map of tools by method name\n */\nexport function getToolMap(tools: KnockTool[]) {\n return tools.reduce(\n (acc, tool) => {\n acc[tool.method] = tool;\n return acc;\n },\n {} as Record<string, KnockTool>\n );\n}\n\n/**\n * Serialize a message response from the API to a more LLM-friendly format.\n *\n * @param message - The message to serialize\n * @returns A serialized message\n */\nexport function serializeMessageResponse(message: Record<string, any>) {\n return {\n id: message.id,\n status: message.status,\n engagement_statuses: message.engagement_statuses,\n data: message.data,\n metadata: message.metadata,\n };\n}\n","import { Workflow } from \"@knocklabs/mgmt/resources/index.js\";\nimport { z } from \"zod\";\n\nimport { KnockTool } from \"../knock-tool.js\";\n\nimport { workflowStepTools } from \"./workflow-steps.js\";\n\n/**\n * A slimmed down version of the Workflow resource that is easier to work with in the LLM.\n */\nexport type SerializedWorkflow = {\n key: string;\n name: string;\n description: string | undefined;\n categories: string[] | undefined;\n schema: Record<string, unknown> | undefined;\n};\n\nexport function serializeWorkflowResponse(\n workflow: Workflow\n): SerializedWorkflow {\n return {\n key: workflow.key,\n name: workflow.name,\n description: workflow.description,\n categories: workflow.categories,\n schema: workflow.trigger_data_json_schema,\n };\n}\n\nconst listWorkflows = KnockTool({\n method: \"list_workflows\",\n name: \"List workflows\",\n description: `\n List all workflows available for the given environment. Returns structural information about the workflows, including the key, name, description, and categories.\n\n Use this tool when you need to understand which workflows are available to be called.\n `,\n parameters: z.object({\n environment: z\n .string()\n .optional()\n .describe(\n \"(string): The environment to list workflows for. Defaults to `development`.\"\n ),\n }),\n execute: (knockClient, config) => async (params) => {\n const allWorkflows: SerializedWorkflow[] = [];\n const listParams = {\n environment: params.environment ?? config.environment ?? \"development\",\n };\n\n for await (const workflow of knockClient.workflows.list(listParams)) {\n allWorkflows.push(serializeWorkflowResponse(workflow));\n }\n\n return allWorkflows;\n },\n});\n\nconst getWorkflow = KnockTool({\n method: \"get_workflow\",\n name: \"Get workflow\",\n description: `\n Get a workflow by key. Returns structural information about the workflow, including the key, name, description, and categories.\n `,\n parameters: z.object({\n environment: z\n .string()\n .optional()\n .describe(\n \"(string): The environment to get the workflow for. Defaults to `development`.\"\n ),\n workflowKey: z\n .string()\n .describe(\"(string): The key of the workflow to get.\"),\n }),\n execute: (knockClient, config) => async (params) => {\n const workflow = await knockClient.workflows.retrieve(params.workflowKey, {\n environment: params.environment ?? config.environment ?? \"development\",\n });\n\n return serializeWorkflowResponse(workflow);\n },\n});\n\nconst triggerWorkflow = KnockTool({\n method: \"trigger_workflow\",\n name: \"Trigger workflow\",\n description: `\n Trigger a workflow for one or more recipients, which may produce one or more messages for each recipient depending on the workflow's steps.\n\n Use this tool when you need to trigger a workflow to send a notification across the channels configured for the workflow. \n\n When recipients aren't provided, the workflow will be triggered for the current user specified in the config.\n\n Returns the workflow run ID, which can be used to lookup messages produced by the workflow.\n `,\n parameters: z.object({\n environment: z\n .string()\n .optional()\n .describe(\n \"(string): The environment to trigger the workflow in. Defaults to `development`.\"\n ),\n workflowKey: z\n .string()\n .describe(\"(string): The key of the workflow to trigger.\"),\n recipients: z\n .array(z.string())\n .optional()\n .describe(\n \"(array): The recipients to trigger the workflow for. This is an array of user IDs.\"\n ),\n data: z\n .record(z.string(), z.any())\n .optional()\n .describe(\"(object): Data to pass to the workflow.\"),\n tenant: z\n .record(z.string(), z.any())\n .optional()\n .describe(\n \"(object): The tenant to trigger the workflow for. Must contain an id if being sent.\"\n ),\n }),\n execute: (knockClient, config) => async (params) => {\n const publicClient = await knockClient.publicApi(params.environment);\n\n const result = await publicClient.workflows.trigger(params.workflowKey, {\n recipients: params.recipients ?? [config.userId] ?? [],\n data: params.data,\n tenant: params.tenant ?? config.tenantId,\n });\n\n return result.workflow_run_id;\n },\n});\n\nconst createWorkflow = KnockTool({\n method: \"create_workflow\",\n name: \"Create workflow\",\n description: `\n Create a new workflow, which is used to control the flow of notifications. Use this tool when you're asked to create a new workflow, or you need to create a new workflow before adding a step to it.\n `,\n parameters: z.object({\n environment: z\n .string()\n .optional()\n .describe(\n \"(string): The environment to create the workflow in. Defaults to `development`.\"\n ),\n workflowKey: z\n .string()\n .describe(\n \"(string): The key of the workflow to create. Only use a kebab-case string with no spaces or special characters.\"\n ),\n name: z.string().describe(\"(string): The name of the workflow.\"),\n description: z\n .string()\n .describe(\"(string): The description of the workflow.\"),\n categories: z\n .array(z.string())\n .describe(\"(array): The categories to add to the workflow.\"),\n }),\n execute: (knockClient, config) => async (params) => {\n const result = await knockClient.workflows.upsert(params.workflowKey, {\n environment: config.environment ?? \"development\",\n workflow: {\n name: params.name,\n description: params.description,\n categories: params.categories ?? [],\n steps: [],\n },\n });\n\n return serializeWorkflowResponse(result.workflow);\n },\n});\n\nconst createOneOffWorkflowSchedule = KnockTool({\n method: \"create_one_off_workflow_schedule\",\n name: \"Create one-off workflow schedule\",\n description: `\n Create a one-off workflow schedule for a user. Use this tool when you need to schedule the execution of a workflow for a specific user in the future, like to power a delayed notification.\n \n Schedules can accept a set of data that will be passed to the workflow trigger when it is executed. When the userId is not provided, the schedule will be created for the current user specified in the config.\n\n Examples:\n \n - In three days, send a welcome email to a user\n - In one hour, send a password reset email to a user\n - In two weeks, send a survey to a user\n `,\n parameters: z.object({\n environment: z\n .string()\n .optional()\n .describe(\n \"(string): The environment to create the workflow in. Defaults to `development`.\"\n ),\n workflowKey: z\n .string()\n .describe(\"(string): The key of the workflow to schedule.\"),\n userId: z\n .string()\n .describe(\n \"(string): The userId of the user to schedule the workflow for.\"\n ),\n scheduledAt: z\n .string()\n .describe(\n \"(string): The date and time to schedule the workflow for. Must be in ISO 8601 format.\"\n ),\n data: z\n .record(z.string(), z.any())\n .optional()\n .describe(\"(object): Data to pass to the workflow.\"),\n }),\n execute: (knockClient, config) => async (params) => {\n const publicClient = await knockClient.publicApi(params.environment);\n\n return await publicClient.workflows.createSchedules(params.workflowKey, {\n recipients: [params.userId ?? config.userId],\n scheduled_at: params.scheduledAt,\n data: params.data,\n });\n },\n});\n\nexport const workflows = {\n listWorkflows,\n getWorkflow,\n triggerWorkflow,\n createWorkflow,\n ...workflowStepTools,\n createOneOffWorkflowSchedule,\n};\n\nexport const permissions = {\n read: [\"listWorkflows\", \"getWorkflow\"],\n manage: [\n \"createWorkflow\",\n \"createOneOffWorkflowSchedule\",\n \"triggerWorkflow\",\n ].concat(...Object.keys(workflowStepTools)),\n trigger: [],\n};\n","import {\n ChatTemplate,\n EmailTemplate,\n InAppFeedTemplate,\n PushTemplate,\n SMSTemplate,\n Workflow,\n WorkflowStep,\n WorkflowUpsertParams,\n} from \"@knocklabs/mgmt/resources/index.js\";\nimport { z } from \"zod\";\n\nimport { KnockClient } from \"../knock-client.js\";\nimport { KnockTool } from \"../knock-tool.js\";\n\nimport { serializeWorkflowResponse } from \"./workflows\";\n\nfunction generateStepRef(stepType: string) {\n const randomString = Math.random().toString(36).substring(2, 7).toUpperCase();\n return `${stepType}_${randomString}`;\n}\n\nasync function updateWorkflowWithStep(\n knockClient: KnockClient,\n workflow: Workflow,\n step: WorkflowStep,\n environment: string\n) {\n const workflowParams: WorkflowUpsertParams = {\n environment,\n workflow: {\n ...workflow,\n steps: [...workflow.steps, step],\n },\n };\n\n const result = await knockClient.workflows.upsert(\n workflow.key,\n workflowParams\n );\n\n return serializeWorkflowResponse(result.workflow);\n}\n\nconst SHARED_PROMPTS = {\n workflow: `\n To use this tool, you MUST first create a workflow using the \\`createWorkflow\\` tool, or get an existing workflow using the \\`getWorkflow\\` tool. You ONLY need to pass the workflow key to this tool and the sms step will be added to the end of the workflow's steps array.\n `,\n liquid: `\n ## Personalization\n\n If you need to include personalization, you can use liquid to include dynamic content in the email and the subject line.\n The following variables are always available to use in liquid:\n\n - \\`recipient.id\\`: The ID of the recipient. \n - \\`recipient.name\\`: The name of the recipient.\n - \\`recipient.email\\`: The email of the recipient.\n - \\`recipient.phone_number\\`: The phone number of the recipient.\n\n You can supply **any** other dynamic variables you think are needed by referencing them under the \\`data\\` key. You add those like \\`{{ data.variable_name }}\\`.\n\n <example>\n # Hello, {{ recipient.name }}\n\n This is a dynamic message: \n \n > {{ data.message }}\n </example>\n\n ## Liquid helpers\n\n You have access to a full suite of liquid helpers to help you perform common templating tasks. The full list of helper is available here: https://docs.knock.app/designing-workflows/template-editor/reference-liquid-helpers.\n\n <example>\n Hello, {{ recipient.name | split: \" \" | first | default: \"there\" }}\n </example>\n `,\n};\n\nconst createEmailStepInWorkflow = KnockTool({\n method: \"create_email_step_in_workflow\",\n name: \"Create email step in workflow\",\n description: `\n Creates an email step in a workflow. Use this tool when you're asked to create an email notification and you need to specify the content of the email.\n\n ${SHARED_PROMPTS.workflow}\n\n ## Blocks\n\n The content of the email is supplied as an array of \"blocks\". The simplest block is a \"markdown\" block, which supports content in a markdown format. That should always be your default block type. \n\n The following block types are supported:\n\n - \\`markdown\\`: A block that supports markdown content.\n - \\`html\\`: A block that supports markdown content.\n - \\`image\\`: A block that supports an image.\n - \\`button_set\\`: A block that adds one or more buttons.\n - \\`divider\\`: A block that supports a divider.\n - \\`partial\\`: A block that supports rendering a shared content partial.\n\n <example>\n {\n \"blocks\": [\n {\n \"type\": \"markdown\",\n \"content\": \"# Greetings from Knock!\\nHello, {{ recipient.name }}.\"\n },\n {\n \"type\": \"divider\"\n },\n {\n \"type\": \"button_set\",\n \"buttons\": [\n {\n \"label\": \"Approve\",\n \"action\": \"{{ data.primary_action_url }}\",\n \"variant\": \"solid\"\n }\n ]\n }\n ]\n }\n </example>\n\n ### Markdown\n\n When using the \\`markdown\\` block, you must supply a \\`content\\` key. The \\`content\\` key supports markdown.\n\n <example>\n {\n \"type\": \"markdown\",\n \"content\": \"Hello, world!\"\n }\n </example>\n\n ### HTML \n\n The \\`html\\` block supports raw HTML content. This should be used sparingly, and only when you need to include custom HTML content that markdown doesn't support. When using the \\`html\\` block, you must supply a \\`content\\` key. HTML content can include liquid personalization.\n\n ### Button sets\n\n Button sets are a special type of block that allows you to add one or more buttons to the email. They're useful for directing users to take specific actions. Button sets support one or more buttons. You must always include at least one button in a button set.\n\n Buttons are specified in a button set under the \\`buttons\\` key. Each button requires a \\`label\\`, \\`action\\`, and \\`variant\\`. The ONLY valid variants are \\`solid\\` and \\`outline\\`. The label and action can allowed be dynamic variables using liquid.\n\n <example>\n {\n \"type\": \"button_set\",\n \"buttons\": [\n {\n \"label\": \"Approve\",\n \"action\": \"https://example.com\",\n \"variant\": \"solid\"\n }\n ]\n }\n </example>\n\n ### Image\n\n Images are a special type of block that allows you to add an image to the email. When using the \\`image\\` block, you must supply a \\`url\\` key. The \\`url\\` key supports a URL to an image.\n\n <example>\n {\n \"type\": \"image\",\n \"url\": \"https://example.com/image.png\"\n }\n </example>\n\n ${SHARED_PROMPTS.liquid}\n\n ## Partials\n\n If you need to reuse content across multiple emails, you can create or reference an existing partial and reference it in the email. You should only use partials if you're instructed to do so.\n\n When you do need to use a partial in an email, you can use the \\`partial\\` block and then set the \\`key\\` to the key of the partial you want to use. If the partial requires any variables, you pass those in the \\`attrs\\` key.\n\n ## Writing style\n\n Unless asked otherwise, you should write content for the email in a concise and formal writing style. Do NOT use complex language or try to over explain. Keep the subject line to 8 words or less.\n `,\n parameters: z.object({\n workflowKey: z\n .string()\n .describe(\"(string): The key of the workflow to add the step to.\"),\n blocks: z\n .array(z.any())\n .describe(\"(array): The blocks for the email step.\"),\n subject: z.string().describe(\"(string): The subject of the email step.\"),\n }),\n execute: (knockClient, config) => async (params) => {\n const workflow = await knockClient.workflows.retrieve(params.workflowKey, {\n environment: config.environment ?? \"development\",\n });\n\n const emailChannelsPage = await knockClient.channels.list();\n const emailChannels = emailChannelsPage.entries.filter(\n (channel) => channel.type === \"email\"\n );\n\n if (emailChannels.length === 0) {\n throw new Error(\"No email channels found\");\n }\n\n return await updateWorkflowWithStep(\n knockClient,\n workflow,\n // @ts-expect-error\n {\n type: \"channel\",\n channel_key: emailChannels[0].key,\n template: {\n settings: {\n layout_key: \"default\",\n },\n subject: params.subject,\n visual_blocks: params.blocks,\n } as EmailTemplate,\n ref: generateStepRef(\"email\"),\n },\n config.environment ?? \"development\"\n );\n },\n});\n\nconst createSmsStepInWorkflow = KnockTool({\n method: \"create_sms_step_in_workflow\",\n name: \"Create sms step in workflow\",\n description: `\n Creates an SMS step in a workflow. Use this tool when you're asked to create an SMS notification and you need to specify the content of the SMS. \n \n ${SHARED_PROMPTS.workflow}\n\n ${SHARED_PROMPTS.liquid}\n `,\n parameters: z.object({\n workflowKey: z\n .string()\n .describe(\"(string): The key of the workflow to add the step to.\"),\n content: z.string().describe(\"(string): The content of the SMS.\"),\n }),\n execute: (knockClient, config) => async (params) => {\n const workflow = await knockClient.workflows.retrieve(params.workflowKey, {\n environment: config.environment ?? \"development\",\n });\n\n const smsChannelsPage = await knockClient.channels.list();\n const smsChannels = smsChannelsPage.entries.filter(\n (channel) => channel.type === \"sms\"\n );\n\n if (smsChannels.length === 0) {\n throw new Error(\"No SMS channels found\");\n }\n\n return await updateWorkflowWithStep(\n knockClient,\n workflow,\n // @ts-expect-error\n {\n type: \"channel\",\n channel_key: smsChannels[0].key,\n template: {\n text_body: params.content,\n } as SMSTemplate,\n ref: generateStepRef(\"sms\"),\n },\n config.environment ?? \"development\"\n );\n },\n});\n\nconst createPushStepInWorkflow = KnockTool({\n method: \"create_push_step_in_workflow\",\n name: \"Create push step in workflow\",\n description: `\n Creates a push step in a workflow. Use this tool when you're asked to create a push notification and you need to specify the content of the push notification.\n\n ${SHARED_PROMPTS.workflow}\n\n ${SHARED_PROMPTS.liquid}\n\n Be terse in your writing as this is a push notification and should be direct and to the point.\n `,\n parameters: z.object({\n workflowKey: z\n .string()\n .describe(\"(string): The key of the workflow to add the step to.\"),\n title: z.string().describe(\"(string): The title of the push notification.\"),\n content: z\n .string()\n .describe(\"(string): The content (body) of the push notification.\"),\n }),\n execute: (knockClient, config) => async (params) => {\n const workflow = await knockClient.workflows.retrieve(params.workflowKey, {\n environment: config.environment ?? \"development\",\n });\n\n const pushChannelsPage = await knockClient.channels.list();\n const pushChannels = pushChannelsPage.entries.filter(\n (channel) => channel.type === \"push\"\n );\n\n if (pushChannels.length === 0) {\n throw new Error(\"No push channels found\");\n }\n\n return await updateWorkflowWithStep(\n knockClient,\n workflow,\n // @ts-expect-error\n {\n type: \"channel\",\n channel_key: pushChannels[0].key,\n template: {\n title: params.title,\n text_body: params.content,\n } as PushTemplate,\n ref: generateStepRef(\"push\"),\n },\n config.environment ?? \"development\"\n );\n },\n});\n\n// TODO: Add support for action buttons, not just the action URL\nconst createInAppFeedStepInWorkflow = KnockTool({\n method: \"create_in_app_feed_step_in_workflow\",\n name: \"Create in app feed step in workflow\",\n description: `\n Creates an in app feed step in a workflow. Use this tool when you're asked to create an in app feed notification and you need to specify the content of the in app feed notification. \n\n ${SHARED_PROMPTS.workflow}\n\n ${SHARED_PROMPTS.liquid}\n `,\n parameters: z.object({\n workflowKey: z\n .string()\n .describe(\"(string): The key of the workflow to add the step to.\"),\n actionUrl: z\n .string()\n .describe(\n \"(string): The URL to navigate to when the in app feed is tapped.\"\n ),\n body: z\n .string()\n .describe(\"(string): The markdown content of the in app feed.\"),\n }),\n execute: (knockClient, config) => async (params) => {\n const workflow = await knockClient.workflows.retrieve(params.workflowKey, {\n environment: config.environment ?? \"development\",\n });\n\n const inAppChannelsPage = await knockClient.channels.list();\n const inAppChannels = inAppChannelsPage.entries.filter(\n (channel) => channel.type === \"in_app_feed\"\n );\n\n if (inAppChannels.length === 0) {\n throw new Error(\"No in app channels found\");\n }\n\n return await updateWorkflowWithStep(\n knockClient,\n workflow,\n // @ts-expect-error\n {\n type: \"channel\",\n channel_key: inAppChannels[0].key,\n template: {\n action_url: params.actionUrl,\n markdown_body: params.body,\n } as InAppFeedTemplate,\n ref: generateStepRef(\"in_app_feed\"),\n },\n config.environment ?? \"development\"\n );\n },\n});\n\nconst createChatStepInWorkflow = KnockTool({\n method: \"create_chat_step_in_workflow\",\n name: \"Create chat step in workflow\",\n description: `\n Creates a chat step in a workflow. Use this tool when you're asked to create a chat, Slack, Discord, or Microsoft Teams notification and you need to specify the content of the chat notification.\n\n ${SHARED_PROMPTS.workflow}\n\n ${SHARED_PROMPTS.liquid}\n `,\n parameters: z.object({\n workflowKey: z\n .string()\n .describe(\"(string): The key of the workflow to add the step to.\"),\n body: z\n .string()\n .describe(\"(string): The markdown content of the notification.\"),\n }),\n execute: (knockClient, config) => async (params) => {\n const workflow = await knockClient.workflows.retrieve(params.workflowKey, {\n environment: config.environment ?? \"development\",\n });\n\n const chatChannelsPage = await knockClient.channels.list();\n const chatChannels = chatChannelsPage.entries.filter(\n (channel) => channel.type === \"chat\"\n );\n\n if (chatChannels.length === 0) {\n throw new Error(\"No chat channels found\");\n }\n\n return await updateWorkflowWithStep(\n knockClient,\n workflow,\n // @ts-expect-error\n {\n type: \"channel\",\n channel_key: chatChannels[0].key,\n template: {\n markdown_body: params.body,\n } as ChatTemplate,\n ref: generateStepRef(\"chat\"),\n },\n config.environment ?? \"development\"\n );\n },\n});\n\nconst createDelayStepInWorkflow = KnockTool({\n method: \"create_delay_step_in_workflow\",\n name: \"Create delay step in workflow\",\n description: `\n Creates a delay step in a workflow. Use this tool when you're asked to add a delay to the workflow that pauses, or waits for a period of time before continuing.\n\n ${SHARED_PROMPTS.workflow}\n \n Delays are specified in \"unit\" and \"value\" pairs. The only valid units are \"seconds\", \"minutes\", \"hours\", and \"days\".\n\n <example>\n {\n \"delayValue\": 5,\n \"delayUnit\": \"minutes\"\n }\n </example>\n `,\n parameters: z.object({\n workflowKey: z\n .string()\n .describe(\"(string): The key of the workflow to add the step to.\"),\n delayValue: z.number().describe(\"(number): The value of the delay.\"),\n delayUnit: z\n .enum([\"seconds\", \"minutes\", \"hours\", \"days\"])\n .describe(\"(enum): The unit of the delay.\"),\n }),\n execute: (knockClient, config) => async (params) => {\n const workflow = await knockClient.workflows.retrieve(params.workflowKey, {\n environment: config.environment ?? \"development\",\n });\n\n const workflowParams: WorkflowUpsertParams = {\n environment: config.environment ?? \"development\",\n workflow: {\n ...workflow,\n steps: [\n // @ts-expect-error\n ...workflow.steps,\n // @ts-expect-error\n {\n type: \"delay\",\n settings: {\n delay_for: {\n value: params.delayValue,\n unit: params.delayUnit,\n },\n },\n ref: generateStepRef(\"delay\"),\n },\n ],\n },\n };\n\n const result = await knockClient.workflows.upsert(\n params.workflowKey,\n workflowParams\n );\n\n return serializeWorkflowResponse(result.workflow);\n },\n});\n\nconst createBatchStepInWorkflow = KnockTool({\n method: \"create_batch_step_in_workflow\",\n name: \"Create batch step in workflow\",\n description: `\n Creates a batch step in a workflow. Use this tool when you're asked to create a batch step or asked to add digesting behavior to a workflow. The batch step collects multiple workflow triggers for a single recipient over a period of time and then flushes the content to the next step.\n\n ${SHARED_PROMPTS.workflow}\n\n Batch windows are specified in \"unit\" and \"value\" pairs. The only valid units are \"seconds\", \"minutes\", \"hours\", and \"days\".\n\n <example>\n {\n \"batchWindow\": {\n \"value\": 5,\n \"unit\": \"minutes\"\n }\n }\n </example>\n `,\n parameters: z.object({\n workflowKey: z\n .string()\n .describe(\"(string): The key of the workflow to add the step to.\"),\n batchWindow: z.object({\n value: z.number().describe(\"(number): The value of the batch window.\"),\n unit: z\n .enum([\"seconds\", \"minutes\", \"hours\", \"days\"])\n .describe(\"(enum): The unit of the batch window.\"),\n }),\n }),\n execute: (knockClient, config) => async (params) => {\n const workflow = await knockClient.workflows.retrieve(params.workflowKey, {\n environment: config.environment ?? \"development\",\n });\n\n return await updateWorkflowWithStep(\n knockClient,\n workflow,\n // @ts-expect-error\n {\n type: \"batch\",\n settings: {\n batch_window: {\n value: params.batchWindow.value,\n unit: params.batchWindow.unit,\n },\n },\n ref: generateStepRef(\"batch\"),\n },\n config.environment ?? \"development\"\n );\n },\n});\n\nconst workflowStepTools = {\n // Channel steps\n createEmailStepInWorkflow,\n createSmsStepInWorkflow,\n createPushStepInWorkflow,\n createInAppFeedStepInWorkflow,\n createChatStepInWorkflow,\n\n // Function steps\n createDelayStepInWorkflow,\n createBatchStepInWorkflow,\n};\n\nexport { workflowStepTools };\n","import { channels, permissions as channelsPermissions } from \"./channels.js\";\nimport { commits, permissions as commitsPermissions } from \"./commits.js\";\nimport {\n documentation,\n permissions as documentationPermissions,\n} from \"./documentation.js\";\nimport {\n emailLayouts,\n permissions as emailLayoutsPermissions,\n} from \"./email-layouts.js\";\nimport {\n environments,\n permissions as environmentsPermissions,\n} from \"./environments.js\";\nimport {\n messageTypes,\n permissions as messageTypesPermissions,\n} from \"./message-types.js\";\nimport { messages, permissions as messagesPermissions } from \"./messages.js\";\nimport { objects, permissions as objectsPermissions } from \"./objects.js\";\nimport { partials, permissions as partialsPermissions } from \"./partials.js\";\nimport { tenants, permissions as tenantsPermissions } from \"./tenants.js\";\nimport { users, permissions as usersPermissions } from \"./users.js\";\nimport { workflows, permissions as workflowsPermissions } from \"./workflows.js\";\n\nexport const tools = {\n channels,\n commits,\n documentation,\n emailLayouts,\n environments,\n messages,\n messageTypes,\n objects,\n partials,\n tenants,\n users,\n workflows,\n};\n\nexport const allTools = {\n ...channels,\n ...commits,\n ...documentation,\n ...emailLayouts,\n ...environments,\n ...messageTypes,\n ...messages,\n ...objects,\n ...partials,\n ...tenants,\n ...users,\n ...workflows,\n};\n\nexport const toolPermissions = {\n channels: channelsPermissions,\n commits: commitsPermissions,\n documentation: documentationPermissions,\n emailLayouts: emailLayoutsPermissions,\n environments: environmentsPermissions,\n messages: messagesPermissions,\n messageTypes: messageTypesPermissions,\n objects: objectsPermissions,\n partials: partialsPermissions,\n tenants: tenantsPermissions,\n users: usersPermissions,\n workflows: workflowsPermissions,\n};\n"],"mappings":"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","names":["z","z","permissions","z","z","permissions","z","z","permissions","permissions","z","z","permissions","z","z","permissions","z","z","permissions","z","z","permissions","z","z","permissions","z","z","z","z","workflows","workflow","tools","category","z","messages","permissions","z","z","workflow","z","workflow","z","permissions","permissions"]}
|