@sentry/junior 0.181.1 → 0.183.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/dist/{agent-hooks-KO56HJ74.js → agent-hooks-SNRBZYAU.js} +11 -11
- package/dist/api/code/overview.d.ts +35 -0
- package/dist/api/code/routes.d.ts +4 -0
- package/dist/api/schema/code.d.ts +75 -0
- package/dist/api/schema.d.ts +2 -0
- package/dist/api/schema.js +9 -1
- package/dist/api.js +347 -149
- package/dist/app-adapter.d.ts +85 -0
- package/dist/app.d.ts +6 -1
- package/dist/app.js +380 -501
- package/dist/{catalog-runtime-CJTFLCK3.js → catalog-runtime-3I3JOIIH.js} +4 -4
- package/dist/chat/agent-invocations/store.d.ts +4 -2
- package/dist/chat/agent-invocations/work.d.ts +1 -3
- package/dist/chat/api-turns/adapter-conversations.d.ts +15 -0
- package/dist/chat/api-turns/stop.d.ts +12 -0
- package/dist/chat/api-turns/work.d.ts +9 -1
- package/dist/chat/app/conversation-work.d.ts +1 -1
- package/dist/chat/app/factory.d.ts +3 -3
- package/dist/chat/app/services.d.ts +3 -3
- package/dist/chat/code/publisher.d.ts +3 -0
- package/dist/chat/code/store.d.ts +9 -0
- package/dist/chat/event-tasks/store.d.ts +10 -0
- package/dist/chat/event-tasks/tool-support.d.ts +7 -1
- package/dist/chat/event-tasks/types.d.ts +1 -0
- package/dist/chat/experimental.d.ts +1 -1
- package/dist/chat/ingress/slack-webhook.d.ts +1 -1
- package/dist/chat/plugins/agent-hooks.d.ts +5 -0
- package/dist/chat/{runtime/slack-runtime.d.ts → providers/slack/runtime.d.ts} +2 -2
- package/dist/chat/{runtime/reply-executor.d.ts → providers/slack/turn.d.ts} +10 -9
- package/dist/chat/resource-events/catalog.d.ts +11 -1
- package/dist/chat/resource-events/store.d.ts +17 -1
- package/dist/chat/runtime/turn-execution.d.ts +30 -0
- package/dist/chat/services/subscribed-decision.d.ts +2 -1
- package/dist/chat/slack/dispatch-turn.d.ts +12 -14
- package/dist/chat/task-execution/slack-work.d.ts +1 -1
- package/dist/chat/tools/create-event-task.d.ts +3 -0
- package/dist/chat/tools/delete-event-task.d.ts +2 -0
- package/dist/chat/tools/list-event-tasks.d.ts +2 -0
- package/dist/chat/tools/list-resource-event-subscriptions.d.ts +2 -0
- package/dist/chat/tools/search-resource-event-types.d.ts +10 -0
- package/dist/chat/tools/update-event-task.d.ts +3 -0
- package/dist/chat/tools/watch-resource-events.d.ts +3 -0
- package/dist/{chunk-DTRCZOHE.js → chunk-24OJZ5OU.js} +6 -6
- package/dist/{chunk-Z2UG4FBT.js → chunk-2ADFGSUS.js} +1 -1
- package/dist/{chunk-RULGB5NX.js → chunk-2EPYYVJC.js} +9 -9
- package/dist/{chunk-VRS6WDK5.js → chunk-2LYHWMR4.js} +1 -1
- package/dist/{chunk-XQ56HNH5.js → chunk-35PM4YY5.js} +6 -6
- package/dist/{chunk-6TB7JN63.js → chunk-37IQ6DGU.js} +3 -3
- package/dist/{chunk-MR36BRPE.js → chunk-3HJ4F4L7.js} +4 -4
- package/dist/{chunk-4WYHL4EH.js → chunk-3L7CWDQQ.js} +1 -1
- package/dist/{chunk-CJRUBOJI.js → chunk-4WGFWHWP.js} +1 -1
- package/dist/{chunk-VHSBLFNT.js → chunk-56XONJPF.js} +1 -1
- package/dist/{chunk-ULM7P4EQ.js → chunk-6UXDTPEN.js} +233 -173
- package/dist/{chunk-WDNA4LML.js → chunk-AHMWPFIW.js} +188 -11
- package/dist/{chunk-YCW6RZGX.js → chunk-AX3UDIMA.js} +3 -3
- package/dist/{chunk-HG6HNOTQ.js → chunk-AYW7J6K4.js} +130 -200
- package/dist/{chunk-DXK3VTVP.js → chunk-E3OBGRHN.js} +1 -1
- package/dist/{chunk-7UF37LNL.js → chunk-EENQGEIP.js} +1 -1
- package/dist/{chunk-HRTW7FFX.js → chunk-FJMTMGBC.js} +1 -1
- package/dist/{chunk-H6MPFFBE.js → chunk-G2B2XZQW.js} +1 -1
- package/dist/{chunk-4GOZBB22.js → chunk-HUK5XIZL.js} +63 -7
- package/dist/{chunk-DINF4LMR.js → chunk-IO6KFXYE.js} +160 -97
- package/dist/{chunk-KH2SL2HT.js → chunk-KTXOGLNE.js} +2 -2
- package/dist/{chunk-S63LNPIV.js → chunk-LMNMMESF.js} +2 -2
- package/dist/{chunk-2CZ63QCL.js → chunk-LZBPGX5A.js} +1 -1
- package/dist/{chunk-PJ7EGFME.js → chunk-PLZT45VC.js} +5 -5
- package/dist/{chunk-ZQQWJMHE.js → chunk-QI5JW5AG.js} +6 -6
- package/dist/{chunk-IWRPJ3J5.js → chunk-QZV76CM4.js} +58 -32
- package/dist/{chunk-YFJDRORU.js → chunk-R767Y7QV.js} +202 -90
- package/dist/{chunk-4OSVTPYQ.js → chunk-SQHFVIMZ.js} +1 -1
- package/dist/{chunk-J4ID4ZI6.js → chunk-T5MTGX2E.js} +19 -19
- package/dist/{chunk-NRF23QZ4.js → chunk-V64JCZUV.js} +3 -3
- package/dist/{chunk-GITIZ6TZ.js → chunk-VOV3SCM3.js} +1 -1
- package/dist/{chunk-S5X2VQOD.js → chunk-W46NIB5H.js} +3 -2
- package/dist/{chunk-XL3C4NAR.js → chunk-W5JMPEBO.js} +9 -9
- package/dist/{chunk-HPFHC7YR.js → chunk-WOKJRLM2.js} +5 -5
- package/dist/chunk-WVIA7V3M.js +975 -0
- package/dist/{chunk-QA6RE6IB.js → chunk-X52ESOBP.js} +3 -3
- package/dist/cli/chat.js +35 -37
- package/dist/cli/check.js +5 -5
- package/dist/cli/plugins.js +12 -12
- package/dist/cli/snapshot-create.js +9 -9
- package/dist/cli/upgrade.js +6 -6
- package/dist/db/schema/code.d.ts +367 -0
- package/dist/db/schema.d.ts +367 -1
- package/dist/{db-4PXTD3OH.js → db-K2VMNLHQ.js} +6 -6
- package/dist/{experimental-SIJSRDJD.js → experimental-P5FZM4CU.js} +1 -1
- package/dist/instrumentation.js +3 -3
- package/dist/nitro.js +6 -6
- package/dist/{oauth-callback-server-TQWNEVR6.js → oauth-callback-server-DZZMTKSS.js} +26 -26
- package/dist/{runner-G5HLQA43.js → runner-IIAKWDXI.js} +18 -18
- package/dist/{skills-BNNNRYNT.js → skills-EXIQ7BP5.js} +5 -5
- package/dist/spawn-ZR6OOEAN.js +37 -0
- package/dist/task-runner-C52HYCVD.js +32 -0
- package/dist/{validation-IJSBB6JR.js → validation-XUGIWBJF.js} +5 -5
- package/dist/version.js +1 -1
- package/dist/{work-5FQI4P2A.js → work-G4RLJ634.js} +18 -18
- package/dist/worker-R2JEHK67.js +22 -0
- package/migrations/0036_complex_rage.sql +32 -0
- package/migrations/meta/0036_snapshot.json +3186 -0
- package/migrations/meta/_journal.json +8 -1
- package/package.json +6 -5
- package/dist/api/acp/route.d.ts +0 -13
- package/dist/chunk-CZYNWPWD.js +0 -930
- package/dist/spawn-U2RKOFP2.js +0 -37
- package/dist/task-runner-CDZJBEXP.js +0 -32
- package/dist/worker-KJ362GVB.js +0 -22
package/dist/app.js
CHANGED
|
@@ -1,15 +1,15 @@
|
|
|
1
1
|
import {
|
|
2
2
|
processConversationWork
|
|
3
|
-
} from "./chunk-
|
|
3
|
+
} from "./chunk-3HJ4F4L7.js";
|
|
4
4
|
import {
|
|
5
5
|
bindSpawnAgent
|
|
6
|
-
} from "./chunk-
|
|
6
|
+
} from "./chunk-VOV3SCM3.js";
|
|
7
7
|
import {
|
|
8
8
|
createAgentInvocationWorker,
|
|
9
9
|
enqueueAgentInvocation,
|
|
10
10
|
listPendingAgentInvocationMailboxAppends,
|
|
11
11
|
routeAgentInvocationWork
|
|
12
|
-
} from "./chunk-
|
|
12
|
+
} from "./chunk-IO6KFXYE.js";
|
|
13
13
|
import {
|
|
14
14
|
GET as GET2,
|
|
15
15
|
GET2 as GET3,
|
|
@@ -36,25 +36,25 @@ import {
|
|
|
36
36
|
startSlackProcessingReaction,
|
|
37
37
|
stripLeadingBotMention,
|
|
38
38
|
wakePausedTurn
|
|
39
|
-
} from "./chunk-
|
|
39
|
+
} from "./chunk-T5MTGX2E.js";
|
|
40
40
|
import "./chunk-FA6POGLH.js";
|
|
41
41
|
import {
|
|
42
42
|
GET,
|
|
43
43
|
apiTurnIdForMessage,
|
|
44
44
|
appendAndEnqueueApiConversationMessage,
|
|
45
|
-
authenticatePersonalToken,
|
|
46
45
|
conversationVisibilityFromSlackChannelType,
|
|
47
46
|
createApiTurnCancellation,
|
|
48
47
|
createApiTurnWorker,
|
|
49
48
|
createVercelAttachmentStorage,
|
|
49
|
+
getAuthPausedApiTurnId,
|
|
50
50
|
readConversationAccessFromSql,
|
|
51
51
|
recordApiConversationActivity,
|
|
52
52
|
resolveSlackChannelTypeFromMessage,
|
|
53
53
|
resolveSlackConversationContext,
|
|
54
54
|
routeApiTurnWork,
|
|
55
55
|
webActorFromEmail
|
|
56
|
-
} from "./chunk-
|
|
57
|
-
import "./chunk-
|
|
56
|
+
} from "./chunk-AYW7J6K4.js";
|
|
57
|
+
import "./chunk-4WGFWHWP.js";
|
|
58
58
|
import {
|
|
59
59
|
buildDeliveredTurnStatePatch,
|
|
60
60
|
completeAuthPauseTurn,
|
|
@@ -65,7 +65,7 @@ import {
|
|
|
65
65
|
getTurnUserSlackMessageTs,
|
|
66
66
|
persistAuthPauseTurnState,
|
|
67
67
|
requireTurnFailureEventId
|
|
68
|
-
} from "./chunk-
|
|
68
|
+
} from "./chunk-WOKJRLM2.js";
|
|
69
69
|
import {
|
|
70
70
|
claimDispatchMailboxAppend,
|
|
71
71
|
confirmDispatchMailboxAppend,
|
|
@@ -85,7 +85,7 @@ import {
|
|
|
85
85
|
recordTaskExecution,
|
|
86
86
|
resolveTurnSessionRouting,
|
|
87
87
|
scheduleSessionCompletedPluginTasks
|
|
88
|
-
} from "./chunk-
|
|
88
|
+
} from "./chunk-W5JMPEBO.js";
|
|
89
89
|
import {
|
|
90
90
|
ConversationTurnLifecycleService
|
|
91
91
|
} from "./chunk-M3QYTBQ6.js";
|
|
@@ -97,17 +97,17 @@ import {
|
|
|
97
97
|
persistThreadRuntimeState,
|
|
98
98
|
persistThreadState,
|
|
99
99
|
persistThreadStateById
|
|
100
|
-
} from "./chunk-
|
|
100
|
+
} from "./chunk-PLZT45VC.js";
|
|
101
101
|
import "./chunk-UTL3MHPC.js";
|
|
102
102
|
import {
|
|
103
103
|
createVercelPluginTaskCallback,
|
|
104
104
|
queueCallback,
|
|
105
105
|
registerVercelPluginTaskDevConsumer
|
|
106
|
-
} from "./chunk-
|
|
106
|
+
} from "./chunk-V64JCZUV.js";
|
|
107
107
|
import {
|
|
108
108
|
validatePluginEgressCredentialHooks,
|
|
109
109
|
validatePluginRegistrations
|
|
110
|
-
} from "./chunk-
|
|
110
|
+
} from "./chunk-3L7CWDQQ.js";
|
|
111
111
|
import {
|
|
112
112
|
defineJuniorPlugins,
|
|
113
113
|
pluginCatalogConfigFromEnv,
|
|
@@ -155,11 +155,11 @@ import {
|
|
|
155
155
|
unpublishedArtifactHeaders,
|
|
156
156
|
verifySlackSignature,
|
|
157
157
|
withNormalizedThreadId
|
|
158
|
-
} from "./chunk-
|
|
158
|
+
} from "./chunk-QZV76CM4.js";
|
|
159
159
|
import {
|
|
160
160
|
AuthorizationFlowDisabledError,
|
|
161
161
|
PluginCredentialFailureError
|
|
162
|
-
} from "./chunk-
|
|
162
|
+
} from "./chunk-35PM4YY5.js";
|
|
163
163
|
import "./chunk-6Y5B5PEX.js";
|
|
164
164
|
import "./chunk-DIB4GX3G.js";
|
|
165
165
|
import {
|
|
@@ -168,7 +168,7 @@ import {
|
|
|
168
168
|
deleteMcpAuthSessionsForUserProvider,
|
|
169
169
|
deleteMcpServerSessionId,
|
|
170
170
|
deleteMcpStoredOAuthCredentials
|
|
171
|
-
} from "./chunk-
|
|
171
|
+
} from "./chunk-2EPYYVJC.js";
|
|
172
172
|
import {
|
|
173
173
|
RetryableDeliveryError
|
|
174
174
|
} from "./chunk-RF6J3DIO.js";
|
|
@@ -176,14 +176,15 @@ import {
|
|
|
176
176
|
formatProviderLabel,
|
|
177
177
|
postSlackMessage,
|
|
178
178
|
startOAuthFlow
|
|
179
|
-
} from "./chunk-
|
|
179
|
+
} from "./chunk-QI5JW5AG.js";
|
|
180
180
|
import {
|
|
181
181
|
getExperimentalFeatures,
|
|
182
182
|
isExperimentalFeatureEnabled,
|
|
183
183
|
setExperimentalFeatures
|
|
184
|
-
} from "./chunk-
|
|
184
|
+
} from "./chunk-2LYHWMR4.js";
|
|
185
185
|
import {
|
|
186
186
|
collectAttachmentGarbage,
|
|
187
|
+
collectEventTaskMatchKeys,
|
|
187
188
|
findMatchingEventTasks,
|
|
188
189
|
getResourceEventCatalog,
|
|
189
190
|
listScheduledTasks,
|
|
@@ -196,21 +197,25 @@ import {
|
|
|
196
197
|
scheduledRunId,
|
|
197
198
|
scheduledRunSchema,
|
|
198
199
|
withScheduledTaskLock
|
|
199
|
-
} from "./chunk-
|
|
200
|
+
} from "./chunk-R767Y7QV.js";
|
|
200
201
|
import {
|
|
201
202
|
parseSlackThreadId
|
|
202
|
-
} from "./chunk-
|
|
203
|
+
} from "./chunk-SQHFVIMZ.js";
|
|
203
204
|
import {
|
|
204
205
|
CONVERSATION_WORK_STALE_ENQUEUE_MS,
|
|
205
206
|
appendAndEnqueueInboundMessage,
|
|
206
207
|
clearExpiredConversationLease,
|
|
207
208
|
ensureConversationWake,
|
|
209
|
+
getConversation,
|
|
208
210
|
getConversationWorkState,
|
|
209
211
|
hasRunnableConversationWork,
|
|
212
|
+
hasRunnableConversationWork2,
|
|
210
213
|
isInvalidConversationRecordError,
|
|
211
214
|
listActiveConversationIds,
|
|
212
|
-
removeActiveConversation
|
|
213
|
-
|
|
215
|
+
removeActiveConversation,
|
|
216
|
+
requestConversationWork,
|
|
217
|
+
stopConversationWork
|
|
218
|
+
} from "./chunk-HUK5XIZL.js";
|
|
214
219
|
import {
|
|
215
220
|
ConversationTurnBoundaryError,
|
|
216
221
|
CooperativeTurnYieldError,
|
|
@@ -228,7 +233,7 @@ import {
|
|
|
228
233
|
markTurnCompleted,
|
|
229
234
|
markTurnFailed,
|
|
230
235
|
startActiveTurn
|
|
231
|
-
} from "./chunk-
|
|
236
|
+
} from "./chunk-56XONJPF.js";
|
|
232
237
|
import {
|
|
233
238
|
abandonTurnRecord,
|
|
234
239
|
appendThreadContextMessages,
|
|
@@ -264,11 +269,11 @@ import {
|
|
|
264
269
|
trimTrailingAssistantMessages,
|
|
265
270
|
turnHasReply,
|
|
266
271
|
upsertConversationMessage
|
|
267
|
-
} from "./chunk-
|
|
272
|
+
} from "./chunk-24OJZ5OU.js";
|
|
268
273
|
import {
|
|
269
274
|
getSandboxResourceConfig,
|
|
270
275
|
setSandboxResourceConfig
|
|
271
|
-
} from "./chunk-
|
|
276
|
+
} from "./chunk-37IQ6DGU.js";
|
|
272
277
|
import "./chunk-PDO5BLNM.js";
|
|
273
278
|
import "./chunk-UIE3R5XU.js";
|
|
274
279
|
import {
|
|
@@ -287,13 +292,14 @@ import {
|
|
|
287
292
|
import "./chunk-7H2VZTWN.js";
|
|
288
293
|
import {
|
|
289
294
|
getTurnRequestDeadline
|
|
290
|
-
} from "./chunk-
|
|
295
|
+
} from "./chunk-FJMTMGBC.js";
|
|
291
296
|
import {
|
|
292
297
|
SlackActionError,
|
|
293
298
|
bindEventTaskCredentialSubject,
|
|
294
299
|
bindScheduledTaskCredentialSubject,
|
|
295
300
|
bindSlackDirectCredentialSubject,
|
|
296
301
|
cancelSubscriptions,
|
|
302
|
+
collectResourceEventMatchKeys,
|
|
297
303
|
createPluginLogger,
|
|
298
304
|
createPluginState,
|
|
299
305
|
createResourceEventTeamIdResolver,
|
|
@@ -305,7 +311,6 @@ import {
|
|
|
305
311
|
getWorkspaceTeamId,
|
|
306
312
|
isDmChannel,
|
|
307
313
|
normalizeSlackConversationId,
|
|
308
|
-
resolveViewerUser,
|
|
309
314
|
runWithWorkspaceTeamId,
|
|
310
315
|
setDashboardConversationLinkOptions,
|
|
311
316
|
setPlugins,
|
|
@@ -313,7 +318,7 @@ import {
|
|
|
313
318
|
verifyEventTaskCredentialSubject,
|
|
314
319
|
verifyScheduledTaskCredentialSubject,
|
|
315
320
|
verifySlackDirectCredentialSubject
|
|
316
|
-
} from "./chunk-
|
|
321
|
+
} from "./chunk-AHMWPFIW.js";
|
|
317
322
|
import "./chunk-3Y47VMHV.js";
|
|
318
323
|
import {
|
|
319
324
|
contextProvenance,
|
|
@@ -326,7 +331,7 @@ import {
|
|
|
326
331
|
requireSlackDestination,
|
|
327
332
|
withConversationEventLock,
|
|
328
333
|
withConversationMutationLock
|
|
329
|
-
} from "./chunk-
|
|
334
|
+
} from "./chunk-AX3UDIMA.js";
|
|
330
335
|
import {
|
|
331
336
|
juniorAgentBindings,
|
|
332
337
|
juniorAgentInvocations,
|
|
@@ -334,15 +339,13 @@ import {
|
|
|
334
339
|
juniorConversations,
|
|
335
340
|
juniorSchedulerRuns,
|
|
336
341
|
juniorSchedulerTasks
|
|
337
|
-
} from "./chunk-
|
|
338
|
-
import
|
|
339
|
-
sleep
|
|
340
|
-
} from "./chunk-QA6RE6IB.js";
|
|
342
|
+
} from "./chunk-6UXDTPEN.js";
|
|
343
|
+
import "./chunk-X52ESOBP.js";
|
|
341
344
|
import {
|
|
342
345
|
acquireActiveLock,
|
|
343
346
|
getStateAdapter,
|
|
344
347
|
withActiveLock
|
|
345
|
-
} from "./chunk-
|
|
348
|
+
} from "./chunk-G2B2XZQW.js";
|
|
346
349
|
import {
|
|
347
350
|
juniorDestinations
|
|
348
351
|
} from "./chunk-VFUK3X5B.js";
|
|
@@ -363,13 +366,13 @@ import {
|
|
|
363
366
|
modelIdForProfile,
|
|
364
367
|
setProfiles,
|
|
365
368
|
setSlackReactionConfig
|
|
366
|
-
} from "./chunk-
|
|
367
|
-
import "./chunk-
|
|
368
|
-
import "./chunk-
|
|
369
|
+
} from "./chunk-LMNMMESF.js";
|
|
370
|
+
import "./chunk-2ADFGSUS.js";
|
|
371
|
+
import "./chunk-KTXOGLNE.js";
|
|
369
372
|
import {
|
|
370
373
|
pluginCatalogRuntime
|
|
371
|
-
} from "./chunk-
|
|
372
|
-
import "./chunk-
|
|
374
|
+
} from "./chunk-E3OBGRHN.js";
|
|
375
|
+
import "./chunk-EENQGEIP.js";
|
|
373
376
|
import {
|
|
374
377
|
credentialContextForActor
|
|
375
378
|
} from "./chunk-CEMMLV5L.js";
|
|
@@ -404,13 +407,13 @@ import {
|
|
|
404
407
|
withContext,
|
|
405
408
|
withLogContext,
|
|
406
409
|
withSpan
|
|
407
|
-
} from "./chunk-
|
|
410
|
+
} from "./chunk-LZBPGX5A.js";
|
|
408
411
|
import {
|
|
409
412
|
continueTrace
|
|
410
413
|
} from "./chunk-PEQXYSSE.js";
|
|
411
414
|
import {
|
|
412
415
|
JUNIOR_VERSION
|
|
413
|
-
} from "./chunk-
|
|
416
|
+
} from "./chunk-W46NIB5H.js";
|
|
414
417
|
|
|
415
418
|
// src/app.ts
|
|
416
419
|
import { createRequire } from "module";
|
|
@@ -514,7 +517,7 @@ async function recoverConversationWork(args) {
|
|
|
514
517
|
}
|
|
515
518
|
return;
|
|
516
519
|
}
|
|
517
|
-
if (work.execution.lease || !
|
|
520
|
+
if (work.execution.lease || !hasRunnableConversationWork2(work)) {
|
|
518
521
|
return;
|
|
519
522
|
}
|
|
520
523
|
const wake = await ensureConversationWake({
|
|
@@ -4044,17 +4047,9 @@ async function decideSubscribedThreadReply(args) {
|
|
|
4044
4047
|
if (preflightDecision) {
|
|
4045
4048
|
return preflightDecision;
|
|
4046
4049
|
}
|
|
4047
|
-
const evidence = buildRouterEvidence(args.input);
|
|
4048
4050
|
if (!text && !args.input.hasAttachments) {
|
|
4049
4051
|
return { shouldReply: false, reason: "empty_message" /* EmptyMessage */ };
|
|
4050
4052
|
}
|
|
4051
|
-
if (!args.input.isExplicitMention && !args.input.hasAttachments && isAcknowledgmentOnly(text)) {
|
|
4052
|
-
return {
|
|
4053
|
-
shouldReply: false,
|
|
4054
|
-
reason: "side_conversation" /* SideConversation */,
|
|
4055
|
-
reasonDetail: "acknowledgment"
|
|
4056
|
-
};
|
|
4057
|
-
}
|
|
4058
4053
|
if (args.input.isExplicitMention) {
|
|
4059
4054
|
if (isThreadOptOutInstruction(rawText, text)) {
|
|
4060
4055
|
return {
|
|
@@ -4069,6 +4064,21 @@ async function decideSubscribedThreadReply(args) {
|
|
|
4069
4064
|
reason: "explicit_mention" /* ExplicitMention */
|
|
4070
4065
|
};
|
|
4071
4066
|
}
|
|
4067
|
+
if (!isExperimentalFeatureEnabled("passive-routing")) {
|
|
4068
|
+
return {
|
|
4069
|
+
shouldReply: false,
|
|
4070
|
+
reason: "passive_disabled" /* PassiveDisabled */,
|
|
4071
|
+
reasonDetail: "passive-routing"
|
|
4072
|
+
};
|
|
4073
|
+
}
|
|
4074
|
+
if (!args.input.hasAttachments && isAcknowledgmentOnly(text)) {
|
|
4075
|
+
return {
|
|
4076
|
+
shouldReply: false,
|
|
4077
|
+
reason: "side_conversation" /* SideConversation */,
|
|
4078
|
+
reasonDetail: "acknowledgment"
|
|
4079
|
+
};
|
|
4080
|
+
}
|
|
4081
|
+
const evidence = buildRouterEvidence(args.input);
|
|
4072
4082
|
if (evidence.assistantWasLastSpeaker && evidence.humanMessagesSinceLastAssistant === 0 && !evidence.currentMessageHasAttachments && (evidence.currentMessageHasDirectedFollowUpCue || evidence.currentMessageIsTerseClarification)) {
|
|
4073
4083
|
return {
|
|
4074
4084
|
shouldReply: true,
|
|
@@ -4200,7 +4210,7 @@ function combineTurnText(queuedMessages, latestText) {
|
|
|
4200
4210
|
};
|
|
4201
4211
|
}
|
|
4202
4212
|
|
|
4203
|
-
// src/chat/
|
|
4213
|
+
// src/chat/providers/slack/runtime.ts
|
|
4204
4214
|
var THREAD_OPTOUT_ACK = "Understood. I'll stay out of this thread unless someone @mentions me again.";
|
|
4205
4215
|
function shouldRethrowTurnControlError(error) {
|
|
4206
4216
|
return isCooperativeTurnYieldError(error) || isTurnInputCommitLostError(error) || isTurnInputDeferredError(error) || isProviderRetryError(error);
|
|
@@ -4579,7 +4589,7 @@ function createSlackTurnRuntime(deps) {
|
|
|
4579
4589
|
}),
|
|
4580
4590
|
stripLeadingBotMention: deps.stripLeadingBotMention
|
|
4581
4591
|
});
|
|
4582
|
-
await deps.
|
|
4592
|
+
await deps.executeSlackTurn(thread, message, {
|
|
4583
4593
|
explicitMention: true,
|
|
4584
4594
|
beforeFirstResponsePost: hooks.beforeFirstResponsePost,
|
|
4585
4595
|
conversationId: hooks.conversationId,
|
|
@@ -4745,6 +4755,31 @@ function createSlackTurnRuntime(deps) {
|
|
|
4745
4755
|
});
|
|
4746
4756
|
return;
|
|
4747
4757
|
}
|
|
4758
|
+
if (!isResourceEventNotification && !turnIsExplicitMention && !isExperimentalFeatureEnabled("passive-routing")) {
|
|
4759
|
+
const decision2 = await deps.decideSubscribedReply({
|
|
4760
|
+
rawText: combinedText.rawText,
|
|
4761
|
+
text: combinedText.userText,
|
|
4762
|
+
hasAttachments: content.hasAttachments || queuedMessages.some(
|
|
4763
|
+
(queued) => queued.message.attachments.length > 0
|
|
4764
|
+
),
|
|
4765
|
+
isExplicitMention: false,
|
|
4766
|
+
context: threadContext
|
|
4767
|
+
});
|
|
4768
|
+
await maybeHandleThreadOptOutDecision({
|
|
4769
|
+
thread,
|
|
4770
|
+
decision: decision2,
|
|
4771
|
+
beforeFirstResponsePost: hooks.beforeFirstResponsePost
|
|
4772
|
+
});
|
|
4773
|
+
await skipSubscribedMessage({
|
|
4774
|
+
thread,
|
|
4775
|
+
message,
|
|
4776
|
+
decision: decision2,
|
|
4777
|
+
context: threadContext,
|
|
4778
|
+
ack: hooks.ack,
|
|
4779
|
+
text: combinedText
|
|
4780
|
+
});
|
|
4781
|
+
return;
|
|
4782
|
+
}
|
|
4748
4783
|
const preparedState = await deps.prepareTurnState({
|
|
4749
4784
|
thread,
|
|
4750
4785
|
message,
|
|
@@ -4844,7 +4879,7 @@ function createSlackTurnRuntime(deps) {
|
|
|
4844
4879
|
processingReaction,
|
|
4845
4880
|
hooks
|
|
4846
4881
|
);
|
|
4847
|
-
await deps.
|
|
4882
|
+
await deps.executeSlackTurn(thread, message, {
|
|
4848
4883
|
explicitMention: Boolean(message.isMention),
|
|
4849
4884
|
conversationId: hooks.conversationId,
|
|
4850
4885
|
destination: hooks.destination,
|
|
@@ -5483,7 +5518,7 @@ function createJuniorRuntimeServices(overrides = {}) {
|
|
|
5483
5518
|
};
|
|
5484
5519
|
}
|
|
5485
5520
|
|
|
5486
|
-
// src/chat/
|
|
5521
|
+
// src/chat/providers/slack/turn.ts
|
|
5487
5522
|
import { createSlackSource as createSlackSource2 } from "@sentry/junior-plugin-api";
|
|
5488
5523
|
|
|
5489
5524
|
// src/chat/slack/message/identity.ts
|
|
@@ -5581,7 +5616,7 @@ async function maybeApplyProviderDefaultConfigRequest(args) {
|
|
|
5581
5616
|
};
|
|
5582
5617
|
}
|
|
5583
5618
|
|
|
5584
|
-
// src/chat/
|
|
5619
|
+
// src/chat/providers/slack/turn.ts
|
|
5585
5620
|
async function persistThreadRuntimeStateWithRetry(thread, patch) {
|
|
5586
5621
|
await persistWithRetry(() => persistThreadRuntimeState(thread, patch));
|
|
5587
5622
|
}
|
|
@@ -5706,8 +5741,8 @@ async function loadPiMessagesForTurn(args) {
|
|
|
5706
5741
|
function shouldPublishExternally2(publishExternally) {
|
|
5707
5742
|
return publishExternally !== false;
|
|
5708
5743
|
}
|
|
5709
|
-
function
|
|
5710
|
-
return async function
|
|
5744
|
+
function createSlackTurn(deps) {
|
|
5745
|
+
return async function executeSlackTurn(thread, message, options) {
|
|
5711
5746
|
if (message.author.isMe) {
|
|
5712
5747
|
return;
|
|
5713
5748
|
}
|
|
@@ -7115,7 +7150,7 @@ function createSlackDispatchTurnRunner(options) {
|
|
|
7115
7150
|
let errorMessage;
|
|
7116
7151
|
let resultMessageTs;
|
|
7117
7152
|
const routing = buildDispatchRoutingContext(dispatch2);
|
|
7118
|
-
await options.
|
|
7153
|
+
await options.executeSlackTurn(thread, message, {
|
|
7119
7154
|
ack: hooks.ack,
|
|
7120
7155
|
conversationId,
|
|
7121
7156
|
destination: dispatch2.destination,
|
|
@@ -7195,7 +7230,7 @@ function createSlackRuntime(options) {
|
|
|
7195
7230
|
);
|
|
7196
7231
|
}
|
|
7197
7232
|
});
|
|
7198
|
-
const
|
|
7233
|
+
const executeSlackTurn = createSlackTurn({
|
|
7199
7234
|
getSlackAdapter: options.getSlackAdapter,
|
|
7200
7235
|
prepareTurnState,
|
|
7201
7236
|
resolveUserAttachments: services.visionContext.resolveUserAttachments,
|
|
@@ -7294,7 +7329,7 @@ function createSlackRuntime(options) {
|
|
|
7294
7329
|
conversation: preparedState.conversation
|
|
7295
7330
|
});
|
|
7296
7331
|
},
|
|
7297
|
-
|
|
7332
|
+
executeSlackTurn,
|
|
7298
7333
|
initializeAssistantThread: async ({
|
|
7299
7334
|
channelId,
|
|
7300
7335
|
threadTs,
|
|
@@ -7325,7 +7360,7 @@ function createSlackRuntime(options) {
|
|
|
7325
7360
|
runDispatchTurn: createSlackDispatchTurnRunner({
|
|
7326
7361
|
getLocationConfiguration: getLocationConfigurationService,
|
|
7327
7362
|
getSlackAdapter: options.getSlackAdapter,
|
|
7328
|
-
|
|
7363
|
+
executeSlackTurn
|
|
7329
7364
|
})
|
|
7330
7365
|
};
|
|
7331
7366
|
}
|
|
@@ -7918,9 +7953,7 @@ function createConversationWork(options) {
|
|
|
7918
7953
|
turnLifecycle: services.replyExecutor?.turnLifecycle
|
|
7919
7954
|
}),
|
|
7920
7955
|
fallbackWorker: routeAgentInvocationWork({
|
|
7921
|
-
invocationWorker: createAgentInvocationWorker(
|
|
7922
|
-
agentRunner: options.agentRunner
|
|
7923
|
-
}),
|
|
7956
|
+
invocationWorker: createAgentInvocationWorker(options.agentRunner),
|
|
7924
7957
|
fallbackWorker: providerWorker
|
|
7925
7958
|
})
|
|
7926
7959
|
}),
|
|
@@ -8118,416 +8151,203 @@ async function ingestEventTasks(input, options) {
|
|
|
8118
8151
|
return { dispatched };
|
|
8119
8152
|
}
|
|
8120
8153
|
|
|
8121
|
-
// src/api/
|
|
8122
|
-
|
|
8123
|
-
|
|
8124
|
-
|
|
8125
|
-
|
|
8126
|
-
|
|
8127
|
-
|
|
8128
|
-
|
|
8129
|
-
|
|
8130
|
-
|
|
8131
|
-
|
|
8132
|
-
|
|
8133
|
-
|
|
8134
|
-
|
|
8135
|
-
|
|
8136
|
-
|
|
8137
|
-
|
|
8138
|
-
|
|
8139
|
-
|
|
8140
|
-
|
|
8141
|
-
|
|
8142
|
-
|
|
8143
|
-
|
|
8144
|
-
user.email ?? email,
|
|
8145
|
-
user.displayName ? { fullName: user.displayName } : void 0
|
|
8146
|
-
),
|
|
8147
|
-
user
|
|
8148
|
-
};
|
|
8149
|
-
}
|
|
8150
|
-
function rejectUnsupportedMcpServers(mcpServers) {
|
|
8151
|
-
if (mcpServers.length > 0) {
|
|
8152
|
-
throw acp.RequestError.invalidParams(
|
|
8153
|
-
{ field: "mcpServers" },
|
|
8154
|
-
"Junior does not accept client MCP servers"
|
|
8155
|
-
);
|
|
8156
|
-
}
|
|
8157
|
-
}
|
|
8158
|
-
async function requireOwnedSession(sessionId, user) {
|
|
8159
|
-
if (!sessionId.startsWith(ACP_CONVERSATION_PREFIX)) {
|
|
8160
|
-
throw acp.RequestError.resourceNotFound(sessionId);
|
|
8154
|
+
// src/chat/api-turns/stop.ts
|
|
8155
|
+
async function stopApiConversationTurn(args) {
|
|
8156
|
+
const nowMs = args.nowMs ?? Date.now();
|
|
8157
|
+
const stop = async () => await stopConversationWork({
|
|
8158
|
+
conversationId: args.conversationId,
|
|
8159
|
+
conversationStore: args.conversationStore,
|
|
8160
|
+
nowMs,
|
|
8161
|
+
state: args.state
|
|
8162
|
+
});
|
|
8163
|
+
let result = await stop();
|
|
8164
|
+
if (result.status === "no_work" && await getAuthPausedApiTurnId(args.conversationId)) {
|
|
8165
|
+
const conversation = await getConversation({
|
|
8166
|
+
conversationId: args.conversationId,
|
|
8167
|
+
state: args.state
|
|
8168
|
+
});
|
|
8169
|
+
await requestConversationWork({
|
|
8170
|
+
conversationId: args.conversationId,
|
|
8171
|
+
conversationStore: args.conversationStore,
|
|
8172
|
+
destination: conversation?.destination,
|
|
8173
|
+
nowMs,
|
|
8174
|
+
state: args.state
|
|
8175
|
+
});
|
|
8176
|
+
result = await stop();
|
|
8161
8177
|
}
|
|
8162
|
-
|
|
8163
|
-
|
|
8164
|
-
|
|
8178
|
+
if (result.status === "requested") {
|
|
8179
|
+
await ensureConversationWake({
|
|
8180
|
+
conversationId: args.conversationId,
|
|
8181
|
+
conversationStore: args.conversationStore,
|
|
8182
|
+
idempotencyKey: `api-stop:${args.conversationId}:${result.runId}`,
|
|
8183
|
+
nowMs,
|
|
8184
|
+
queue: args.queue,
|
|
8185
|
+
replaceExistingWake: true,
|
|
8186
|
+
state: args.state
|
|
8187
|
+
});
|
|
8165
8188
|
}
|
|
8189
|
+
return result;
|
|
8166
8190
|
}
|
|
8167
|
-
|
|
8168
|
-
|
|
8169
|
-
|
|
8170
|
-
|
|
8171
|
-
|
|
8172
|
-
|
|
8173
|
-
|
|
8174
|
-
|
|
8175
|
-
|
|
8176
|
-
|
|
8177
|
-
|
|
8178
|
-
|
|
8179
|
-
|
|
8180
|
-
|
|
8181
|
-
|
|
8182
|
-
|
|
8183
|
-
|
|
8184
|
-
|
|
8185
|
-
|
|
8186
|
-
|
|
8187
|
-
|
|
8188
|
-
|
|
8191
|
+
|
|
8192
|
+
// src/chat/api-turns/adapter-conversations.ts
|
|
8193
|
+
var EVENT_PAGE_SIZE = 50;
|
|
8194
|
+
function actorFromUser(user) {
|
|
8195
|
+
return webActorFromEmail(
|
|
8196
|
+
user.email,
|
|
8197
|
+
user.displayName ? { fullName: user.displayName } : void 0
|
|
8198
|
+
);
|
|
8199
|
+
}
|
|
8200
|
+
async function hasConversationAccess(conversationId, user) {
|
|
8201
|
+
const access = (await readConversationAccessFromSql(getDb(), [conversationId], user)).get(conversationId);
|
|
8202
|
+
return Boolean(access?.isParticipant);
|
|
8203
|
+
}
|
|
8204
|
+
async function turnTerminalIsReady(args) {
|
|
8205
|
+
const conversation = await getConversation({
|
|
8206
|
+
conversationId: args.conversationId,
|
|
8207
|
+
state: args.state
|
|
8208
|
+
});
|
|
8209
|
+
if (conversation?.execution.pendingMessages.some(
|
|
8210
|
+
(message) => message.inboundMessageId === args.messageId
|
|
8211
|
+
)) {
|
|
8212
|
+
return false;
|
|
8189
8213
|
}
|
|
8190
|
-
|
|
8191
|
-
|
|
8192
|
-
throw acp.RequestError.invalidParams(
|
|
8193
|
-
{ field: "prompt" },
|
|
8194
|
-
`Junior accepts at most ${MAX_PROMPT_TEXT_LENGTH} prompt characters`
|
|
8195
|
-
);
|
|
8214
|
+
if (!conversation || !hasRunnableConversationWork(conversation)) {
|
|
8215
|
+
return true;
|
|
8196
8216
|
}
|
|
8197
|
-
|
|
8198
|
-
|
|
8199
|
-
|
|
8200
|
-
|
|
8201
|
-
|
|
8217
|
+
const later = await args.eventStore.query(args.conversationId, {
|
|
8218
|
+
afterSeq: args.terminalSeq,
|
|
8219
|
+
limit: 1,
|
|
8220
|
+
types: ["turn_started"]
|
|
8221
|
+
});
|
|
8222
|
+
return later.events.some(
|
|
8223
|
+
(event) => event.data.type === "turn_started" && event.data.turnId !== args.turnId
|
|
8224
|
+
);
|
|
8202
8225
|
}
|
|
8203
|
-
async function
|
|
8226
|
+
async function latestEventCursor(eventStore, conversationId) {
|
|
8204
8227
|
const page = await eventStore.query(conversationId, { limit: 1 });
|
|
8205
8228
|
return page.events.at(-1)?.seq ?? 0;
|
|
8206
8229
|
}
|
|
8207
|
-
|
|
8208
|
-
|
|
8209
|
-
|
|
8210
|
-
|
|
8211
|
-
|
|
8212
|
-
sessionId,
|
|
8213
|
-
update: {
|
|
8214
|
-
sessionUpdate: message.role === "user" ? "user_message_chunk" : "agent_message_chunk",
|
|
8215
|
-
content: { type: "text", text: message.text },
|
|
8216
|
-
messageId: message.id
|
|
8217
|
-
}
|
|
8218
|
-
});
|
|
8219
|
-
}
|
|
8220
|
-
}
|
|
8221
|
-
async function waitForTurn(args) {
|
|
8222
|
-
let cursor = args.afterSeq;
|
|
8223
|
-
const assistantPrefix = `${args.turnId}:assistant:`;
|
|
8224
|
-
const sentMessageIds = /* @__PURE__ */ new Set();
|
|
8225
|
-
while (true) {
|
|
8226
|
-
if (args.signal.aborted) {
|
|
8227
|
-
throw acp.RequestError.requestCancelled();
|
|
8228
|
-
}
|
|
8229
|
-
const page = await args.eventStore.query(args.sessionId, {
|
|
8230
|
-
afterSeq: cursor,
|
|
8231
|
-
limit: EVENT_PAGE_SIZE,
|
|
8232
|
-
types: ["message", "turn_completed", "turn_failed"]
|
|
8233
|
-
});
|
|
8234
|
-
if (page.events.length === 0) {
|
|
8235
|
-
try {
|
|
8236
|
-
await sleep(EVENT_POLL_INTERVAL_MS, args.signal);
|
|
8237
|
-
} catch (error) {
|
|
8238
|
-
if (args.signal.aborted) {
|
|
8239
|
-
throw acp.RequestError.requestCancelled();
|
|
8240
|
-
}
|
|
8241
|
-
throw error;
|
|
8242
|
-
}
|
|
8243
|
-
continue;
|
|
8244
|
-
}
|
|
8245
|
-
for (const event of page.events) {
|
|
8246
|
-
cursor = event.seq;
|
|
8247
|
-
const data = event.data;
|
|
8248
|
-
if (data.type === "message" && data.role === "assistant" && data.messageId.startsWith(assistantPrefix) && !sentMessageIds.has(data.messageId)) {
|
|
8249
|
-
sentMessageIds.add(data.messageId);
|
|
8250
|
-
await args.client.notify(acp.methods.client.session.update, {
|
|
8251
|
-
sessionId: args.sessionId,
|
|
8252
|
-
update: {
|
|
8253
|
-
sessionUpdate: "agent_message_chunk",
|
|
8254
|
-
content: { type: "text", text: data.text },
|
|
8255
|
-
messageId: data.messageId
|
|
8256
|
-
}
|
|
8257
|
-
});
|
|
8258
|
-
continue;
|
|
8259
|
-
}
|
|
8260
|
-
if (data.type === "turn_completed" && data.turnId === args.turnId) {
|
|
8261
|
-
args.cancellation.finish(args.sessionId, args.cancellationSignal);
|
|
8262
|
-
return {
|
|
8263
|
-
stopReason: data.outcome === "cancelled" ? "cancelled" : "end_turn"
|
|
8264
|
-
};
|
|
8265
|
-
}
|
|
8266
|
-
if (data.type === "turn_failed" && data.turnId === args.turnId) {
|
|
8267
|
-
args.cancellation.finish(args.sessionId, args.cancellationSignal);
|
|
8268
|
-
throw acp.RequestError.internalError(
|
|
8269
|
-
{ failureCode: data.failureCode },
|
|
8270
|
-
"Junior Turn failed"
|
|
8271
|
-
);
|
|
8230
|
+
function createAdapterConversations(options) {
|
|
8231
|
+
return {
|
|
8232
|
+
async cancel({ conversationId, user }) {
|
|
8233
|
+
if (!await hasConversationAccess(conversationId, user)) {
|
|
8234
|
+
return "not_found";
|
|
8272
8235
|
}
|
|
8273
|
-
|
|
8274
|
-
|
|
8275
|
-
|
|
8276
|
-
|
|
8277
|
-
|
|
8278
|
-
|
|
8279
|
-
|
|
8280
|
-
name,
|
|
8281
|
-
{
|
|
8282
|
-
actorId: authenticated.actor.userId,
|
|
8283
|
-
conversationId,
|
|
8284
|
-
platform: "acp",
|
|
8285
|
-
userId: authenticated.actor.userId
|
|
8236
|
+
await stopApiConversationTurn({
|
|
8237
|
+
conversationId,
|
|
8238
|
+
conversationStore: options.conversationStore,
|
|
8239
|
+
queue: options.queue,
|
|
8240
|
+
state: options.state
|
|
8241
|
+
});
|
|
8242
|
+
return "cancelled";
|
|
8286
8243
|
},
|
|
8287
|
-
async ()
|
|
8288
|
-
|
|
8289
|
-
|
|
8290
|
-
|
|
8291
|
-
|
|
8292
|
-
|
|
8293
|
-
|
|
8294
|
-
|
|
8295
|
-
|
|
8296
|
-
}
|
|
8297
|
-
|
|
8298
|
-
}
|
|
8299
|
-
|
|
8300
|
-
|
|
8301
|
-
|
|
8302
|
-
return acp.agent({ name: "junior" }).onRequest(
|
|
8303
|
-
acp.methods.agent.initialize,
|
|
8304
|
-
() => runAcpOperation(authenticated, "initialize", void 0, () => ({
|
|
8305
|
-
protocolVersion: acp.PROTOCOL_VERSION,
|
|
8306
|
-
agentCapabilities: {
|
|
8307
|
-
loadSession: true,
|
|
8308
|
-
promptCapabilities: {
|
|
8309
|
-
image: false,
|
|
8310
|
-
audio: false,
|
|
8311
|
-
embeddedContext: false
|
|
8312
|
-
}
|
|
8313
|
-
},
|
|
8314
|
-
authMethods: [],
|
|
8315
|
-
agentInfo: { name: "junior", version: JUNIOR_VERSION }
|
|
8316
|
-
}))
|
|
8317
|
-
).onRequest(acp.methods.agent.session.new, async (context) => {
|
|
8318
|
-
return await runAcpOperation(
|
|
8319
|
-
authenticated,
|
|
8320
|
-
"session_new",
|
|
8321
|
-
void 0,
|
|
8322
|
-
async () => {
|
|
8323
|
-
rejectUnsupportedMcpServers(context.params.mcpServers);
|
|
8324
|
-
const sessionId = `${ACP_CONVERSATION_PREFIX}${randomUUID()}`;
|
|
8325
|
-
await recordApiConversationActivity({
|
|
8326
|
-
actor: authenticated.actor,
|
|
8327
|
-
conversationId: sessionId,
|
|
8328
|
-
conversationStore,
|
|
8329
|
-
nowMs: Date.now(),
|
|
8330
|
-
rootVisibility: "private"
|
|
8331
|
-
});
|
|
8332
|
-
return { sessionId };
|
|
8333
|
-
}
|
|
8334
|
-
);
|
|
8335
|
-
}).onRequest(acp.methods.agent.session.load, async (context) => {
|
|
8336
|
-
return await runAcpOperation(
|
|
8337
|
-
authenticated,
|
|
8338
|
-
"session_load",
|
|
8339
|
-
context.params.sessionId,
|
|
8340
|
-
async () => {
|
|
8341
|
-
rejectUnsupportedMcpServers(context.params.mcpServers);
|
|
8342
|
-
await requireOwnedSession(
|
|
8343
|
-
context.params.sessionId,
|
|
8344
|
-
authenticated.user
|
|
8345
|
-
);
|
|
8346
|
-
await replaySession(
|
|
8347
|
-
eventStore,
|
|
8348
|
-
context.params.sessionId,
|
|
8349
|
-
context.client
|
|
8350
|
-
);
|
|
8351
|
-
return {};
|
|
8244
|
+
async create({ conversationId, user }) {
|
|
8245
|
+
await recordApiConversationActivity({
|
|
8246
|
+
actor: actorFromUser(user),
|
|
8247
|
+
conversationId,
|
|
8248
|
+
conversationStore: options.conversationStore,
|
|
8249
|
+
nowMs: Date.now(),
|
|
8250
|
+
rootVisibility: "private"
|
|
8251
|
+
});
|
|
8252
|
+
},
|
|
8253
|
+
async hasAccess({ conversationId, user }) {
|
|
8254
|
+
return await hasConversationAccess(conversationId, user);
|
|
8255
|
+
},
|
|
8256
|
+
async prompt({ conversationId, idempotencyKey, text, user }) {
|
|
8257
|
+
if (!await hasConversationAccess(conversationId, user)) {
|
|
8258
|
+
return { status: "not_found" };
|
|
8352
8259
|
}
|
|
8353
|
-
|
|
8354
|
-
|
|
8355
|
-
|
|
8356
|
-
|
|
8357
|
-
|
|
8358
|
-
|
|
8359
|
-
async () => {
|
|
8360
|
-
await requireOwnedSession(
|
|
8361
|
-
context.params.sessionId,
|
|
8362
|
-
authenticated.user
|
|
8363
|
-
);
|
|
8364
|
-
const text = promptText(context.params.prompt);
|
|
8365
|
-
const currentSeq = await latestEventSeq(
|
|
8366
|
-
eventStore,
|
|
8367
|
-
context.params.sessionId
|
|
8368
|
-
);
|
|
8369
|
-
const cancellationSignal = options.cancellation.begin(
|
|
8370
|
-
context.params.sessionId
|
|
8371
|
-
);
|
|
8372
|
-
if (!cancellationSignal) {
|
|
8373
|
-
throw acp.RequestError.invalidParams(
|
|
8374
|
-
{ field: "sessionId" },
|
|
8375
|
-
"This ACP session already has an active prompt"
|
|
8376
|
-
);
|
|
8377
|
-
}
|
|
8378
|
-
const recordDisconnect = () => options.cancellation.disconnect(
|
|
8379
|
-
context.params.sessionId,
|
|
8380
|
-
cancellationSignal
|
|
8381
|
-
);
|
|
8382
|
-
if (context.signal.aborted) {
|
|
8383
|
-
recordDisconnect();
|
|
8384
|
-
} else {
|
|
8385
|
-
context.signal.addEventListener("abort", recordDisconnect, {
|
|
8386
|
-
once: true
|
|
8387
|
-
});
|
|
8388
|
-
}
|
|
8389
|
-
let accepted;
|
|
8390
|
-
try {
|
|
8391
|
-
accepted = await appendAndEnqueueApiConversationMessage(
|
|
8392
|
-
{
|
|
8393
|
-
actor: authenticated.actor,
|
|
8394
|
-
conversationId: context.params.sessionId,
|
|
8395
|
-
idempotencyKey: `${connectionNonce}:${requestIdKey(context.requestId)}`,
|
|
8396
|
-
message: text
|
|
8397
|
-
},
|
|
8398
|
-
{
|
|
8399
|
-
conversationStore,
|
|
8400
|
-
queue: options.queue,
|
|
8401
|
-
state: options.state
|
|
8402
|
-
}
|
|
8403
|
-
);
|
|
8404
|
-
} catch (error) {
|
|
8405
|
-
options.cancellation.finish(
|
|
8406
|
-
context.params.sessionId,
|
|
8407
|
-
cancellationSignal
|
|
8408
|
-
);
|
|
8409
|
-
throw error;
|
|
8410
|
-
}
|
|
8411
|
-
const afterSeq = accepted.status === "duplicate" ? 0 : currentSeq;
|
|
8412
|
-
return await waitForTurn({
|
|
8413
|
-
afterSeq,
|
|
8414
|
-
cancellation: options.cancellation,
|
|
8415
|
-
cancellationSignal,
|
|
8416
|
-
client: context.client,
|
|
8417
|
-
eventStore,
|
|
8418
|
-
sessionId: context.params.sessionId,
|
|
8419
|
-
signal: context.signal,
|
|
8420
|
-
turnId: apiTurnIdForMessage(accepted.messageId)
|
|
8421
|
-
});
|
|
8260
|
+
const currentCursor = await latestEventCursor(
|
|
8261
|
+
options.eventStore,
|
|
8262
|
+
conversationId
|
|
8263
|
+
);
|
|
8264
|
+
if (await getAuthPausedApiTurnId(conversationId)) {
|
|
8265
|
+
return { status: "active" };
|
|
8422
8266
|
}
|
|
8423
|
-
|
|
8424
|
-
|
|
8425
|
-
|
|
8426
|
-
|
|
8427
|
-
|
|
8428
|
-
|
|
8429
|
-
|
|
8430
|
-
|
|
8431
|
-
|
|
8432
|
-
|
|
8433
|
-
);
|
|
8434
|
-
if (!options.cancellation.cancel(context.params.sessionId)) {
|
|
8435
|
-
return;
|
|
8436
|
-
}
|
|
8437
|
-
const nowMs = Date.now();
|
|
8438
|
-
await ensureConversationWake({
|
|
8439
|
-
conversationId: context.params.sessionId,
|
|
8440
|
-
conversationStore,
|
|
8441
|
-
idempotencyKey: `acp-cancel:${context.params.sessionId}:${nowMs}`,
|
|
8442
|
-
nowMs,
|
|
8267
|
+
const admission = await appendAndEnqueueApiConversationMessage(
|
|
8268
|
+
{
|
|
8269
|
+
actor: actorFromUser(user),
|
|
8270
|
+
conversationId,
|
|
8271
|
+
idempotencyKey,
|
|
8272
|
+
message: text
|
|
8273
|
+
},
|
|
8274
|
+
{
|
|
8275
|
+
conversationStore: options.conversationStore,
|
|
8276
|
+
exclusive: true,
|
|
8443
8277
|
queue: options.queue,
|
|
8444
|
-
replaceExistingWake: true,
|
|
8445
8278
|
state: options.state
|
|
8446
|
-
}
|
|
8447
|
-
|
|
8448
|
-
|
|
8449
|
-
|
|
8450
|
-
|
|
8451
|
-
|
|
8452
|
-
|
|
8453
|
-
|
|
8454
|
-
|
|
8455
|
-
|
|
8456
|
-
|
|
8457
|
-
|
|
8458
|
-
|
|
8459
|
-
|
|
8460
|
-
|
|
8461
|
-
|
|
8462
|
-
|
|
8463
|
-
|
|
8464
|
-
|
|
8465
|
-
|
|
8466
|
-
|
|
8467
|
-
|
|
8468
|
-
|
|
8469
|
-
|
|
8470
|
-
|
|
8471
|
-
|
|
8472
|
-
|
|
8473
|
-
|
|
8474
|
-
|
|
8475
|
-
|
|
8476
|
-
|
|
8477
|
-
|
|
8478
|
-
|
|
8479
|
-
|
|
8480
|
-
|
|
8481
|
-
|
|
8482
|
-
|
|
8483
|
-
|
|
8484
|
-
|
|
8485
|
-
|
|
8486
|
-
|
|
8487
|
-
|
|
8488
|
-
|
|
8489
|
-
|
|
8490
|
-
|
|
8491
|
-
|
|
8492
|
-
|
|
8493
|
-
|
|
8494
|
-
|
|
8495
|
-
|
|
8496
|
-
|
|
8497
|
-
|
|
8498
|
-
|
|
8499
|
-
|
|
8500
|
-
|
|
8501
|
-
|
|
8502
|
-
});
|
|
8503
|
-
const responseConnectionId = response.headers.get(ACP_CONNECTION_ID_HEADER);
|
|
8504
|
-
if (response.ok && responseConnectionId && !connectionId) {
|
|
8505
|
-
if (await initializationSucceeded(response)) {
|
|
8506
|
-
connectionActors.set(responseConnectionId, authenticated.actor.userId);
|
|
8507
|
-
} else {
|
|
8508
|
-
await server.handleRequest(
|
|
8509
|
-
new Request(request.url, {
|
|
8510
|
-
method: "DELETE",
|
|
8511
|
-
headers: { [ACP_CONNECTION_ID_HEADER]: responseConnectionId }
|
|
8512
|
-
})
|
|
8513
|
-
);
|
|
8514
|
-
const headers = new Headers(response.headers);
|
|
8515
|
-
headers.delete(ACP_CONNECTION_ID_HEADER);
|
|
8516
|
-
return new Response(response.body, {
|
|
8517
|
-
headers,
|
|
8518
|
-
status: response.status,
|
|
8519
|
-
statusText: response.statusText
|
|
8520
|
-
});
|
|
8279
|
+
}
|
|
8280
|
+
);
|
|
8281
|
+
if (admission.status === "active") return { status: "active" };
|
|
8282
|
+
return {
|
|
8283
|
+
afterCursor: admission.status === "duplicate" ? 0 : currentCursor,
|
|
8284
|
+
messageId: admission.messageId,
|
|
8285
|
+
status: "accepted",
|
|
8286
|
+
turnId: apiTurnIdForMessage(admission.messageId)
|
|
8287
|
+
};
|
|
8288
|
+
},
|
|
8289
|
+
async readMessages(conversationId) {
|
|
8290
|
+
const history = await options.eventStore.loadMessageHistory(conversationId);
|
|
8291
|
+
return projectConversationMessages(history).filter(
|
|
8292
|
+
(message) => message.role !== "system"
|
|
8293
|
+
).map(({ id, role, text }) => ({ id, role, text }));
|
|
8294
|
+
},
|
|
8295
|
+
async readTurn({ afterCursor, conversationId, messageId, turnId }) {
|
|
8296
|
+
const page = await options.eventStore.query(conversationId, {
|
|
8297
|
+
afterSeq: afterCursor,
|
|
8298
|
+
limit: EVENT_PAGE_SIZE,
|
|
8299
|
+
types: ["message", "turn_completed", "turn_failed"]
|
|
8300
|
+
});
|
|
8301
|
+
const cursor = page.events.at(-1)?.seq ?? afterCursor;
|
|
8302
|
+
const assistantPrefix = `${turnId}:assistant:`;
|
|
8303
|
+
const messages = page.events.flatMap((event) => {
|
|
8304
|
+
const data = event.data;
|
|
8305
|
+
return data.type === "message" && data.role === "assistant" && data.messageId.startsWith(assistantPrefix) ? [
|
|
8306
|
+
{
|
|
8307
|
+
id: data.messageId,
|
|
8308
|
+
role: "assistant",
|
|
8309
|
+
text: data.text
|
|
8310
|
+
}
|
|
8311
|
+
] : [];
|
|
8312
|
+
});
|
|
8313
|
+
let terminal;
|
|
8314
|
+
const terminalEvent = await options.eventStore.loadByIdempotencyKey(
|
|
8315
|
+
conversationId,
|
|
8316
|
+
`turn:${turnId}:terminal`
|
|
8317
|
+
);
|
|
8318
|
+
if (terminalEvent && terminalEvent.seq <= cursor && await turnTerminalIsReady({
|
|
8319
|
+
conversationId,
|
|
8320
|
+
eventStore: options.eventStore,
|
|
8321
|
+
messageId,
|
|
8322
|
+
state: options.state,
|
|
8323
|
+
terminalSeq: terminalEvent.seq,
|
|
8324
|
+
turnId
|
|
8325
|
+
})) {
|
|
8326
|
+
const data = terminalEvent.data;
|
|
8327
|
+
if (data.type === "turn_completed" && data.turnId === turnId) {
|
|
8328
|
+
terminal = {
|
|
8329
|
+
outcome: data.outcome === "cancelled" ? "cancelled" : "completed",
|
|
8330
|
+
status: "completed"
|
|
8331
|
+
};
|
|
8332
|
+
} else if (data.type === "turn_failed" && data.turnId === turnId) {
|
|
8333
|
+
terminal = { failureCode: data.failureCode, status: "failed" };
|
|
8334
|
+
}
|
|
8521
8335
|
}
|
|
8336
|
+
const turnPage = { cursor, messages };
|
|
8337
|
+
if (terminal) turnPage.terminal = terminal;
|
|
8338
|
+
return turnPage;
|
|
8522
8339
|
}
|
|
8523
|
-
if (request.method === "DELETE" && response.ok && connectionId) {
|
|
8524
|
-
connectionActors.delete(connectionId);
|
|
8525
|
-
}
|
|
8526
|
-
return response;
|
|
8527
8340
|
};
|
|
8528
8341
|
}
|
|
8529
8342
|
|
|
8530
8343
|
// src/app.ts
|
|
8344
|
+
function resolveAdapterBaseURL(dashboard) {
|
|
8345
|
+
const configured = dashboard?.baseURL?.trim() || process.env.JUNIOR_BASE_URL?.trim();
|
|
8346
|
+
if (configured) return configured;
|
|
8347
|
+
const vercelURL = process.env.VERCEL_PROJECT_PRODUCTION_URL?.trim() || process.env.VERCEL_URL?.trim();
|
|
8348
|
+
if (!vercelURL) return void 0;
|
|
8349
|
+
return /^https?:\/\//.test(vercelURL) ? vercelURL : `https://${vercelURL}`;
|
|
8350
|
+
}
|
|
8531
8351
|
var DASHBOARD_PACKAGE_NAME = "@sentry/junior-dashboard";
|
|
8532
8352
|
async function defaultWaitUntil() {
|
|
8533
8353
|
try {
|
|
@@ -8625,6 +8445,7 @@ async function createDashboardRouteRegistrations(args) {
|
|
|
8625
8445
|
}
|
|
8626
8446
|
const createDashboardApp = args.createDashboardApp ?? await loadDashboardAppFactory();
|
|
8627
8447
|
return dashboardRouteRegistrations({
|
|
8448
|
+
authenticatedRoutes: args.authenticatedRoutes,
|
|
8628
8449
|
dashboard: args.dashboard,
|
|
8629
8450
|
createDashboardApp,
|
|
8630
8451
|
pluginRoutes: args.pluginRoutes
|
|
@@ -8672,7 +8493,7 @@ function normalizeDashboardPath(path, fallback) {
|
|
|
8672
8493
|
const withSlash = value.startsWith("/") ? value : `/${value}`;
|
|
8673
8494
|
return stripTrailingSlashes(withSlash);
|
|
8674
8495
|
}
|
|
8675
|
-
function dashboardHostRoutePaths(dashboard) {
|
|
8496
|
+
function dashboardHostRoutePaths(dashboard, authenticatedRoutes = []) {
|
|
8676
8497
|
const basePath = normalizeDashboardPath(dashboard.basePath, "/");
|
|
8677
8498
|
const authPath = normalizeDashboardPath(dashboard.authPath, "/api/auth");
|
|
8678
8499
|
const pagePath = (suffix) => basePath === "/" ? `/${suffix}` : `${basePath}/${suffix}`;
|
|
@@ -8680,6 +8501,7 @@ function dashboardHostRoutePaths(dashboard) {
|
|
|
8680
8501
|
const peoplePath = pagePath("people");
|
|
8681
8502
|
const pagePaths = [
|
|
8682
8503
|
basePath,
|
|
8504
|
+
pagePath("code"),
|
|
8683
8505
|
conversationsPath,
|
|
8684
8506
|
`${conversationsPath}/*`,
|
|
8685
8507
|
pagePath("locations"),
|
|
@@ -8719,6 +8541,7 @@ function dashboardHostRoutePaths(dashboard) {
|
|
|
8719
8541
|
"/api/tasks",
|
|
8720
8542
|
"/api/tasks/*",
|
|
8721
8543
|
"/api/skills",
|
|
8544
|
+
"/api/code",
|
|
8722
8545
|
"/api/stats",
|
|
8723
8546
|
"/api/conversations",
|
|
8724
8547
|
"/api/conversations/*",
|
|
@@ -8732,6 +8555,7 @@ function dashboardHostRoutePaths(dashboard) {
|
|
|
8732
8555
|
"/api/workspaces/*",
|
|
8733
8556
|
"/api/config",
|
|
8734
8557
|
"/api/me",
|
|
8558
|
+
...authenticatedRoutes.map((route) => route.path),
|
|
8735
8559
|
authPath,
|
|
8736
8560
|
`${authPath}/*`
|
|
8737
8561
|
];
|
|
@@ -8782,35 +8606,43 @@ function routePatternOverlaps(ownedPath, routePath) {
|
|
|
8782
8606
|
(example) => routePatternMatchesConcretePath(routePath, example)
|
|
8783
8607
|
);
|
|
8784
8608
|
}
|
|
8785
|
-
function dashboardOwnedRoutePath(routePath, dashboard) {
|
|
8786
|
-
return dashboardHostRoutePaths(dashboard).some(
|
|
8609
|
+
function dashboardOwnedRoutePath(routePath, dashboard, authenticatedRoutes = []) {
|
|
8610
|
+
return dashboardHostRoutePaths(dashboard, authenticatedRoutes).some(
|
|
8787
8611
|
(path) => routePatternOverlaps(path, routePath)
|
|
8788
8612
|
);
|
|
8789
8613
|
}
|
|
8790
8614
|
function dashboardRouteRegistrations(args) {
|
|
8791
8615
|
let app;
|
|
8792
8616
|
const fetch2 = (request) => {
|
|
8793
|
-
|
|
8617
|
+
const dashboardOptions = {
|
|
8794
8618
|
...args.dashboard,
|
|
8795
8619
|
agentName: botConfig.userName,
|
|
8620
|
+
authenticatedRoutes: args.authenticatedRoutes,
|
|
8796
8621
|
pluginRoutes: args.pluginRoutes
|
|
8797
|
-
}
|
|
8622
|
+
};
|
|
8623
|
+
app ??= args.createDashboardApp(dashboardOptions);
|
|
8798
8624
|
if (!app || typeof app.fetch !== "function") {
|
|
8799
8625
|
throw new Error("createDashboardApp() must return an app with fetch()");
|
|
8800
8626
|
}
|
|
8801
8627
|
return app.fetch(request);
|
|
8802
8628
|
};
|
|
8803
|
-
return dashboardHostRoutePaths(args.dashboard).map(
|
|
8804
|
-
|
|
8805
|
-
|
|
8806
|
-
|
|
8629
|
+
return dashboardHostRoutePaths(args.dashboard, args.authenticatedRoutes).map(
|
|
8630
|
+
(path) => ({
|
|
8631
|
+
handler: fetch2,
|
|
8632
|
+
path
|
|
8633
|
+
})
|
|
8634
|
+
);
|
|
8807
8635
|
}
|
|
8808
8636
|
function validateDashboardRouteOwnership(args) {
|
|
8809
8637
|
if (!args.dashboard || args.dashboard.disabled) {
|
|
8810
8638
|
return;
|
|
8811
8639
|
}
|
|
8812
8640
|
for (const route of args.routes) {
|
|
8813
|
-
if (dashboardOwnedRoutePath(
|
|
8641
|
+
if (dashboardOwnedRoutePath(
|
|
8642
|
+
route.path,
|
|
8643
|
+
args.dashboard,
|
|
8644
|
+
args.authenticatedRoutes
|
|
8645
|
+
)) {
|
|
8814
8646
|
throw new Error(
|
|
8815
8647
|
`Plugin "${route.pluginName}" route "${route.path}" conflicts with core dashboard routes`
|
|
8816
8648
|
);
|
|
@@ -8820,11 +8652,11 @@ function validateDashboardRouteOwnership(args) {
|
|
|
8820
8652
|
function mountRoutes(app, routes) {
|
|
8821
8653
|
for (const route of routes) {
|
|
8822
8654
|
const handler = (c) => route.handler(c.req.raw);
|
|
8823
|
-
const
|
|
8824
|
-
const explicitMethods =
|
|
8655
|
+
const methods = typeof route.method === "string" ? [route.method] : route.method ?? ["ALL"];
|
|
8656
|
+
const explicitMethods = methods.filter(
|
|
8825
8657
|
(method) => method !== "ALL"
|
|
8826
8658
|
);
|
|
8827
|
-
if (
|
|
8659
|
+
if (methods.includes("ALL")) {
|
|
8828
8660
|
app.all(route.path, handler);
|
|
8829
8661
|
} else if (explicitMethods.length > 0) {
|
|
8830
8662
|
app.on(explicitMethods, route.path, handler);
|
|
@@ -8858,10 +8690,42 @@ async function createApp(options) {
|
|
|
8858
8690
|
const previousSandboxResources = getSandboxResourceConfig();
|
|
8859
8691
|
const previousExperimentalFeatures = getExperimentalFeatures();
|
|
8860
8692
|
const previousDashboardLinkOptions = setDashboardConversationLinkOptions(dashboard);
|
|
8693
|
+
const restoreRuntimeConfig = () => {
|
|
8694
|
+
pluginCatalogRuntime.setConfig(previousPluginCatalogConfig);
|
|
8695
|
+
setPlugins(previousPlugins);
|
|
8696
|
+
setConfigDefaults(previousConfigDefaults);
|
|
8697
|
+
botConfig.defaultProfile = previousDefaultProfile;
|
|
8698
|
+
botConfig.profiles = previousModelProfiles;
|
|
8699
|
+
setSlackReactionConfig(previousSlackReactionConfig);
|
|
8700
|
+
setSandboxResourceConfig(previousSandboxResources);
|
|
8701
|
+
setExperimentalFeatures(previousExperimentalFeatures);
|
|
8702
|
+
setDashboardConversationLinkOptions(previousDashboardLinkOptions);
|
|
8703
|
+
};
|
|
8861
8704
|
let pluginRoutes = [];
|
|
8862
8705
|
let pluginApiRoutes = [];
|
|
8863
8706
|
const resolveResourceEventTeamId = createResourceEventTeamIdResolver();
|
|
8864
8707
|
const resourceEvents = {
|
|
8708
|
+
async neededMatchKeys(input) {
|
|
8709
|
+
const teamId = await resolveResourceEventTeamId();
|
|
8710
|
+
if (!teamId) return [];
|
|
8711
|
+
const conversationWork = getConversationWorkOptions();
|
|
8712
|
+
const [watchKeys, taskKeys] = await Promise.all([
|
|
8713
|
+
collectResourceEventMatchKeys({
|
|
8714
|
+
eventTypes: input.eventTypes,
|
|
8715
|
+
identifiers: input.identifiers,
|
|
8716
|
+
namespace: input.namespace,
|
|
8717
|
+
state: conversationWork.state,
|
|
8718
|
+
teamId
|
|
8719
|
+
}),
|
|
8720
|
+
collectEventTaskMatchKeys(getDb(), {
|
|
8721
|
+
eventTypes: input.eventTypes,
|
|
8722
|
+
identifiers: input.identifiers,
|
|
8723
|
+
namespace: input.namespace,
|
|
8724
|
+
teamId
|
|
8725
|
+
})
|
|
8726
|
+
]);
|
|
8727
|
+
return [.../* @__PURE__ */ new Set([...watchKeys, ...taskKeys])].sort();
|
|
8728
|
+
},
|
|
8865
8729
|
async publish(event) {
|
|
8866
8730
|
const teamId = await resolveResourceEventTeamId();
|
|
8867
8731
|
if (!teamId) {
|
|
@@ -8909,20 +8773,11 @@ async function createApp(options) {
|
|
|
8909
8773
|
);
|
|
8910
8774
|
}
|
|
8911
8775
|
pluginRoutes = getPluginRoutes({ resourceEvents });
|
|
8912
|
-
validateDashboardRouteOwnership({ dashboard, routes: pluginRoutes });
|
|
8913
8776
|
if (dashboard && !dashboard.disabled) {
|
|
8914
8777
|
pluginApiRoutes = getPluginApiRoutes();
|
|
8915
8778
|
}
|
|
8916
8779
|
} catch (error) {
|
|
8917
|
-
|
|
8918
|
-
setPlugins(previousPlugins);
|
|
8919
|
-
setConfigDefaults(previousConfigDefaults);
|
|
8920
|
-
botConfig.defaultProfile = previousDefaultProfile;
|
|
8921
|
-
botConfig.profiles = previousModelProfiles;
|
|
8922
|
-
setSlackReactionConfig(previousSlackReactionConfig);
|
|
8923
|
-
setSandboxResourceConfig(previousSandboxResources);
|
|
8924
|
-
setExperimentalFeatures(previousExperimentalFeatures);
|
|
8925
|
-
setDashboardConversationLinkOptions(previousDashboardLinkOptions);
|
|
8780
|
+
restoreRuntimeConfig();
|
|
8926
8781
|
throw error;
|
|
8927
8782
|
}
|
|
8928
8783
|
const waitUntil = options?.waitUntil ?? await defaultWaitUntil();
|
|
@@ -8938,6 +8793,54 @@ async function createApp(options) {
|
|
|
8938
8793
|
replyExecutor: { agentRunner },
|
|
8939
8794
|
sandbox: { tracePropagation }
|
|
8940
8795
|
};
|
|
8796
|
+
let conversationWorkOptions;
|
|
8797
|
+
const getConversationWorkOptions = () => {
|
|
8798
|
+
conversationWorkOptions ??= options?.conversationWork ?? createProductionConversationWorkOptions({
|
|
8799
|
+
agentRunner,
|
|
8800
|
+
services: runtimeServiceOverrides
|
|
8801
|
+
});
|
|
8802
|
+
return conversationWorkOptions;
|
|
8803
|
+
};
|
|
8804
|
+
let adapterRoutes = [];
|
|
8805
|
+
let authenticatedRoutes = [];
|
|
8806
|
+
try {
|
|
8807
|
+
const adapterOutputs = await Promise.all(
|
|
8808
|
+
(options?.adapters ?? []).map(async (adapter) => {
|
|
8809
|
+
const work = getConversationWorkOptions();
|
|
8810
|
+
const state = work.state ?? getStateAdapter();
|
|
8811
|
+
return await adapter({
|
|
8812
|
+
agentName: botConfig.userName,
|
|
8813
|
+
baseURL: resolveAdapterBaseURL(dashboard),
|
|
8814
|
+
conversations: createAdapterConversations({
|
|
8815
|
+
conversationStore: work.conversationStore,
|
|
8816
|
+
eventStore: getConversationEventStore(),
|
|
8817
|
+
queue: work.queue ?? getVercelConversationWorkQueue(),
|
|
8818
|
+
state
|
|
8819
|
+
}),
|
|
8820
|
+
reportError: (error, event, attributes) => void logException(error, event, attributes),
|
|
8821
|
+
state,
|
|
8822
|
+
version: JUNIOR_VERSION
|
|
8823
|
+
});
|
|
8824
|
+
})
|
|
8825
|
+
);
|
|
8826
|
+
adapterRoutes = adapterOutputs.flatMap((output) => output.routes ?? []);
|
|
8827
|
+
authenticatedRoutes = adapterOutputs.flatMap(
|
|
8828
|
+
(output) => output.authenticatedRoutes ?? []
|
|
8829
|
+
);
|
|
8830
|
+
if (authenticatedRoutes.length > 0 && (!dashboard || dashboard.disabled)) {
|
|
8831
|
+
throw new Error(
|
|
8832
|
+
"createApp() adapters with authenticated routes require an enabled dashboard"
|
|
8833
|
+
);
|
|
8834
|
+
}
|
|
8835
|
+
validateDashboardRouteOwnership({
|
|
8836
|
+
authenticatedRoutes,
|
|
8837
|
+
dashboard,
|
|
8838
|
+
routes: pluginRoutes
|
|
8839
|
+
});
|
|
8840
|
+
} catch (error) {
|
|
8841
|
+
restoreRuntimeConfig();
|
|
8842
|
+
throw error;
|
|
8843
|
+
}
|
|
8941
8844
|
const slackWebhookServices = createProductionSlackWebhookServices({
|
|
8942
8845
|
services: runtimeServiceOverrides
|
|
8943
8846
|
});
|
|
@@ -8954,9 +8857,11 @@ async function createApp(options) {
|
|
|
8954
8857
|
);
|
|
8955
8858
|
});
|
|
8956
8859
|
mountRoutes(app, pluginRoutes);
|
|
8860
|
+
mountRoutes(app, adapterRoutes);
|
|
8957
8861
|
mountRoutes(
|
|
8958
8862
|
app,
|
|
8959
8863
|
await createDashboardRouteRegistrations({
|
|
8864
|
+
authenticatedRoutes,
|
|
8960
8865
|
dashboard,
|
|
8961
8866
|
createDashboardApp: virtualConfig?.createDashboardApp,
|
|
8962
8867
|
pluginRoutes: pluginApiRoutes
|
|
@@ -8994,32 +8899,6 @@ async function createApp(options) {
|
|
|
8994
8899
|
});
|
|
8995
8900
|
let agentContinuePOST;
|
|
8996
8901
|
let pluginTaskPOST;
|
|
8997
|
-
let conversationWorkOptions;
|
|
8998
|
-
const getConversationWorkOptions = () => {
|
|
8999
|
-
conversationWorkOptions ??= options?.conversationWork ?? createProductionConversationWorkOptions({
|
|
9000
|
-
agentRunner,
|
|
9001
|
-
services: runtimeServiceOverrides
|
|
9002
|
-
});
|
|
9003
|
-
return conversationWorkOptions;
|
|
9004
|
-
};
|
|
9005
|
-
if (isExperimentalFeatureEnabled("acp")) {
|
|
9006
|
-
const work = getConversationWorkOptions();
|
|
9007
|
-
const cancellation = work.apiTurnCancellation;
|
|
9008
|
-
if (!cancellation) {
|
|
9009
|
-
throw new Error("Experimental ACP requires API Turn cancellation wiring");
|
|
9010
|
-
}
|
|
9011
|
-
const handleAcpRequest = createAcpHttpHandler({
|
|
9012
|
-
cancellation,
|
|
9013
|
-
conversationStore: work.conversationStore,
|
|
9014
|
-
queue: work.queue ?? getVercelConversationWorkQueue(),
|
|
9015
|
-
state: work.state
|
|
9016
|
-
});
|
|
9017
|
-
app.on(
|
|
9018
|
-
["GET", "POST", "DELETE"],
|
|
9019
|
-
"/api/acp",
|
|
9020
|
-
(c) => handleAcpRequest(c.req.raw)
|
|
9021
|
-
);
|
|
9022
|
-
}
|
|
9023
8902
|
if (process.env.NODE_ENV === "development") {
|
|
9024
8903
|
registerVercelConversationWorkDevConsumer(getConversationWorkOptions());
|
|
9025
8904
|
registerVercelPluginTaskDevConsumer();
|