@inkeep/agents-core 0.42.0 → 0.44.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (125) hide show
  1. package/dist/auth/auth.d.ts +28 -26
  2. package/dist/auth/auth.js +21 -16
  3. package/dist/auth/authz/client.d.ts +8 -3
  4. package/dist/auth/authz/client.js +23 -17
  5. package/dist/auth/authz/config.d.ts +50 -29
  6. package/dist/auth/authz/config.js +42 -33
  7. package/dist/auth/authz/index.d.ts +3 -3
  8. package/dist/auth/authz/index.js +3 -3
  9. package/dist/auth/authz/permissions.d.ts +0 -4
  10. package/dist/auth/authz/permissions.js +9 -13
  11. package/dist/auth/authz/sync.d.ts +23 -2
  12. package/dist/auth/authz/sync.js +127 -53
  13. package/dist/auth/init.d.ts +1 -0
  14. package/dist/auth/init.js +115 -0
  15. package/dist/auth/permissions.d.ts +9 -9
  16. package/dist/client-exports.d.ts +3 -6
  17. package/dist/client-exports.js +4 -7
  18. package/dist/constants/execution-limits-shared/defaults.d.ts +1 -1
  19. package/dist/constants/execution-limits-shared/defaults.js +1 -1
  20. package/dist/constants/execution-limits-shared/index.d.ts +1 -1
  21. package/dist/constants/otel-attributes.d.ts +5 -0
  22. package/dist/constants/otel-attributes.js +8 -3
  23. package/dist/constants/signoz-queries.d.ts +1 -0
  24. package/dist/constants/signoz-queries.js +2 -1
  25. package/dist/context/TemplateEngine.d.ts +0 -6
  26. package/dist/context/TemplateEngine.js +4 -18
  27. package/dist/credential-stores/keychain-store.d.ts +20 -8
  28. package/dist/credential-stores/keychain-store.js +107 -43
  29. package/dist/data-access/index.d.ts +5 -4
  30. package/dist/data-access/index.js +5 -4
  31. package/dist/data-access/manage/agentFull.js +70 -25
  32. package/dist/data-access/manage/agents.d.ts +41 -41
  33. package/dist/data-access/manage/agents.js +29 -21
  34. package/dist/data-access/manage/artifactComponents.d.ts +12 -12
  35. package/dist/data-access/manage/artifactComponents.js +1 -1
  36. package/dist/data-access/manage/contextConfigs.d.ts +12 -12
  37. package/dist/data-access/manage/dataComponents.d.ts +6 -6
  38. package/dist/data-access/manage/dataComponents.js +1 -1
  39. package/dist/data-access/manage/functionTools.d.ts +44 -21
  40. package/dist/data-access/manage/functionTools.js +34 -22
  41. package/dist/data-access/manage/subAgentExternalAgentRelations.d.ts +24 -24
  42. package/dist/data-access/manage/subAgentRelations.d.ts +26 -26
  43. package/dist/data-access/manage/subAgentTeamAgentRelations.d.ts +18 -18
  44. package/dist/data-access/manage/subAgents.d.ts +15 -15
  45. package/dist/data-access/manage/tools.d.ts +39 -28
  46. package/dist/data-access/manage/tools.js +73 -31
  47. package/dist/data-access/manage/triggers.d.ts +27 -1
  48. package/dist/data-access/runtime/apiKeys.d.ts +20 -20
  49. package/dist/data-access/runtime/cascade-delete.d.ts +48 -1
  50. package/dist/data-access/runtime/cascade-delete.js +52 -2
  51. package/dist/data-access/runtime/conversations.d.ts +24 -24
  52. package/dist/data-access/runtime/github-work-app-installations.d.ts +261 -0
  53. package/dist/data-access/runtime/github-work-app-installations.js +457 -0
  54. package/dist/data-access/runtime/messages.d.ts +18 -18
  55. package/dist/data-access/runtime/organizations.d.ts +2 -2
  56. package/dist/data-access/runtime/organizations.js +4 -4
  57. package/dist/data-access/runtime/tasks.d.ts +6 -6
  58. package/dist/db/manage/manage-schema.d.ts +533 -402
  59. package/dist/db/manage/manage-schema.js +38 -27
  60. package/dist/db/runtime/runtime-schema.d.ts +1021 -177
  61. package/dist/db/runtime/runtime-schema.js +173 -5
  62. package/dist/db/utils.d.ts +6 -0
  63. package/dist/db/utils.js +42 -0
  64. package/dist/dolt/branch.js +1 -1
  65. package/dist/dolt/branches-api.js +1 -1
  66. package/dist/dolt/index.d.ts +2 -2
  67. package/dist/dolt/index.js +4 -4
  68. package/dist/dolt/migrate-all-branches.js +6 -1
  69. package/dist/dolt/migrate-dolt.js +4 -1
  70. package/dist/dolt/ref-helpers.js +1 -1
  71. package/dist/dolt/ref-middleware.js +1 -1
  72. package/dist/dolt/ref-scope.js +1 -1
  73. package/dist/dolt/schema-sync.d.ts +2 -1
  74. package/dist/dolt/schema-sync.js +10 -1
  75. package/dist/env.d.ts +6 -4
  76. package/dist/env.js +11 -10
  77. package/dist/index.d.ts +15 -16
  78. package/dist/index.js +23 -24
  79. package/dist/types/@napi-rs__keyring/index.d.ts +14 -0
  80. package/dist/types/entities.d.ts +9 -2
  81. package/dist/types/index.d.ts +3 -3
  82. package/dist/types/utility.d.ts +17 -3
  83. package/dist/types/utility.js +2 -1
  84. package/dist/utils/JsonTransformer.d.ts +1 -3
  85. package/dist/utils/JsonTransformer.js +14 -23
  86. package/dist/utils/index.d.ts +3 -3
  87. package/dist/utils/index.js +3 -3
  88. package/dist/utils/jmespath-utils.d.ts +152 -0
  89. package/dist/utils/jmespath-utils.js +213 -0
  90. package/dist/utils/mcp-client.d.ts +1 -1
  91. package/dist/utils/mcp-client.js +1 -1
  92. package/dist/utils/signature-validation.d.ts +2 -0
  93. package/dist/utils/signature-validation.js +3 -0
  94. package/dist/utils/third-party-mcp-servers/composio-client.d.ts +13 -1
  95. package/dist/utils/third-party-mcp-servers/composio-client.js +24 -6
  96. package/dist/utils/third-party-mcp-servers/index.d.ts +2 -2
  97. package/dist/utils/third-party-mcp-servers/index.js +2 -2
  98. package/dist/utils/trigger-auth.d.ts +31 -8
  99. package/dist/utils/trigger-auth.js +121 -13
  100. package/dist/validation/agentFull.js +1 -1
  101. package/dist/validation/drizzle-schema-helpers.d.ts +4 -23
  102. package/dist/validation/drizzle-schema-helpers.js +3 -30
  103. package/dist/validation/index.d.ts +3 -5
  104. package/dist/validation/index.js +5 -7
  105. package/dist/validation/render-validation.js +19 -0
  106. package/dist/validation/schemas.d.ts +3675 -1665
  107. package/dist/validation/schemas.js +409 -94
  108. package/dist/validation/stream-event-schemas.d.ts +96 -1
  109. package/dist/validation/stream-event-schemas.js +67 -2
  110. package/drizzle/manage/0003_tiny_captain_universe.sql +8 -0
  111. package/drizzle/manage/0004_curious_phil_sheldon.sql +2 -0
  112. package/drizzle/manage/0005_silent_shatterstar.sql +53 -0
  113. package/drizzle/manage/0006_fixed_umar.sql +1 -0
  114. package/drizzle/manage/meta/0003_snapshot.json +3134 -0
  115. package/drizzle/manage/meta/0004_snapshot.json +3141 -0
  116. package/drizzle/manage/meta/0005_snapshot.json +3141 -0
  117. package/drizzle/manage/meta/0006_snapshot.json +3148 -0
  118. package/drizzle/manage/meta/_journal.json +28 -0
  119. package/drizzle/runtime/0010_previous_black_knight.sql +84 -0
  120. package/drizzle/runtime/meta/0010_snapshot.json +3066 -0
  121. package/drizzle/runtime/meta/_journal.json +7 -0
  122. package/package.json +12 -5
  123. package/spicedb/schema.zed +114 -0
  124. package/dist/validation/id-validation.d.ts +0 -24
  125. package/dist/validation/id-validation.js +0 -52
@@ -7,28 +7,35 @@ import "../../index.js";
7
7
  import { McpTool, ToolInsert, ToolSelect, ToolUpdate } from "../../types/entities.js";
8
8
 
9
9
  //#region src/data-access/manage/tools.d.ts
10
+ /**
11
+ * Convert DB result to McpTool skeleton WITHOUT MCP discovery.
12
+ * This is a fast path that returns status='unknown' and empty availableTools.
13
+ * Use this for list views where you want instant page load.
14
+ */
15
+ declare const dbResultToMcpToolSkeleton: (dbResult: ToolSelect, relationshipId?: string) => McpTool;
10
16
  declare const dbResultToMcpTool: (dbResult: ToolSelect, dbClient: AgentsManageDatabaseClient, credentialStoreRegistry?: CredentialStoreRegistry, relationshipId?: string, userId?: string) => Promise<McpTool>;
11
17
  declare const getToolById: (db: AgentsManageDatabaseClient) => (params: {
12
18
  scopes: ProjectScopeConfig;
13
19
  toolId: string;
14
20
  }) => Promise<{
15
- tenantId: string;
16
- projectId: string;
17
21
  id: string;
18
22
  name: string;
23
+ createdAt: string;
24
+ updatedAt: string;
19
25
  description: string | null;
26
+ headers: Record<string, string> | null;
27
+ projectId: string;
28
+ tenantId: string;
20
29
  config: {
21
30
  type: "mcp";
22
31
  mcp: ToolMcpConfig;
23
32
  };
24
33
  credentialReferenceId: string | null;
25
- createdAt: string;
26
- updatedAt: string;
27
- headers: Record<string, string> | null;
28
34
  credentialScope: string;
29
35
  imageUrl: string | null;
30
36
  capabilities: ToolServerCapabilities | null;
31
37
  lastError: string | null;
38
+ isWorkApp: boolean;
32
39
  } | null>;
33
40
  declare const getMcpToolById: (db: AgentsManageDatabaseClient) => (params: {
34
41
  scopes: ProjectScopeConfig;
@@ -56,6 +63,7 @@ declare const listTools: (db: AgentsManageDatabaseClient) => (params: {
56
63
  imageUrl: string | null;
57
64
  capabilities: ToolServerCapabilities | null;
58
65
  lastError: string | null;
66
+ isWorkApp: boolean;
59
67
  projectId: string;
60
68
  tenantId: string;
61
69
  id: string;
@@ -68,23 +76,24 @@ declare const listTools: (db: AgentsManageDatabaseClient) => (params: {
68
76
  };
69
77
  }>;
70
78
  declare const createTool: (db: AgentsManageDatabaseClient) => (params: ToolInsert) => Promise<{
71
- tenantId: string;
72
- projectId: string;
73
79
  id: string;
74
80
  name: string;
81
+ createdAt: string;
82
+ updatedAt: string;
75
83
  description: string | null;
84
+ headers: Record<string, string> | null;
85
+ projectId: string;
86
+ tenantId: string;
76
87
  config: {
77
88
  type: "mcp";
78
89
  mcp: ToolMcpConfig;
79
90
  };
80
91
  credentialReferenceId: string | null;
81
- createdAt: string;
82
- updatedAt: string;
83
- headers: Record<string, string> | null;
84
92
  credentialScope: string;
85
93
  imageUrl: string | null;
86
94
  capabilities: ToolServerCapabilities | null;
87
95
  lastError: string | null;
96
+ isWorkApp: boolean;
88
97
  }>;
89
98
  declare const updateTool: (db: AgentsManageDatabaseClient) => (params: {
90
99
  scopes: ProjectScopeConfig;
@@ -105,6 +114,7 @@ declare const updateTool: (db: AgentsManageDatabaseClient) => (params: {
105
114
  imageUrl: string | null;
106
115
  capabilities: ToolServerCapabilities | null;
107
116
  lastError: string | null;
117
+ isWorkApp: boolean;
108
118
  projectId: string;
109
119
  tenantId: string;
110
120
  id: string;
@@ -123,18 +133,18 @@ declare const addToolToAgent: (db: AgentsManageDatabaseClient) => (params: {
123
133
  needsApproval?: boolean;
124
134
  }> | null;
125
135
  }) => Promise<{
126
- tenantId: string;
127
- projectId: string;
128
136
  id: string;
129
- agentId: string;
130
137
  createdAt: string;
131
138
  updatedAt: string;
132
- toolId: string;
133
139
  headers: Record<string, string> | null;
140
+ agentId: string;
141
+ projectId: string;
142
+ tenantId: string;
134
143
  toolPolicies: Record<string, {
135
144
  needsApproval?: boolean;
136
145
  }> | null;
137
146
  subAgentId: string;
147
+ toolId: string;
138
148
  selectedTools: string[] | null;
139
149
  }>;
140
150
  declare const removeToolFromAgent: (db: AgentsManageDatabaseClient) => (params: {
@@ -142,18 +152,18 @@ declare const removeToolFromAgent: (db: AgentsManageDatabaseClient) => (params:
142
152
  subAgentId: string;
143
153
  toolId: string;
144
154
  }) => Promise<{
145
- tenantId: string;
146
- projectId: string;
147
155
  id: string;
148
- agentId: string;
149
156
  createdAt: string;
150
157
  updatedAt: string;
151
- toolId: string;
152
158
  headers: Record<string, string> | null;
159
+ agentId: string;
160
+ projectId: string;
161
+ tenantId: string;
153
162
  toolPolicies: Record<string, {
154
163
  needsApproval?: boolean;
155
164
  }> | null;
156
165
  subAgentId: string;
166
+ toolId: string;
157
167
  selectedTools: string[] | null;
158
168
  }>;
159
169
  /**
@@ -170,18 +180,18 @@ declare const upsertSubAgentToolRelation: (db: AgentsManageDatabaseClient) => (p
170
180
  }> | null;
171
181
  relationId?: string;
172
182
  }) => Promise<{
173
- tenantId: string;
174
- projectId: string;
175
183
  id: string;
176
- agentId: string;
177
184
  createdAt: string;
178
185
  updatedAt: string;
179
- toolId: string;
180
186
  headers: Record<string, string> | null;
187
+ agentId: string;
188
+ projectId: string;
189
+ tenantId: string;
181
190
  toolPolicies: Record<string, {
182
191
  needsApproval?: boolean;
183
192
  }> | null;
184
193
  subAgentId: string;
194
+ toolId: string;
185
195
  selectedTools: string[] | null;
186
196
  }>;
187
197
  /**
@@ -190,23 +200,24 @@ declare const upsertSubAgentToolRelation: (db: AgentsManageDatabaseClient) => (p
190
200
  declare const upsertTool: (db: AgentsManageDatabaseClient) => (params: {
191
201
  data: ToolInsert;
192
202
  }) => Promise<{
193
- tenantId: string;
194
- projectId: string;
195
203
  id: string;
196
204
  name: string;
205
+ createdAt: string;
206
+ updatedAt: string;
197
207
  description: string | null;
208
+ headers: Record<string, string> | null;
209
+ projectId: string;
210
+ tenantId: string;
198
211
  config: {
199
212
  type: "mcp";
200
213
  mcp: ToolMcpConfig;
201
214
  };
202
215
  credentialReferenceId: string | null;
203
- createdAt: string;
204
- updatedAt: string;
205
- headers: Record<string, string> | null;
206
216
  credentialScope: string;
207
217
  imageUrl: string | null;
208
218
  capabilities: ToolServerCapabilities | null;
209
219
  lastError: string | null;
220
+ isWorkApp: boolean;
210
221
  }>;
211
222
  //#endregion
212
- export { addToolToAgent, createTool, dbResultToMcpTool, deleteTool, getMcpToolById, getToolById, listTools, removeToolFromAgent, updateTool, upsertSubAgentToolRelation, upsertTool };
223
+ export { addToolToAgent, createTool, dbResultToMcpTool, dbResultToMcpToolSkeleton, deleteTool, getMcpToolById, getToolById, listTools, removeToolFromAgent, updateTool, upsertSubAgentToolRelation, upsertTool };
@@ -1,20 +1,41 @@
1
1
  import { CredentialStoreType, MCPServerType, MCPTransportType } from "../../types/utility.js";
2
2
  import { subAgentToolRelations, tools } from "../../db/manage/manage-schema.js";
3
3
  import { detectAuthenticationRequired } from "../../utils/auth-detection.js";
4
+ import { env } from "../../env.js";
4
5
  import { getLogger } from "../../utils/logger.js";
5
6
  import { getCredentialStoreLookupKeyFromRetrievalParams } from "../../utils/credential-store-utils.js";
6
7
  import { CredentialStuffer } from "../../credential-stuffer/CredentialStuffer.js";
7
8
  import "../../credential-stuffer/index.js";
9
+ import { createAgentsRunDatabaseClient } from "../../db/runtime/runtime-client.js";
8
10
  import { generateId } from "../../utils/conversations.js";
9
11
  import { updateAgentToolRelation } from "./subAgentRelations.js";
12
+ import { getActiveBranch } from "../../dolt/schema-sync.js";
10
13
  import { toISODateString } from "../../utils/date.js";
11
14
  import { McpClient } from "../../utils/mcp-client.js";
15
+ import { buildComposioMCPUrl } from "../../utils/third-party-mcp-servers/composio-client.js";
12
16
  import { isThirdPartyMCPServerAuthenticated } from "../../utils/third-party-mcp-servers/third-party-check.js";
13
17
  import "../../utils/index.js";
18
+ import { cascadeDeleteByTool } from "../runtime/cascade-delete.js";
19
+ import { isGithubWorkAppTool } from "../runtime/github-work-app-installations.js";
14
20
  import { getCredentialReference, getUserScopedCredentialReference } from "./credentialReferences.js";
15
21
  import { and, count, desc, eq } from "drizzle-orm";
22
+ import { ErrorCode, McpError } from "@modelcontextprotocol/sdk/types.js";
16
23
 
17
24
  //#region src/data-access/manage/tools.ts
25
+ /**
26
+ * Check if an error is a timeout/connection error.
27
+ * Uses MCP SDK ErrorCode for proper type safety.
28
+ */
29
+ function isTimeoutOrConnectionError(error) {
30
+ if (error instanceof McpError) return error.code === ErrorCode.RequestTimeout || error.code === ErrorCode.ConnectionClosed;
31
+ if (error instanceof Error) {
32
+ const message = error.message.toLowerCase();
33
+ const cause = error.cause;
34
+ if (message.includes("timed out") || message.includes("timeout")) return true;
35
+ if (cause?.code === "ETIMEDOUT" || cause?.code === "ECONNABORTED" || cause?.code === "ECONNRESET") return true;
36
+ }
37
+ return false;
38
+ }
18
39
  const logger = getLogger("tools");
19
40
  /**
20
41
  * Extract expiration date from credential data stored in credential store
@@ -70,24 +91,10 @@ const convertToMCPToolConfig = (tool) => {
70
91
  toolOverrides: tool.config.mcp.toolOverrides
71
92
  };
72
93
  };
73
- const discoverToolsFromServer = async (tool, dbClient, credentialStoreRegistry, userId) => {
94
+ const discoverToolsFromServer = async (tool, credentialReference, credentialStoreRegistry, userId) => {
74
95
  if (tool.config.type !== "mcp") throw new Error(`Cannot discover tools from non-MCP tool: ${tool.id}`);
75
96
  try {
76
97
  let serverConfig;
77
- const credentialReference = tool.credentialReferenceId && tool.credentialScope !== "user" ? await getCredentialReference(dbClient)({
78
- scopes: {
79
- tenantId: tool.tenantId,
80
- projectId: tool.projectId
81
- },
82
- id: tool.credentialReferenceId
83
- }) : userId && tool.credentialScope === "user" ? await getUserScopedCredentialReference(dbClient)({
84
- scopes: {
85
- tenantId: tool.tenantId,
86
- projectId: tool.projectId
87
- },
88
- toolId: tool.id,
89
- userId
90
- }) : void 0;
91
98
  if (credentialReference) {
92
99
  const storeReference = {
93
100
  credentialStoreId: credentialReference.credentialStoreId,
@@ -111,12 +118,12 @@ const discoverToolsFromServer = async (tool, dbClient, credentialStoreRegistry,
111
118
  reconnectionOptions: tool.config.mcp.transport?.reconnectionOptions,
112
119
  sessionId: tool.config.mcp.transport?.sessionId
113
120
  };
114
- if (serverConfig.url?.toString().includes("composio.dev")) {
115
- const urlObj = new URL(serverConfig.url.toString());
116
- if (tool.credentialScope === "user" && userId) urlObj.searchParams.set("user_id", userId);
117
- else urlObj.searchParams.set("user_id", `${tool.tenantId}||${tool.projectId}`);
118
- serverConfig.url = urlObj.toString();
119
- }
121
+ if (serverConfig.url) serverConfig.url = buildComposioMCPUrl(serverConfig.url.toString(), tool.tenantId, tool.projectId, tool.credentialScope === "user" ? "user" : "project", userId);
122
+ if (isGithubWorkAppTool(tool)) serverConfig.headers = {
123
+ ...serverConfig.headers,
124
+ "x-inkeep-tool-id": tool.id,
125
+ Authorization: `Bearer ${env.GITHUB_MCP_API_KEY}`
126
+ };
120
127
  const client = new McpClient({
121
128
  name: tool.name,
122
129
  server: serverConfig
@@ -141,6 +148,27 @@ const discoverToolsFromServer = async (tool, dbClient, credentialStoreRegistry,
141
148
  throw error;
142
149
  }
143
150
  };
151
+ /**
152
+ * Convert DB result to McpTool skeleton WITHOUT MCP discovery.
153
+ * This is a fast path that returns status='unknown' and empty availableTools.
154
+ * Use this for list views where you want instant page load.
155
+ */
156
+ const dbResultToMcpToolSkeleton = (dbResult, relationshipId) => {
157
+ const { headers, capabilities, credentialReferenceId, imageUrl, createdAt, ...rest } = dbResult;
158
+ return {
159
+ ...rest,
160
+ status: "unknown",
161
+ availableTools: [],
162
+ capabilities: capabilities || void 0,
163
+ credentialReferenceId: credentialReferenceId || void 0,
164
+ createdAt: toISODateString(createdAt),
165
+ updatedAt: toISODateString(dbResult.updatedAt),
166
+ lastError: dbResult.lastError || null,
167
+ headers: headers || void 0,
168
+ imageUrl: imageUrl || void 0,
169
+ relationshipId
170
+ };
171
+ };
144
172
  const dbResultToMcpTool = async (dbResult, dbClient, credentialStoreRegistry, relationshipId, userId) => {
145
173
  const { headers, capabilities, credentialReferenceId, imageUrl, createdAt, ...rest } = dbResult;
146
174
  if (dbResult.config.type !== "mcp") return {
@@ -181,18 +209,23 @@ const dbResultToMcpTool = async (dbResult, dbClient, credentialStoreRegistry, re
181
209
  }
182
210
  const mcpServerUrl = dbResult.config.mcp.server.url;
183
211
  try {
184
- availableTools = await discoverToolsFromServer(dbResult, dbClient, credentialStoreRegistry, userId);
212
+ availableTools = await discoverToolsFromServer(dbResult, credentialReference, credentialStoreRegistry, userId);
185
213
  status = "healthy";
186
214
  lastErrorComputed = null;
187
215
  } catch (error) {
188
- const toolNeedsAuth = error instanceof Error && await detectAuthenticationRequired({
189
- serverUrl: mcpServerUrl,
190
- error,
191
- logger
192
- });
193
- status = toolNeedsAuth ? "needs_auth" : "unhealthy";
194
216
  const errorMessage = error instanceof Error ? error.message : "Tool discovery failed";
195
- lastErrorComputed = toolNeedsAuth ? `Authentication required - OAuth login needed. ${errorMessage}` : errorMessage;
217
+ if (isTimeoutOrConnectionError(error)) {
218
+ status = "unavailable";
219
+ lastErrorComputed = `Connection failed - the MCP server may be slow or temporarily unreachable.${error instanceof McpError ? ` (MCP error ${error.code})` : ""} ${errorMessage}`;
220
+ } else {
221
+ const toolNeedsAuth = await detectAuthenticationRequired({
222
+ serverUrl: mcpServerUrl,
223
+ error: error instanceof Error ? error : void 0,
224
+ logger
225
+ });
226
+ status = toolNeedsAuth ? "needs_auth" : "unhealthy";
227
+ lastErrorComputed = toolNeedsAuth ? `Authentication required - OAuth login needed. ${errorMessage}` : errorMessage;
228
+ }
196
229
  }
197
230
  if (dbResult.config.mcp.server.url.includes("composio.dev")) {
198
231
  const credentialScope = dbResult.credentialScope || "project";
@@ -284,7 +317,16 @@ const updateTool = (db) => async (params) => {
284
317
  };
285
318
  const deleteTool = (db) => async (params) => {
286
319
  const [deleted] = await db.delete(tools).where(and(eq(tools.tenantId, params.scopes.tenantId), eq(tools.projectId, params.scopes.projectId), eq(tools.id, params.toolId))).returning();
287
- return !!deleted;
320
+ if (!deleted) return false;
321
+ if (deleted.isWorkApp && deleted.config.mcp.server.url.includes("/github/mcp")) try {
322
+ if (await getActiveBranch(db)() === `${params.scopes.tenantId}_${params.scopes.projectId}_main`) await cascadeDeleteByTool(createAgentsRunDatabaseClient())({ toolId: params.toolId });
323
+ } catch (error) {
324
+ logger.debug({
325
+ error,
326
+ toolId: params.toolId
327
+ }, "Skipping cascade delete - active_branch() not available");
328
+ }
329
+ return true;
288
330
  };
289
331
  const addToolToAgent = (db) => async (params) => {
290
332
  const id = generateId();
@@ -351,4 +393,4 @@ const upsertTool = (db) => async (params) => {
351
393
  };
352
394
 
353
395
  //#endregion
354
- export { addToolToAgent, createTool, dbResultToMcpTool, deleteTool, getMcpToolById, getToolById, listTools, removeToolFromAgent, updateTool, upsertSubAgentToolRelation, upsertTool };
396
+ export { addToolToAgent, createTool, dbResultToMcpTool, dbResultToMcpToolSkeleton, deleteTool, getMcpToolById, getToolById, listTools, removeToolFromAgent, updateTool, upsertSubAgentToolRelation, upsertTool };
@@ -35,7 +35,33 @@ declare const listTriggersPaginated: (db: AgentsManageDatabaseClient) => (params
35
35
  } | null;
36
36
  messageTemplate: string | null;
37
37
  authentication: unknown;
38
- signingSecret: string | null;
38
+ signingSecretCredentialReferenceId: string | null;
39
+ signatureVerification: {
40
+ algorithm: "sha256" | "sha512" | "sha384" | "sha1" | "md5";
41
+ encoding: "hex" | "base64";
42
+ signature: {
43
+ source: "query" | "body" | "header";
44
+ key: string;
45
+ prefix?: string | undefined;
46
+ regex?: string | undefined;
47
+ };
48
+ signedComponents: {
49
+ source: "literal" | "body" | "header";
50
+ required: boolean;
51
+ key?: string | undefined;
52
+ value?: string | undefined;
53
+ regex?: string | undefined;
54
+ }[];
55
+ componentJoin: {
56
+ strategy: "concatenate";
57
+ separator: string;
58
+ };
59
+ validation?: {
60
+ headerCaseSensitive: boolean;
61
+ allowEmptyBody: boolean;
62
+ normalizeUnicode: boolean;
63
+ } | undefined;
64
+ } | null;
39
65
  name: string;
40
66
  description: string | null;
41
67
  agentId: string;
@@ -7,49 +7,49 @@ declare const getApiKeyById: (db: AgentsRunDatabaseClient) => (params: {
7
7
  scopes: ProjectScopeConfig;
8
8
  id: string;
9
9
  }) => Promise<{
10
- tenantId: string;
11
- projectId: string;
12
10
  id: string;
13
11
  name: string | null;
12
+ createdAt: string;
13
+ updatedAt: string;
14
+ expiresAt: string | null;
14
15
  agentId: string;
16
+ projectId: string;
17
+ tenantId: string;
15
18
  publicId: string;
16
19
  keyHash: string;
17
20
  keyPrefix: string;
18
21
  lastUsedAt: string | null;
19
- expiresAt: string | null;
20
- createdAt: string;
21
- updatedAt: string;
22
22
  } | undefined>;
23
23
  declare const getApiKeyByPublicId: (db: AgentsRunDatabaseClient) => (publicId: string) => Promise<{
24
- tenantId: string;
25
- projectId: string;
26
24
  id: string;
27
25
  name: string | null;
26
+ createdAt: string;
27
+ updatedAt: string;
28
+ expiresAt: string | null;
28
29
  agentId: string;
30
+ projectId: string;
31
+ tenantId: string;
29
32
  publicId: string;
30
33
  keyHash: string;
31
34
  keyPrefix: string;
32
35
  lastUsedAt: string | null;
33
- expiresAt: string | null;
34
- createdAt: string;
35
- updatedAt: string;
36
36
  } | undefined>;
37
37
  declare const listApiKeys: (db: AgentsRunDatabaseClient) => (params: {
38
38
  scopes: ProjectScopeConfig;
39
39
  agentId?: string;
40
40
  }) => Promise<{
41
- tenantId: string;
42
- projectId: string;
43
41
  id: string;
44
42
  name: string | null;
43
+ createdAt: string;
44
+ updatedAt: string;
45
+ expiresAt: string | null;
45
46
  agentId: string;
47
+ projectId: string;
48
+ tenantId: string;
46
49
  publicId: string;
47
50
  keyHash: string;
48
51
  keyPrefix: string;
49
52
  lastUsedAt: string | null;
50
- expiresAt: string | null;
51
- createdAt: string;
52
- updatedAt: string;
53
53
  }[]>;
54
54
  declare const listApiKeysPaginated: (db: AgentsRunDatabaseClient) => (params: {
55
55
  scopes: ProjectScopeConfig;
@@ -65,18 +65,18 @@ declare const listApiKeysPaginated: (db: AgentsRunDatabaseClient) => (params: {
65
65
  };
66
66
  }>;
67
67
  declare const createApiKey: (db: AgentsRunDatabaseClient) => (params: ApiKeyInsert) => Promise<{
68
- tenantId: string;
69
- projectId: string;
70
68
  id: string;
71
69
  name: string | null;
70
+ createdAt: string;
71
+ updatedAt: string;
72
+ expiresAt: string | null;
72
73
  agentId: string;
74
+ projectId: string;
75
+ tenantId: string;
73
76
  publicId: string;
74
77
  keyHash: string;
75
78
  keyPrefix: string;
76
79
  lastUsedAt: string | null;
77
- expiresAt: string | null;
78
- createdAt: string;
79
- updatedAt: string;
80
80
  }>;
81
81
  declare const updateApiKey: (db: AgentsRunDatabaseClient) => (params: {
82
82
  scopes: ProjectScopeConfig;
@@ -73,5 +73,52 @@ declare const cascadeDeleteByContextConfig: (db: AgentsRunDatabaseClient) => (pa
73
73
  }) => Promise<{
74
74
  contextCacheDeleted: number;
75
75
  }>;
76
+ /**
77
+ * Result of a tool cascade delete operation
78
+ */
79
+ type ToolCascadeDeleteResult = {
80
+ mcpToolRepositoryAccessDeleted: number;
81
+ mcpToolAccessModeDeleted: boolean;
82
+ };
83
+ /**
84
+ * Delete all runtime entities for a specific MCP tool.
85
+ * Called when an MCP tool is deleted from the manage database.
86
+ *
87
+ * Cleans up:
88
+ * - workAppGitHubMcpToolRepositoryAccess entries
89
+ * - workAppGitHubMcpToolAccessMode entry
90
+ *
91
+ * @param db - Runtime database client
92
+ * @returns Function that performs the cascade delete
93
+ */
94
+ declare const cascadeDeleteByTool: (db: AgentsRunDatabaseClient) => (params: {
95
+ toolId: string;
96
+ }) => Promise<ToolCascadeDeleteResult>;
97
+ /**
98
+ * Result of a project cascade delete operation (GitHub access only)
99
+ */
100
+ type ProjectGitHubAccessCascadeDeleteResult = {
101
+ projectRepositoryAccessDeleted: number;
102
+ projectAccessModeDeleted: boolean;
103
+ mcpToolRepositoryAccessDeleted: number;
104
+ mcpToolAccessModesDeleted: number;
105
+ };
106
+ /**
107
+ * Delete all GitHub access runtime entities for a specific project.
108
+ * Called when a project is deleted from the manage database.
109
+ *
110
+ * Cleans up:
111
+ * - workAppGitHubProjectRepositoryAccess entries
112
+ * - workAppGitHubProjectAccessMode entry
113
+ * - workAppGitHubMcpToolRepositoryAccess entries (for tools in this project)
114
+ * - workAppGitHubMcpToolAccessMode entries (for tools in this project)
115
+ *
116
+ * @param db - Runtime database client
117
+ * @returns Function that performs the cascade delete
118
+ */
119
+ declare const cascadeDeleteGitHubAccessByProject: (db: AgentsRunDatabaseClient) => (params: {
120
+ tenantId: string;
121
+ projectId: string;
122
+ }) => Promise<ProjectGitHubAccessCascadeDeleteResult>;
76
123
  //#endregion
77
- export { CascadeDeleteResult, cascadeDeleteByAgent, cascadeDeleteByBranch, cascadeDeleteByContextConfig, cascadeDeleteByProject, cascadeDeleteBySubAgent };
124
+ export { CascadeDeleteResult, ProjectGitHubAccessCascadeDeleteResult, ToolCascadeDeleteResult, cascadeDeleteByAgent, cascadeDeleteByBranch, cascadeDeleteByContextConfig, cascadeDeleteByProject, cascadeDeleteBySubAgent, cascadeDeleteByTool, cascadeDeleteGitHubAccessByProject };
@@ -1,4 +1,4 @@
1
- import { apiKeys, contextCache, conversations, tasks } from "../../db/runtime/runtime-schema.js";
1
+ import { apiKeys, contextCache, conversations, tasks, workAppGitHubMcpToolAccessMode, workAppGitHubMcpToolRepositoryAccess, workAppGitHubProjectAccessMode, workAppGitHubProjectRepositoryAccess } from "../../db/runtime/runtime-schema.js";
2
2
  import { and, eq, inArray, sql } from "drizzle-orm";
3
3
 
4
4
  //#region src/data-access/runtime/cascade-delete.ts
@@ -35,6 +35,10 @@ const cascadeDeleteByProject = (db) => async (params) => {
35
35
  const conversationsResult = await db.delete(conversations).where(and(eq(conversations.tenantId, scopes.tenantId), eq(conversations.projectId, scopes.projectId), sql`${conversations.ref}->>'name' = ${fullBranchName}`)).returning();
36
36
  const tasksResult = await db.delete(tasks).where(and(eq(tasks.tenantId, scopes.tenantId), eq(tasks.projectId, scopes.projectId), sql`${tasks.ref}->>'name' = ${fullBranchName}`)).returning();
37
37
  const apiKeysResult = await db.delete(apiKeys).where(and(eq(apiKeys.tenantId, scopes.tenantId), eq(apiKeys.projectId, scopes.projectId))).returning();
38
+ await cascadeDeleteGitHubAccessByProject(db)({
39
+ tenantId: scopes.tenantId,
40
+ projectId: scopes.projectId
41
+ });
38
42
  return {
39
43
  conversationsDeleted: conversationsResult.length,
40
44
  tasksDeleted: tasksResult.length,
@@ -106,6 +110,52 @@ const cascadeDeleteByContextConfig = (db) => async (params) => {
106
110
  const { scopes, contextConfigId, fullBranchName } = params;
107
111
  return { contextCacheDeleted: (await db.delete(contextCache).where(and(eq(contextCache.tenantId, scopes.tenantId), eq(contextCache.projectId, scopes.projectId), eq(contextCache.contextConfigId, contextConfigId), sql`${contextCache.ref}->>'name' = ${fullBranchName}`)).returning()).length };
108
112
  };
113
+ /**
114
+ * Delete all runtime entities for a specific MCP tool.
115
+ * Called when an MCP tool is deleted from the manage database.
116
+ *
117
+ * Cleans up:
118
+ * - workAppGitHubMcpToolRepositoryAccess entries
119
+ * - workAppGitHubMcpToolAccessMode entry
120
+ *
121
+ * @param db - Runtime database client
122
+ * @returns Function that performs the cascade delete
123
+ */
124
+ const cascadeDeleteByTool = (db) => async (params) => {
125
+ const { toolId } = params;
126
+ const repositoryAccessResult = await db.delete(workAppGitHubMcpToolRepositoryAccess).where(eq(workAppGitHubMcpToolRepositoryAccess.toolId, toolId)).returning();
127
+ const accessModeResult = await db.delete(workAppGitHubMcpToolAccessMode).where(eq(workAppGitHubMcpToolAccessMode.toolId, toolId)).returning();
128
+ return {
129
+ mcpToolRepositoryAccessDeleted: repositoryAccessResult.length,
130
+ mcpToolAccessModeDeleted: accessModeResult.length > 0
131
+ };
132
+ };
133
+ /**
134
+ * Delete all GitHub access runtime entities for a specific project.
135
+ * Called when a project is deleted from the manage database.
136
+ *
137
+ * Cleans up:
138
+ * - workAppGitHubProjectRepositoryAccess entries
139
+ * - workAppGitHubProjectAccessMode entry
140
+ * - workAppGitHubMcpToolRepositoryAccess entries (for tools in this project)
141
+ * - workAppGitHubMcpToolAccessMode entries (for tools in this project)
142
+ *
143
+ * @param db - Runtime database client
144
+ * @returns Function that performs the cascade delete
145
+ */
146
+ const cascadeDeleteGitHubAccessByProject = (db) => async (params) => {
147
+ const { tenantId, projectId } = params;
148
+ const projectRepoAccessResult = await db.delete(workAppGitHubProjectRepositoryAccess).where(and(eq(workAppGitHubProjectRepositoryAccess.tenantId, tenantId), eq(workAppGitHubProjectRepositoryAccess.projectId, projectId))).returning();
149
+ const projectAccessModeResult = await db.delete(workAppGitHubProjectAccessMode).where(and(eq(workAppGitHubProjectAccessMode.tenantId, tenantId), eq(workAppGitHubProjectAccessMode.projectId, projectId))).returning();
150
+ const mcpToolRepoAccessResult = await db.delete(workAppGitHubMcpToolRepositoryAccess).where(and(eq(workAppGitHubMcpToolRepositoryAccess.tenantId, tenantId), eq(workAppGitHubMcpToolRepositoryAccess.projectId, projectId))).returning();
151
+ const mcpToolAccessModeResult = await db.delete(workAppGitHubMcpToolAccessMode).where(and(eq(workAppGitHubMcpToolAccessMode.tenantId, tenantId), eq(workAppGitHubMcpToolAccessMode.projectId, projectId))).returning();
152
+ return {
153
+ projectRepositoryAccessDeleted: projectRepoAccessResult.length,
154
+ projectAccessModeDeleted: projectAccessModeResult.length > 0,
155
+ mcpToolRepositoryAccessDeleted: mcpToolRepoAccessResult.length,
156
+ mcpToolAccessModesDeleted: mcpToolAccessModeResult.length
157
+ };
158
+ };
109
159
 
110
160
  //#endregion
111
- export { cascadeDeleteByAgent, cascadeDeleteByBranch, cascadeDeleteByContextConfig, cascadeDeleteByProject, cascadeDeleteBySubAgent };
161
+ export { cascadeDeleteByAgent, cascadeDeleteByBranch, cascadeDeleteByContextConfig, cascadeDeleteByProject, cascadeDeleteBySubAgent, cascadeDeleteByTool, cascadeDeleteGitHubAccessByProject };