replicas-engine 0.1.1028 → 0.1.1030
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/src/{asp-host-A57BJZPM.js → asp-host-5HX6D4TL.js} +5 -5
- package/dist/src/{chunk-DU4QTHOX.js → chunk-27OEXGGC.js} +6 -6
- package/dist/src/{chunk-BFHGBJO2.js → chunk-5HLMUJTJ.js} +45 -5
- package/dist/src/{chunk-CFLUSFBP.js → chunk-7PXLG7IJ.js} +1 -1
- package/dist/src/{chunk-3OGTHVR4.js → chunk-ABUMJRPU.js} +1 -1
- package/dist/src/{chunk-AWQZGS2I.js → chunk-ADUHQPYR.js} +3 -3
- package/dist/src/{chunk-LY4WTFXS.js → chunk-NGZ6IR76.js} +3 -3
- package/dist/src/{chunk-OK37MIB6.js → chunk-RVXD24D4.js} +1 -1
- package/dist/src/command-protection-hook.js +4 -4
- package/dist/src/headless-agent.js +3 -3
- package/dist/src/index.js +284 -67
- package/dist/src/post-tool-pr-hook.js +2 -2
- package/dist/src/subagent-mcp.js +1 -1
- package/package.json +1 -1
|
@@ -5,12 +5,12 @@ import {
|
|
|
5
5
|
getCodexAspHost,
|
|
6
6
|
restartCodexAspHost,
|
|
7
7
|
restartCodexAspHostIfRunning
|
|
8
|
-
} from "./chunk-
|
|
9
|
-
import "./chunk-
|
|
10
|
-
import "./chunk-
|
|
11
|
-
import "./chunk-
|
|
8
|
+
} from "./chunk-27OEXGGC.js";
|
|
9
|
+
import "./chunk-RVXD24D4.js";
|
|
10
|
+
import "./chunk-NGZ6IR76.js";
|
|
11
|
+
import "./chunk-7PXLG7IJ.js";
|
|
12
12
|
import "./chunk-UZSNFLDQ.js";
|
|
13
|
-
import "./chunk-
|
|
13
|
+
import "./chunk-5HLMUJTJ.js";
|
|
14
14
|
import "./chunk-VEQXQN22.js";
|
|
15
15
|
export {
|
|
16
16
|
getCodexAspHost,
|
|
@@ -5,15 +5,15 @@ import {
|
|
|
5
5
|
ENGINE_ENV,
|
|
6
6
|
monolithRequest,
|
|
7
7
|
setAgentCredentialSnapshot
|
|
8
|
-
} from "./chunk-
|
|
8
|
+
} from "./chunk-RVXD24D4.js";
|
|
9
9
|
import {
|
|
10
10
|
AppServerProcess,
|
|
11
11
|
buildCodexAgentEnv
|
|
12
|
-
} from "./chunk-
|
|
12
|
+
} from "./chunk-NGZ6IR76.js";
|
|
13
13
|
import {
|
|
14
14
|
SUBPROCESS_MAX_BUFFER,
|
|
15
15
|
execFileAsync
|
|
16
|
-
} from "./chunk-
|
|
16
|
+
} from "./chunk-7PXLG7IJ.js";
|
|
17
17
|
import {
|
|
18
18
|
isRecord
|
|
19
19
|
} from "./chunk-UZSNFLDQ.js";
|
|
@@ -28,7 +28,7 @@ import {
|
|
|
28
28
|
listOpenAICompatibleModels,
|
|
29
29
|
readOllamaAuthEnv,
|
|
30
30
|
resolveOpenAICompatibleModelsUrl
|
|
31
|
-
} from "./chunk-
|
|
31
|
+
} from "./chunk-5HLMUJTJ.js";
|
|
32
32
|
|
|
33
33
|
// src/managers/codex-token-manager.ts
|
|
34
34
|
import { promises as fs } from "fs";
|
|
@@ -264,7 +264,7 @@ var CodexTokenManager = class extends BaseRefreshManager {
|
|
|
264
264
|
await this.applyCredentialUpdate(++this.credentialGeneration, async () => {
|
|
265
265
|
await this.applyCredentialsResponse(data);
|
|
266
266
|
setAgentCredentialSnapshot("codex", data);
|
|
267
|
-
const { restartCodexAspHostIfRunning: restartCodexAspHostIfRunning2 } = await import("./asp-host-
|
|
267
|
+
const { restartCodexAspHostIfRunning: restartCodexAspHostIfRunning2 } = await import("./asp-host-5HX6D4TL.js");
|
|
268
268
|
await restartCodexAspHostIfRunning2();
|
|
269
269
|
});
|
|
270
270
|
await this.start(true);
|
|
@@ -285,7 +285,7 @@ var CodexTokenManager = class extends BaseRefreshManager {
|
|
|
285
285
|
const accountChanged = ENGINE_ENV.REPLICAS_AGENT_CREDENTIALS.codex?.credentialId !== data.credentialId;
|
|
286
286
|
await this.applyCredentialsResponse(data);
|
|
287
287
|
if (restartOnChange && (accountChanged || CODEX_AUTH_ENV_KEYS.some((key, index) => process.env[key] !== previousEnv[index]))) {
|
|
288
|
-
const { restartCodexAspHostIfRunning: restartCodexAspHostIfRunning2 } = await import("./asp-host-
|
|
288
|
+
const { restartCodexAspHostIfRunning: restartCodexAspHostIfRunning2 } = await import("./asp-host-5HX6D4TL.js");
|
|
289
289
|
await restartCodexAspHostIfRunning2();
|
|
290
290
|
}
|
|
291
291
|
setAgentCredentialSnapshot("codex", data);
|
|
@@ -1258,7 +1258,8 @@ var sendChatMessageRequestSchema = z3.object({
|
|
|
1258
1258
|
senderDisplayName: z3.string().optional(),
|
|
1259
1259
|
senderAvatarUrl: z3.string().optional(),
|
|
1260
1260
|
errorNotificationTarget: integrationErrorNotificationTargetSchema.optional(),
|
|
1261
|
-
errorNotificationTargets: z3.array(integrationErrorNotificationTargetSchema).optional()
|
|
1261
|
+
errorNotificationTargets: z3.array(integrationErrorNotificationTargetSchema).optional(),
|
|
1262
|
+
streamSlackActivity: z3.boolean().optional()
|
|
1262
1263
|
}).passthrough();
|
|
1263
1264
|
function isChatMessageSender(value) {
|
|
1264
1265
|
return isRecord(value) && (value.messageId === void 0 || typeof value.messageId === "string") && typeof value.senderUserId === "string" && typeof value.senderEmail === "string" && typeof value.recordedAt === "string";
|
|
@@ -1548,6 +1549,19 @@ var mcpWorkloadAuthSchema = z4.strictObject({
|
|
|
1548
1549
|
type: z4.literal("workspace_identity"),
|
|
1549
1550
|
audience: workspaceAudienceSchema
|
|
1550
1551
|
});
|
|
1552
|
+
var mcpAuthSchema = z4.discriminatedUnion("type", [
|
|
1553
|
+
mcpWorkloadAuthSchema,
|
|
1554
|
+
z4.strictObject({ type: z4.literal("oauth") })
|
|
1555
|
+
]);
|
|
1556
|
+
var engineMcpOAuthTokenRequestSchema = z4.object({
|
|
1557
|
+
environment_mcp_id: z4.string().uuid(),
|
|
1558
|
+
force_refresh: z4.boolean().optional()
|
|
1559
|
+
});
|
|
1560
|
+
var engineMcpOAuthTokenResponseSchema = z4.object({
|
|
1561
|
+
url: z4.string(),
|
|
1562
|
+
access_token: z4.string(),
|
|
1563
|
+
expires_at: z4.string().nullable()
|
|
1564
|
+
});
|
|
1551
1565
|
|
|
1552
1566
|
// ../shared/src/runtime-env.ts
|
|
1553
1567
|
var REPLICAS_RUNTIME_ENV_ALIASES = {
|
|
@@ -2748,15 +2762,30 @@ function createUuidFromHex(value) {
|
|
|
2748
2762
|
}
|
|
2749
2763
|
var UUID_RE = /^[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}$/i;
|
|
2750
2764
|
|
|
2765
|
+
// ../shared/src/automations/github/index.ts
|
|
2766
|
+
var REVIEW_REQUESTED_EVENT = "pull_request.review_requested";
|
|
2767
|
+
|
|
2751
2768
|
// ../shared/src/automations/trigger-schemas.ts
|
|
2769
|
+
function getReviewerLoginsError(event, logins) {
|
|
2770
|
+
const isReviewRequested = event === REVIEW_REQUESTED_EVENT;
|
|
2771
|
+
if (isReviewRequested === !!logins?.some((login) => login.trim().replace(/^@+/, ""))) return null;
|
|
2772
|
+
return isReviewRequested ? "The PR review requested trigger needs at least one GitHub username" : "Requested reviewers only apply to the PR review requested trigger";
|
|
2773
|
+
}
|
|
2752
2774
|
var repositoryTriggerConfigSchema = z10.object({
|
|
2753
2775
|
event: z10.string(),
|
|
2754
2776
|
repository_ids: z10.array(z10.string().regex(UUID_RE, "must be a repository id")).optional(),
|
|
2755
2777
|
group_pr_events: z10.boolean().optional(),
|
|
2756
|
-
excluded_actors: z10.array(z10.string()).optional()
|
|
2778
|
+
excluded_actors: z10.array(z10.string()).optional(),
|
|
2779
|
+
reviewer_logins: z10.array(z10.string()).optional()
|
|
2757
2780
|
});
|
|
2758
2781
|
var cronTriggerSchema = z10.object({ type: z10.literal("cron"), config: z10.object({ schedule: z10.string(), timezone: z10.string().optional() }) });
|
|
2759
|
-
var githubTriggerSchema = z10.object({
|
|
2782
|
+
var githubTriggerSchema = z10.object({
|
|
2783
|
+
type: z10.literal("github"),
|
|
2784
|
+
config: repositoryTriggerConfigSchema.superRefine((config, ctx) => {
|
|
2785
|
+
const message2 = getReviewerLoginsError(config.event, config.reviewer_logins);
|
|
2786
|
+
if (message2) ctx.addIssue({ code: "custom", message: message2, path: ["reviewer_logins"] });
|
|
2787
|
+
})
|
|
2788
|
+
});
|
|
2760
2789
|
var gitlabTriggerSchema = z10.object({ type: z10.literal("gitlab"), config: repositoryTriggerConfigSchema });
|
|
2761
2790
|
var automationTriggerSchema = z10.discriminatedUnion("type", [
|
|
2762
2791
|
cronTriggerSchema,
|
|
@@ -2776,7 +2805,7 @@ var createEnvironmentMcpRequestSchema = z11.object({
|
|
|
2776
2805
|
transport: z11.enum(ENVIRONMENT_MCP_TRANSPORTS),
|
|
2777
2806
|
config: z11.union([
|
|
2778
2807
|
z11.object({ command: z11.string().min(1), args: z11.array(z11.string()).optional(), env: stringMap.optional() }),
|
|
2779
|
-
z11.object({ url: z11.url(), headers: stringMap.optional(), auth:
|
|
2808
|
+
z11.object({ url: z11.url(), headers: stringMap.optional(), auth: mcpAuthSchema.optional() })
|
|
2780
2809
|
]).describe("stdio: `{ command, args, env }`. http/sse: `{ url, headers }`.")
|
|
2781
2810
|
});
|
|
2782
2811
|
var updateEnvironmentMcpRequestSchema = createEnvironmentMcpRequestSchema.partial();
|
|
@@ -3377,7 +3406,7 @@ Trigger shapes:
|
|
|
3377
3406
|
{ "type": "cron", "config": { "schedule": "0 9 * * 1-5", "timezone": "UTC" } }
|
|
3378
3407
|
\`\`\`
|
|
3379
3408
|
|
|
3380
|
-
GitHub events: \`pull_request.opened\`, \`pull_request.synchronize\`, \`pull_request.merged\`, \`pull_request.closed\`. GitLab events: \`merge_request.opened\`, \`merge_request.updated\`, \`merge_request.merged\`, \`merge_request.closed\`. Use one trigger type family per automation and pick the code host the repositories actually live on.
|
|
3409
|
+
GitHub events: \`pull_request.opened\`, \`pull_request.synchronize\`, \`pull_request.review_requested\` (requires a \`reviewer_logins\` list of GitHub usernames), \`pull_request.merged\`, \`pull_request.closed\`. GitLab events: \`merge_request.opened\`, \`merge_request.updated\`, \`merge_request.merged\`, \`merge_request.closed\`. Use one trigger type family per automation and pick the code host the repositories actually live on.
|
|
3381
3410
|
|
|
3382
3411
|
Test the hooks before proposing them: run the drafted warm hook and start hook scripts in this workspace (from \`~/workspaces\`) and fix the earliest failure until both exit 0 on a second run.
|
|
3383
3412
|
|
|
@@ -6456,6 +6485,11 @@ function parseClaudeEvents(events, parentToolUseId) {
|
|
|
6456
6485
|
const completedStreamIds = /* @__PURE__ */ new Set();
|
|
6457
6486
|
const supersededStreamIds = /* @__PURE__ */ new Set();
|
|
6458
6487
|
let liveStreamId = null;
|
|
6488
|
+
const endStreamingTools = (exceptStreamId) => {
|
|
6489
|
+
for (const streamId of streamingTools.keys()) {
|
|
6490
|
+
if (streamId !== exceptStreamId) streamingTools.delete(streamId);
|
|
6491
|
+
}
|
|
6492
|
+
};
|
|
6459
6493
|
let compaction;
|
|
6460
6494
|
const assistantThinking = /* @__PURE__ */ new Map();
|
|
6461
6495
|
const assistantTextCounts = /* @__PURE__ */ new Map();
|
|
@@ -6509,6 +6543,7 @@ function parseClaudeEvents(events, parentToolUseId) {
|
|
|
6509
6543
|
supersededStreamIds.add(liveStreamId);
|
|
6510
6544
|
}
|
|
6511
6545
|
liveStreamId = payload.streamId;
|
|
6546
|
+
endStreamingTools(payload.streamId);
|
|
6512
6547
|
const existing = partialIndexes.get(payload.streamId) ?? {};
|
|
6513
6548
|
if (payload.thinking && !assistantThinking.has(payload.streamId)) {
|
|
6514
6549
|
const reasoningMessage = {
|
|
@@ -6606,6 +6641,7 @@ function parseClaudeEvents(events, parentToolUseId) {
|
|
|
6606
6641
|
}
|
|
6607
6642
|
const streamRefs = messageId ? partialIndexes.get(messageId) : void 0;
|
|
6608
6643
|
if (messageId) {
|
|
6644
|
+
endStreamingTools(messageId);
|
|
6609
6645
|
if (liveStreamId !== null && liveStreamId !== messageId) {
|
|
6610
6646
|
supersededStreamIds.add(liveStreamId);
|
|
6611
6647
|
}
|
|
@@ -6720,6 +6756,7 @@ function parseClaudeEvents(events, parentToolUseId) {
|
|
|
6720
6756
|
}
|
|
6721
6757
|
});
|
|
6722
6758
|
}
|
|
6759
|
+
if (event.type === "claude-result" || event.type === CHAT_INTERRUPTED_EVENT_TYPE) endStreamingTools();
|
|
6723
6760
|
if (compaction && (event.type === "claude-result" || event.type === CHAT_INTERRUPTED_EVENT_TYPE)) {
|
|
6724
6761
|
compaction.status = "failed";
|
|
6725
6762
|
compaction.completedAt = event.timestamp;
|
|
@@ -9339,6 +9376,8 @@ export {
|
|
|
9339
9376
|
chatHistoryPageParamsFromQuery,
|
|
9340
9377
|
paginateChatHistory,
|
|
9341
9378
|
coerceBackgroundTaskPayload,
|
|
9379
|
+
planItemsFromMessage,
|
|
9380
|
+
getDisplayMessageActivity,
|
|
9342
9381
|
fileContentDiff,
|
|
9343
9382
|
skillNamesFromCommand,
|
|
9344
9383
|
areUserMessagesWithinMatchWindow,
|
|
@@ -9358,6 +9397,7 @@ export {
|
|
|
9358
9397
|
workspaceTokenRequestSchema,
|
|
9359
9398
|
workspaceTokenResponseSchema,
|
|
9360
9399
|
legacyWorkspaceTokenBundleSchema,
|
|
9400
|
+
engineMcpOAuthTokenResponseSchema,
|
|
9361
9401
|
SANDBOX_SKILL_DIRS,
|
|
9362
9402
|
HISTORY_ROOT,
|
|
9363
9403
|
HISTORY_INDEX_FILENAME,
|
|
@@ -3,7 +3,7 @@ import { createRequire as __createRequire } from 'node:module';
|
|
|
3
3
|
const require = __createRequire(import.meta.url);
|
|
4
4
|
import {
|
|
5
5
|
HOOK_EXEC_MAX_BUFFER_BYTES
|
|
6
|
-
} from "./chunk-
|
|
6
|
+
} from "./chunk-5HLMUJTJ.js";
|
|
7
7
|
|
|
8
8
|
// src/utils/exec.ts
|
|
9
9
|
import { exec, execFile } from "child_process";
|
|
@@ -3,18 +3,18 @@ import { createRequire as __createRequire } from 'node:module';
|
|
|
3
3
|
const require = __createRequire(import.meta.url);
|
|
4
4
|
import {
|
|
5
5
|
monolithRequest
|
|
6
|
-
} from "./chunk-
|
|
6
|
+
} from "./chunk-RVXD24D4.js";
|
|
7
7
|
import {
|
|
8
8
|
SUBPROCESS_MAX_BUFFER,
|
|
9
9
|
execFileAsync
|
|
10
|
-
} from "./chunk-
|
|
10
|
+
} from "./chunk-7PXLG7IJ.js";
|
|
11
11
|
import {
|
|
12
12
|
extractCommandProtectionCommandText,
|
|
13
13
|
findCommandProtectionGitLookups,
|
|
14
14
|
findGitCommitSignals,
|
|
15
15
|
findPrMergeSignals,
|
|
16
16
|
parseCommandProtectionRequest
|
|
17
|
-
} from "./chunk-
|
|
17
|
+
} from "./chunk-5HLMUJTJ.js";
|
|
18
18
|
|
|
19
19
|
// src/services/command-protection-service.ts
|
|
20
20
|
import { readFile, stat } from "fs/promises";
|
|
@@ -3,10 +3,10 @@ import { createRequire as __createRequire } from 'node:module';
|
|
|
3
3
|
const require = __createRequire(import.meta.url);
|
|
4
4
|
import {
|
|
5
5
|
execFileAsync
|
|
6
|
-
} from "./chunk-
|
|
6
|
+
} from "./chunk-7PXLG7IJ.js";
|
|
7
7
|
import {
|
|
8
8
|
isVersionBelow
|
|
9
|
-
} from "./chunk-
|
|
9
|
+
} from "./chunk-5HLMUJTJ.js";
|
|
10
10
|
|
|
11
11
|
// src/utils/codex-agent-env.ts
|
|
12
12
|
function buildCodexAgentEnv(source = process.env) {
|
|
@@ -240,7 +240,7 @@ function getCodexModelProvider(method) {
|
|
|
240
240
|
if (method === "foundry") return "azure";
|
|
241
241
|
return method === "ollama" || method === "openai-compatible" ? "replicas_openai_compatible" : "openai";
|
|
242
242
|
}
|
|
243
|
-
var ENGINE_PACKAGE_VERSION = "0.1.
|
|
243
|
+
var ENGINE_PACKAGE_VERSION = "0.1.1030";
|
|
244
244
|
var INITIALIZE_METHOD = "initialize";
|
|
245
245
|
var INITIALIZED_NOTIFICATION = "initialized";
|
|
246
246
|
var ACCOUNT_LOGIN_START_METHOD = "account/login/start";
|
|
@@ -3,13 +3,13 @@ import { createRequire as __createRequire } from 'node:module';
|
|
|
3
3
|
const require = __createRequire(import.meta.url);
|
|
4
4
|
import {
|
|
5
5
|
evaluateCommandProtection
|
|
6
|
-
} from "./chunk-
|
|
7
|
-
import "./chunk-
|
|
8
|
-
import "./chunk-
|
|
6
|
+
} from "./chunk-ADUHQPYR.js";
|
|
7
|
+
import "./chunk-RVXD24D4.js";
|
|
8
|
+
import "./chunk-7PXLG7IJ.js";
|
|
9
9
|
import {
|
|
10
10
|
isRecord
|
|
11
11
|
} from "./chunk-UZSNFLDQ.js";
|
|
12
|
-
import "./chunk-
|
|
12
|
+
import "./chunk-5HLMUJTJ.js";
|
|
13
13
|
import "./chunk-VEQXQN22.js";
|
|
14
14
|
|
|
15
15
|
// src/command-protection-hook.ts
|
|
@@ -7,12 +7,12 @@ import {
|
|
|
7
7
|
import {
|
|
8
8
|
AppServerProcess,
|
|
9
9
|
buildCodexAgentEnv
|
|
10
|
-
} from "./chunk-
|
|
11
|
-
import "./chunk-
|
|
10
|
+
} from "./chunk-NGZ6IR76.js";
|
|
11
|
+
import "./chunk-7PXLG7IJ.js";
|
|
12
12
|
import {
|
|
13
13
|
AGENT,
|
|
14
14
|
headlessAgentRequestSchema
|
|
15
|
-
} from "./chunk-
|
|
15
|
+
} from "./chunk-5HLMUJTJ.js";
|
|
16
16
|
import "./chunk-VEQXQN22.js";
|
|
17
17
|
|
|
18
18
|
// src/headless-agent.ts
|
package/dist/src/index.js
CHANGED
|
@@ -32,7 +32,7 @@ import {
|
|
|
32
32
|
reportCommandProtectionBlock,
|
|
33
33
|
resolveDiffBase,
|
|
34
34
|
runGitCommand
|
|
35
|
-
} from "./chunk-
|
|
35
|
+
} from "./chunk-ADUHQPYR.js";
|
|
36
36
|
import {
|
|
37
37
|
ACCOUNT_RATE_LIMITS_UPDATED_METHOD,
|
|
38
38
|
AGENT_MESSAGE_DELTA_METHOD,
|
|
@@ -57,7 +57,7 @@ import {
|
|
|
57
57
|
} from "./chunk-P73LGPQO.js";
|
|
58
58
|
import {
|
|
59
59
|
publishedPullRequestUrls
|
|
60
|
-
} from "./chunk-
|
|
60
|
+
} from "./chunk-ABUMJRPU.js";
|
|
61
61
|
import {
|
|
62
62
|
BaseRefreshManager,
|
|
63
63
|
CodexAspAuthMethodChangedError,
|
|
@@ -71,7 +71,7 @@ import {
|
|
|
71
71
|
refreshDelayMs,
|
|
72
72
|
restartCodexAspHost,
|
|
73
73
|
routineRefreshRequest
|
|
74
|
-
} from "./chunk-
|
|
74
|
+
} from "./chunk-27OEXGGC.js";
|
|
75
75
|
import {
|
|
76
76
|
ENGINE_ENV,
|
|
77
77
|
monolithRequest,
|
|
@@ -79,16 +79,16 @@ import {
|
|
|
79
79
|
readRuntimeEnvFile,
|
|
80
80
|
reloadEngineEnv,
|
|
81
81
|
setAgentCredentialSnapshot
|
|
82
|
-
} from "./chunk-
|
|
82
|
+
} from "./chunk-RVXD24D4.js";
|
|
83
83
|
import {
|
|
84
84
|
AspClient,
|
|
85
85
|
getCodexModelProvider
|
|
86
|
-
} from "./chunk-
|
|
86
|
+
} from "./chunk-NGZ6IR76.js";
|
|
87
87
|
import {
|
|
88
88
|
SUBPROCESS_MAX_BUFFER,
|
|
89
89
|
execAsync,
|
|
90
90
|
execFileAsync
|
|
91
|
-
} from "./chunk-
|
|
91
|
+
} from "./chunk-7PXLG7IJ.js";
|
|
92
92
|
import {
|
|
93
93
|
isRecord as isRecord2
|
|
94
94
|
} from "./chunk-UZSNFLDQ.js";
|
|
@@ -218,6 +218,7 @@ import {
|
|
|
218
218
|
detectAgentQuotaLimit,
|
|
219
219
|
detectEnvironmentAuthMethod,
|
|
220
220
|
detectLanguageByPath,
|
|
221
|
+
engineMcpOAuthTokenResponseSchema,
|
|
221
222
|
excludeQueuedAcceptedEvents,
|
|
222
223
|
extractErrorText,
|
|
223
224
|
extractFinalResponse,
|
|
@@ -232,6 +233,7 @@ import {
|
|
|
232
233
|
getClaudeModelContextWindow,
|
|
233
234
|
getDefaultAgentModel,
|
|
234
235
|
getDefaultOllamaModel,
|
|
236
|
+
getDisplayMessageActivity,
|
|
235
237
|
getEventStreamId,
|
|
236
238
|
getEventTimestampMs,
|
|
237
239
|
getGitHubAccessToken,
|
|
@@ -293,6 +295,7 @@ import {
|
|
|
293
295
|
parseMcpToolName,
|
|
294
296
|
parseReplicasConfigString,
|
|
295
297
|
percentage,
|
|
298
|
+
planItemsFromMessage,
|
|
296
299
|
raceWithTimeout,
|
|
297
300
|
readJsonlPage,
|
|
298
301
|
readOllamaAuthEnv,
|
|
@@ -318,7 +321,7 @@ import {
|
|
|
318
321
|
workspaceTokenRequestSchema,
|
|
319
322
|
workspaceTokenResponseSchema,
|
|
320
323
|
wrapInTag
|
|
321
|
-
} from "./chunk-
|
|
324
|
+
} from "./chunk-5HLMUJTJ.js";
|
|
322
325
|
import {
|
|
323
326
|
cloneMcpConfig,
|
|
324
327
|
ensureCompatibilityImports,
|
|
@@ -9636,6 +9639,41 @@ async function applyInfisicalCredentials(data, paths) {
|
|
|
9636
9639
|
}
|
|
9637
9640
|
var infisicalTokenManager = new InfisicalTokenManager();
|
|
9638
9641
|
|
|
9642
|
+
// src/token-cache.ts
|
|
9643
|
+
var TokenCache = class {
|
|
9644
|
+
constructor(maxEntries = Infinity) {
|
|
9645
|
+
this.maxEntries = maxEntries;
|
|
9646
|
+
}
|
|
9647
|
+
maxEntries;
|
|
9648
|
+
cache = /* @__PURE__ */ new Map();
|
|
9649
|
+
inflight = /* @__PURE__ */ new Map();
|
|
9650
|
+
get(key, load, force = false) {
|
|
9651
|
+
const cached = this.cache.get(key);
|
|
9652
|
+
if (!force && cached && cached.refreshAt > Date.now()) return Promise.resolve(createSuccessResult(cached.token));
|
|
9653
|
+
const inflightKey = force ? `${key}\0force` : key;
|
|
9654
|
+
let pending = this.inflight.get(inflightKey);
|
|
9655
|
+
if (!pending) {
|
|
9656
|
+
pending = load().then((result) => {
|
|
9657
|
+
this.cache.delete(key);
|
|
9658
|
+
if (!result.ok) return result;
|
|
9659
|
+
const oldest = this.cache.keys().next();
|
|
9660
|
+
if (this.cache.size >= this.maxEntries && !oldest.done) this.cache.delete(oldest.value);
|
|
9661
|
+
this.cache.set(key, result.data);
|
|
9662
|
+
return createSuccessResult(result.data.token);
|
|
9663
|
+
}).finally(() => this.inflight.delete(inflightKey));
|
|
9664
|
+
this.inflight.set(inflightKey, pending);
|
|
9665
|
+
}
|
|
9666
|
+
return pending;
|
|
9667
|
+
}
|
|
9668
|
+
};
|
|
9669
|
+
async function requestToken(request, path7, body, failureMessage) {
|
|
9670
|
+
try {
|
|
9671
|
+
return createSuccessResult(await request(path7, { body }));
|
|
9672
|
+
} catch (error) {
|
|
9673
|
+
return createErrorResult({ message: error instanceof Error ? error.message : failureMessage, code: 503 });
|
|
9674
|
+
}
|
|
9675
|
+
}
|
|
9676
|
+
|
|
9639
9677
|
// src/workspace-identity-tokens.ts
|
|
9640
9678
|
var MIN_REMAINING_MS = 5 * 60 * 1e3;
|
|
9641
9679
|
var MAX_CACHED_AUDIENCES = 32;
|
|
@@ -9644,30 +9682,19 @@ var WorkspaceIdentityTokens = class {
|
|
|
9644
9682
|
this.request = request;
|
|
9645
9683
|
}
|
|
9646
9684
|
request;
|
|
9647
|
-
|
|
9648
|
-
inflight = /* @__PURE__ */ new Map();
|
|
9685
|
+
tokens = new TokenCache(MAX_CACHED_AUDIENCES);
|
|
9649
9686
|
async get(audience = WORKSPACE_IDENTITY_AUDIENCE, awsSourceIdentity = false) {
|
|
9650
9687
|
const parsed = workspaceAudienceSchema.safeParse(audience);
|
|
9651
9688
|
if (!parsed.success) {
|
|
9652
9689
|
return createErrorResult({ message: parsed.error.issues[0]?.message ?? "Invalid audience", code: 400 });
|
|
9653
9690
|
}
|
|
9654
9691
|
const key = awsSourceIdentity ? `${audience} aws_source_identity` : audience;
|
|
9655
|
-
|
|
9656
|
-
if (cached && Date.parse(cached.expires_at) - Date.now() > MIN_REMAINING_MS) return createSuccessResult(cached);
|
|
9657
|
-
let pending = this.inflight.get(key);
|
|
9658
|
-
if (!pending) {
|
|
9659
|
-
pending = this.mint(audience, awsSourceIdentity, key).finally(() => this.inflight.delete(key));
|
|
9660
|
-
this.inflight.set(key, pending);
|
|
9661
|
-
}
|
|
9662
|
-
return pending;
|
|
9692
|
+
return this.tokens.get(key, () => this.mint(audience, awsSourceIdentity));
|
|
9663
9693
|
}
|
|
9664
|
-
async mint(audience, awsSourceIdentity
|
|
9665
|
-
|
|
9666
|
-
|
|
9667
|
-
|
|
9668
|
-
} catch (error) {
|
|
9669
|
-
return createErrorResult({ message: error instanceof Error ? error.message : "Workspace identity request failed", code: 503 });
|
|
9670
|
-
}
|
|
9694
|
+
async mint(audience, awsSourceIdentity) {
|
|
9695
|
+
const requested = await requestToken(this.request, "/v1/engine/workspace-identity/token", { audience, aws_source_identity: awsSourceIdentity }, "Workspace identity request failed");
|
|
9696
|
+
if (!requested.ok) return requested;
|
|
9697
|
+
const response = requested.data;
|
|
9671
9698
|
if (!response.ok) {
|
|
9672
9699
|
return createErrorResult({ message: `Workspace identity request failed: ${response.status} ${await response.text()}`, code: response.status === 400 ? 400 : 503 });
|
|
9673
9700
|
}
|
|
@@ -9687,11 +9714,7 @@ var WorkspaceIdentityTokens = class {
|
|
|
9687
9714
|
return createErrorResult({ message: "AWS source identity is unavailable from this Replicas version", code: 503 });
|
|
9688
9715
|
}
|
|
9689
9716
|
}
|
|
9690
|
-
|
|
9691
|
-
const oldest = this.cache.keys().next();
|
|
9692
|
-
if (this.cache.size >= MAX_CACHED_AUDIENCES && !oldest.done) this.cache.delete(oldest.value);
|
|
9693
|
-
this.cache.set(key, token);
|
|
9694
|
-
return createSuccessResult(token);
|
|
9717
|
+
return createSuccessResult({ token, refreshAt: Date.parse(token.expires_at) - MIN_REMAINING_MS });
|
|
9695
9718
|
}
|
|
9696
9719
|
};
|
|
9697
9720
|
var workspaceIdentityTokens = new WorkspaceIdentityTokens();
|
|
@@ -9729,27 +9752,85 @@ function resolveIdentityRoute(requestUrl) {
|
|
|
9729
9752
|
target.search = url3.search;
|
|
9730
9753
|
return { target, audience: decode(encodedAudience) };
|
|
9731
9754
|
}
|
|
9732
|
-
function
|
|
9755
|
+
function resolveMcpOAuthRoute(requestUrl) {
|
|
9756
|
+
const url3 = new URL(requestUrl, "http://127.0.0.1");
|
|
9757
|
+
const [, kind, environmentMcpId, ...rest] = url3.pathname.split("/");
|
|
9758
|
+
return kind === "mcp-oauth" && environmentMcpId ? { environmentMcpId, rest, search: url3.search } : null;
|
|
9759
|
+
}
|
|
9760
|
+
var MAX_MCP_OAUTH_BODY_BYTES = 10 * 1024 * 1024;
|
|
9761
|
+
function readBody(request, maxBytes) {
|
|
9733
9762
|
return new Promise((resolve7) => {
|
|
9734
9763
|
const chunks = [];
|
|
9735
9764
|
let size = 0;
|
|
9736
9765
|
request.on("data", (chunk) => {
|
|
9737
9766
|
size += chunk.length;
|
|
9738
|
-
if (size
|
|
9739
|
-
|
|
9740
|
-
request.on("end", () => {
|
|
9741
|
-
if (size > MAX_TOKEN_REQUEST_BYTES) return resolve7(null);
|
|
9742
|
-
const text = Buffer.concat(chunks).toString("utf8").trim();
|
|
9743
|
-
try {
|
|
9744
|
-
resolve7(text ? JSON.parse(text) : {});
|
|
9745
|
-
} catch {
|
|
9746
|
-
resolve7(null);
|
|
9747
|
-
}
|
|
9767
|
+
if (size > maxBytes) resolve7("too_large");
|
|
9768
|
+
else chunks.push(chunk);
|
|
9748
9769
|
});
|
|
9770
|
+
request.on("end", () => resolve7(Buffer.concat(chunks)));
|
|
9749
9771
|
request.on("error", () => resolve7(null));
|
|
9750
9772
|
});
|
|
9751
9773
|
}
|
|
9752
|
-
function
|
|
9774
|
+
function forward(request, response, target, token, onResponse = (incoming) => pipeResponse(incoming, response)) {
|
|
9775
|
+
const headers = { host: target.host };
|
|
9776
|
+
for (const [name, value] of Object.entries(request.headers)) {
|
|
9777
|
+
if (!STRIPPED_HEADERS.has(name) && !name.startsWith("x-replicas-") && value !== void 0) headers[name] = value;
|
|
9778
|
+
}
|
|
9779
|
+
headers.authorization = `Bearer ${token}`;
|
|
9780
|
+
const upstream = (target.protocol === "https:" ? https : http).request(target, { method: request.method, headers }, onResponse);
|
|
9781
|
+
upstream.on("error", () => {
|
|
9782
|
+
if (!response.headersSent) response.writeHead(502);
|
|
9783
|
+
response.end();
|
|
9784
|
+
});
|
|
9785
|
+
response.on("close", () => upstream.destroy());
|
|
9786
|
+
return upstream;
|
|
9787
|
+
}
|
|
9788
|
+
function pipeResponse(incoming, response) {
|
|
9789
|
+
response.writeHead(incoming.statusCode ?? 502, incoming.headers);
|
|
9790
|
+
incoming.pipe(response);
|
|
9791
|
+
response.on("close", () => incoming.destroy());
|
|
9792
|
+
}
|
|
9793
|
+
async function proxyMcpOAuth(request, response, tokens, route) {
|
|
9794
|
+
const body = await readBody(request, MAX_MCP_OAUTH_BODY_BYTES);
|
|
9795
|
+
if (body === "too_large") {
|
|
9796
|
+
response.writeHead(413, { connection: "close" }).end();
|
|
9797
|
+
return;
|
|
9798
|
+
}
|
|
9799
|
+
if (!body) {
|
|
9800
|
+
response.writeHead(400).end();
|
|
9801
|
+
return;
|
|
9802
|
+
}
|
|
9803
|
+
const send = async (forceRefresh) => {
|
|
9804
|
+
const token = await tokens.get(route.environmentMcpId, forceRefresh);
|
|
9805
|
+
if (!token.ok) {
|
|
9806
|
+
response.writeHead(token.error.code ?? 503).end(token.error.message);
|
|
9807
|
+
return;
|
|
9808
|
+
}
|
|
9809
|
+
const target = new URL(token.data.url);
|
|
9810
|
+
if (route.rest.length) target.pathname = [target.pathname.replace(/\/$/, ""), ...route.rest].join("/");
|
|
9811
|
+
target.search = route.search;
|
|
9812
|
+
forward(request, response, target, token.data.access_token, (incoming) => {
|
|
9813
|
+
if (incoming.statusCode === 401 && !forceRefresh) {
|
|
9814
|
+
incoming.resume();
|
|
9815
|
+
void send(true);
|
|
9816
|
+
return;
|
|
9817
|
+
}
|
|
9818
|
+
pipeResponse(incoming, response);
|
|
9819
|
+
}).end(body);
|
|
9820
|
+
};
|
|
9821
|
+
await send(false);
|
|
9822
|
+
}
|
|
9823
|
+
async function readJsonBody(request) {
|
|
9824
|
+
const body = await readBody(request, MAX_TOKEN_REQUEST_BYTES);
|
|
9825
|
+
if (!body || body === "too_large") return null;
|
|
9826
|
+
const text = body.toString("utf8").trim();
|
|
9827
|
+
try {
|
|
9828
|
+
return text ? JSON.parse(text) : {};
|
|
9829
|
+
} catch {
|
|
9830
|
+
return null;
|
|
9831
|
+
}
|
|
9832
|
+
}
|
|
9833
|
+
function createIdentityProxy(tokens, mcpOAuthTokens2) {
|
|
9753
9834
|
return http.createServer(async (request, response) => {
|
|
9754
9835
|
const url3 = new URL(request.url ?? "/", "http://127.0.0.1");
|
|
9755
9836
|
if (url3.pathname === IDENTITY_TOKEN_PATH) {
|
|
@@ -9767,6 +9848,11 @@ function createIdentityProxy(tokens) {
|
|
|
9767
9848
|
response.end(JSON.stringify(result.ok ? result.data : { error: result.error.message }));
|
|
9768
9849
|
return;
|
|
9769
9850
|
}
|
|
9851
|
+
const mcpOAuthRoute = resolveMcpOAuthRoute(request.url ?? "/");
|
|
9852
|
+
if (mcpOAuthRoute) {
|
|
9853
|
+
await proxyMcpOAuth(request, response, mcpOAuthTokens2, mcpOAuthRoute);
|
|
9854
|
+
return;
|
|
9855
|
+
}
|
|
9770
9856
|
const route = resolveIdentityRoute(request.url ?? "/");
|
|
9771
9857
|
if (!route) {
|
|
9772
9858
|
response.writeHead(404).end("Unknown identity route");
|
|
@@ -9777,29 +9863,46 @@ function createIdentityProxy(tokens) {
|
|
|
9777
9863
|
response.writeHead(token.error.code ?? 503).end(token.error.message);
|
|
9778
9864
|
return;
|
|
9779
9865
|
}
|
|
9780
|
-
|
|
9781
|
-
for (const [name, value] of Object.entries(request.headers)) {
|
|
9782
|
-
if (!STRIPPED_HEADERS.has(name) && !name.startsWith("x-replicas-") && value !== void 0) headers[name] = value;
|
|
9783
|
-
}
|
|
9784
|
-
headers.authorization = `Bearer ${token.data.token}`;
|
|
9785
|
-
const upstream = (route.target.protocol === "https:" ? https : http).request(
|
|
9786
|
-
route.target,
|
|
9787
|
-
{ method: request.method, headers },
|
|
9788
|
-
(incoming) => {
|
|
9789
|
-
response.writeHead(incoming.statusCode ?? 502, incoming.headers);
|
|
9790
|
-
incoming.pipe(response);
|
|
9791
|
-
response.on("close", () => incoming.destroy());
|
|
9792
|
-
}
|
|
9793
|
-
);
|
|
9794
|
-
upstream.on("error", () => {
|
|
9795
|
-
if (!response.headersSent) response.writeHead(502);
|
|
9796
|
-
response.end();
|
|
9797
|
-
});
|
|
9798
|
-
response.on("close", () => upstream.destroy());
|
|
9799
|
-
request.pipe(upstream);
|
|
9866
|
+
request.pipe(forward(request, response, route.target, token.data.token));
|
|
9800
9867
|
});
|
|
9801
9868
|
}
|
|
9802
9869
|
|
|
9870
|
+
// src/mcp-oauth-tokens.ts
|
|
9871
|
+
var MIN_REMAINING_MS2 = 60 * 1e3;
|
|
9872
|
+
var MAX_CACHE_MS = 5 * 60 * 1e3;
|
|
9873
|
+
var McpOAuthTokens = class {
|
|
9874
|
+
constructor(request = monolithRequest) {
|
|
9875
|
+
this.request = request;
|
|
9876
|
+
}
|
|
9877
|
+
request;
|
|
9878
|
+
tokens = new TokenCache();
|
|
9879
|
+
get(environmentMcpId, forceRefresh = false) {
|
|
9880
|
+
return this.tokens.get(environmentMcpId, () => this.fetch(environmentMcpId, forceRefresh), forceRefresh);
|
|
9881
|
+
}
|
|
9882
|
+
async fetch(environmentMcpId, forceRefresh) {
|
|
9883
|
+
const requested = await requestToken(
|
|
9884
|
+
this.request,
|
|
9885
|
+
"/v1/engine/mcp-oauth/token",
|
|
9886
|
+
{ environment_mcp_id: environmentMcpId, force_refresh: forceRefresh },
|
|
9887
|
+
"MCP OAuth token request failed"
|
|
9888
|
+
);
|
|
9889
|
+
if (!requested.ok) return requested;
|
|
9890
|
+
const response = requested.data;
|
|
9891
|
+
const data = await response.json().catch(() => null);
|
|
9892
|
+
const parsed = engineMcpOAuthTokenResponseSchema.safeParse(data);
|
|
9893
|
+
if (!response.ok || !parsed.success) {
|
|
9894
|
+
const message = isRecord(data) && typeof data.error === "string" ? data.error : `MCP OAuth token request failed: ${response.status}`;
|
|
9895
|
+
return createErrorResult({ message, code: response.ok ? 502 : response.status });
|
|
9896
|
+
}
|
|
9897
|
+
const remaining = parsed.data.expires_at ? Date.parse(parsed.data.expires_at) - Date.now() : Infinity;
|
|
9898
|
+
return createSuccessResult({
|
|
9899
|
+
token: parsed.data,
|
|
9900
|
+
refreshAt: Date.now() + Math.min(Math.max(remaining - MIN_REMAINING_MS2, remaining / 2), MAX_CACHE_MS)
|
|
9901
|
+
});
|
|
9902
|
+
}
|
|
9903
|
+
};
|
|
9904
|
+
var mcpOAuthTokens = new McpOAuthTokens();
|
|
9905
|
+
|
|
9803
9906
|
// src/lifecycle.ts
|
|
9804
9907
|
import { readFileSync, rmSync, writeFileSync } from "fs";
|
|
9805
9908
|
var CLAIM_FILE = "/tmp/replicas-engine.claim";
|
|
@@ -50655,7 +50758,7 @@ data: ${JSON.stringify(payload)}
|
|
|
50655
50758
|
}
|
|
50656
50759
|
async function parseBody(req, res) {
|
|
50657
50760
|
try {
|
|
50658
|
-
const body = await
|
|
50761
|
+
const body = await readBody2(req);
|
|
50659
50762
|
if (!body || typeof body !== "object") {
|
|
50660
50763
|
sendJson(res, 400, { ok: false, error: "Invalid request body" });
|
|
50661
50764
|
return null;
|
|
@@ -50666,7 +50769,7 @@ async function parseBody(req, res) {
|
|
|
50666
50769
|
return null;
|
|
50667
50770
|
}
|
|
50668
50771
|
}
|
|
50669
|
-
function
|
|
50772
|
+
function readBody2(req) {
|
|
50670
50773
|
return new Promise((resolve7, reject) => {
|
|
50671
50774
|
let size = 0;
|
|
50672
50775
|
const chunks = [];
|
|
@@ -53623,9 +53726,9 @@ function Clone2(value) {
|
|
|
53623
53726
|
// ../node_modules/.bun/typebox@1.3.7/node_modules/typebox/build/value/clean/from_union.mjs
|
|
53624
53727
|
function FromUnion9(context, type, value) {
|
|
53625
53728
|
for (const schema of type.anyOf) {
|
|
53626
|
-
const
|
|
53627
|
-
if (Check2(context, schema,
|
|
53628
|
-
return
|
|
53729
|
+
const clean2 = FromType19(context, schema, Clone2(value));
|
|
53730
|
+
if (Check2(context, schema, clean2))
|
|
53731
|
+
return clean2;
|
|
53629
53732
|
}
|
|
53630
53733
|
return value;
|
|
53631
53734
|
}
|
|
@@ -60531,6 +60634,106 @@ async function buildForkHandoff(input) {
|
|
|
60531
60634
|
};
|
|
60532
60635
|
}
|
|
60533
60636
|
|
|
60637
|
+
// src/services/chat/slack-activity-stream.ts
|
|
60638
|
+
var FLUSH_INTERVAL_MS = 3e3;
|
|
60639
|
+
var MAX_ACTIVITY_LENGTH = 300;
|
|
60640
|
+
var MAX_DONE_ATTEMPTS = 3;
|
|
60641
|
+
var sendQueue = Promise.resolve();
|
|
60642
|
+
var truncate = (text, max) => text.length > max ? `${text.slice(0, max - 1)}\u2026` : text;
|
|
60643
|
+
var clean = (text) => truncate(text.replace(/\s+/g, " ").trim(), MAX_ACTIVITY_LENGTH);
|
|
60644
|
+
function describeStep(message) {
|
|
60645
|
+
const plan = planItemsFromMessage(message);
|
|
60646
|
+
if (plan) {
|
|
60647
|
+
const current = plan.find((item) => item.status === "in_progress");
|
|
60648
|
+
return plan.length ? `Plan ${plan.filter((item) => item.status === "completed").length}/${plan.length}${current ? ` \xB7 ${current.text}` : ""}` : null;
|
|
60649
|
+
}
|
|
60650
|
+
if (message.type === "tool_call") {
|
|
60651
|
+
const input = summarizeInput(message.input);
|
|
60652
|
+
return input ? `${toolAction(message.tool)}: ${input}` : toolAction(message.tool);
|
|
60653
|
+
}
|
|
60654
|
+
const activity = getDisplayMessageActivity(message);
|
|
60655
|
+
if (!activity || activity.kind === "error") return null;
|
|
60656
|
+
return (activity.summary ? `${activity.title}: ${activity.summary}` : activity.title).trim().split("\n")[0];
|
|
60657
|
+
}
|
|
60658
|
+
var SlackActivityStream = class {
|
|
60659
|
+
constructor(turnId, provider) {
|
|
60660
|
+
this.turnId = turnId;
|
|
60661
|
+
this.provider = provider;
|
|
60662
|
+
this.timer = setInterval(() => this.enqueue(false), FLUSH_INTERVAL_MS);
|
|
60663
|
+
this.timer.unref?.();
|
|
60664
|
+
}
|
|
60665
|
+
turnId;
|
|
60666
|
+
provider;
|
|
60667
|
+
events = [];
|
|
60668
|
+
timer;
|
|
60669
|
+
sent = null;
|
|
60670
|
+
attempted = false;
|
|
60671
|
+
dirty = false;
|
|
60672
|
+
stopped = false;
|
|
60673
|
+
queued = false;
|
|
60674
|
+
noteEvent(event) {
|
|
60675
|
+
if (event.type === CLAUDE_PARTIAL_MESSAGE_EVENT_TYPE) return;
|
|
60676
|
+
const partialType = event.type === CODEX_ITEM_PARTIAL_EVENT_TYPE ? codexItemFromEvent(event)?.item.type : void 0;
|
|
60677
|
+
if (partialType === "agentMessage" || partialType === "reasoning") return;
|
|
60678
|
+
const streamId = getEventStreamId(event);
|
|
60679
|
+
const index = streamId ? this.events.findLastIndex((previous) => getEventStreamId(previous) === streamId) : -1;
|
|
60680
|
+
if (index >= 0) this.events[index] = event;
|
|
60681
|
+
else this.events.push(event);
|
|
60682
|
+
this.dirty = true;
|
|
60683
|
+
}
|
|
60684
|
+
finish() {
|
|
60685
|
+
clearInterval(this.timer);
|
|
60686
|
+
this.enqueue(true);
|
|
60687
|
+
}
|
|
60688
|
+
enqueue(done) {
|
|
60689
|
+
if (!done && this.queued) return;
|
|
60690
|
+
this.queued = true;
|
|
60691
|
+
sendQueue = sendQueue.then(async () => {
|
|
60692
|
+
this.queued = false;
|
|
60693
|
+
for (let attempt = 1; !await this.flush(done) && done && attempt < MAX_DONE_ATTEMPTS; attempt++) {
|
|
60694
|
+
await new Promise((resolve7) => setTimeout(resolve7, FLUSH_INTERVAL_MS));
|
|
60695
|
+
}
|
|
60696
|
+
}).catch((error) => console.error("[SlackActivityStream] Flush failed:", error));
|
|
60697
|
+
}
|
|
60698
|
+
async flush(done) {
|
|
60699
|
+
if (this.stopped) return true;
|
|
60700
|
+
if (done && !this.attempted) {
|
|
60701
|
+
this.stopped = true;
|
|
60702
|
+
return true;
|
|
60703
|
+
}
|
|
60704
|
+
let activity = {};
|
|
60705
|
+
if (!done) {
|
|
60706
|
+
if (!this.dirty) return true;
|
|
60707
|
+
this.dirty = false;
|
|
60708
|
+
const messages = parseDisplayMessages(this.events, this.provider);
|
|
60709
|
+
const thought = messages.map((message) => message.type === "agent" || message.type === "reasoning" ? message.content : "").findLast((text) => text.trim());
|
|
60710
|
+
const step = messages.map(describeStep).findLast(Boolean);
|
|
60711
|
+
activity = {
|
|
60712
|
+
...thought ? { thought: clean(thought) } : {},
|
|
60713
|
+
...step ? { step: clean(step) } : {}
|
|
60714
|
+
};
|
|
60715
|
+
if (!activity.thought && !activity.step || JSON.stringify(activity) === this.sent) return true;
|
|
60716
|
+
}
|
|
60717
|
+
this.attempted = true;
|
|
60718
|
+
const event = {
|
|
60719
|
+
type: "slack_activity",
|
|
60720
|
+
payload: { turnId: this.turnId, ...done ? { done } : activity }
|
|
60721
|
+
};
|
|
60722
|
+
const response = await monolithRequest("/v1/engine/webhook", { body: event, signal: AbortSignal.timeout(15e3) }).catch(() => null);
|
|
60723
|
+
if (response?.status === 409) {
|
|
60724
|
+
this.stopped = true;
|
|
60725
|
+
return true;
|
|
60726
|
+
}
|
|
60727
|
+
if (!response?.ok) {
|
|
60728
|
+
this.dirty = true;
|
|
60729
|
+
return false;
|
|
60730
|
+
}
|
|
60731
|
+
this.sent = JSON.stringify(activity);
|
|
60732
|
+
if (done) this.stopped = true;
|
|
60733
|
+
return true;
|
|
60734
|
+
}
|
|
60735
|
+
};
|
|
60736
|
+
|
|
60534
60737
|
// src/services/chat/chat-service.ts
|
|
60535
60738
|
var CHATS_BACKUP_FILE = `${CHATS_FILE}.bak`;
|
|
60536
60739
|
function createTurnMetadata(message, messageId, recordedAt) {
|
|
@@ -60993,6 +61196,9 @@ var ChatService = class {
|
|
|
60993
61196
|
...request.errorNotificationTargets ?? [],
|
|
60994
61197
|
...request.errorNotificationTarget ? [request.errorNotificationTarget] : []
|
|
60995
61198
|
];
|
|
61199
|
+
if (request.streamSlackActivity && chat.persisted.parentChatId === null) {
|
|
61200
|
+
chat.slackActivityMessageIds.add(result.messageId);
|
|
61201
|
+
}
|
|
60996
61202
|
if (notificationTargets.length > 0) {
|
|
60997
61203
|
const existingTargets = chat.errorNotificationTargets.get(result.messageId) ?? [];
|
|
60998
61204
|
chat.errorNotificationTargets.set(result.messageId, [
|
|
@@ -61135,6 +61341,7 @@ var ChatService = class {
|
|
|
61135
61341
|
for (const messageId of removed) {
|
|
61136
61342
|
chat.acceptedUserEvents.delete(messageId);
|
|
61137
61343
|
chat.errorNotificationTargets.delete(messageId);
|
|
61344
|
+
chat.slackActivityMessageIds.delete(messageId);
|
|
61138
61345
|
}
|
|
61139
61346
|
await this.persistAllChats().catch((error) => {
|
|
61140
61347
|
console.error("[ChatService] Failed to persist queued-message removals:", error);
|
|
@@ -61240,6 +61447,9 @@ var ChatService = class {
|
|
|
61240
61447
|
target.pendingMessageIds = [];
|
|
61241
61448
|
target.acceptedUserEvents.clear();
|
|
61242
61449
|
}
|
|
61450
|
+
target.slackActivity?.finish();
|
|
61451
|
+
target.slackActivity = null;
|
|
61452
|
+
target.slackActivityMessageIds.clear();
|
|
61243
61453
|
if (hasChatStarted(this.toSummary(target))) {
|
|
61244
61454
|
target.persisted.deletedAt = deletedAt;
|
|
61245
61455
|
} else {
|
|
@@ -61661,6 +61871,8 @@ var ChatService = class {
|
|
|
61661
61871
|
settledProcessing: null,
|
|
61662
61872
|
errorNotificationTargets: /* @__PURE__ */ new Map(),
|
|
61663
61873
|
activeErrorNotificationTargets: [],
|
|
61874
|
+
slackActivityMessageIds: /* @__PURE__ */ new Set(),
|
|
61875
|
+
slackActivity: null,
|
|
61664
61876
|
quotaExhaustion: null,
|
|
61665
61877
|
lastSendRequest: null
|
|
61666
61878
|
};
|
|
@@ -61715,6 +61927,8 @@ var ChatService = class {
|
|
|
61715
61927
|
this.agentTokenUsageTracker.startTurn(context);
|
|
61716
61928
|
chat.activeErrorNotificationTargets = chat.errorNotificationTargets.get(messageId) ?? [];
|
|
61717
61929
|
chat.errorNotificationTargets.delete(messageId);
|
|
61930
|
+
chat.slackActivity?.finish();
|
|
61931
|
+
chat.slackActivity = chat.slackActivityMessageIds.delete(messageId) ? new SlackActivityStream(messageId, chat.persisted.provider) : null;
|
|
61718
61932
|
}
|
|
61719
61933
|
async handleTurnStarted(chatId, message) {
|
|
61720
61934
|
const chat = this.getRuntimeChat(chatId);
|
|
@@ -61764,6 +61978,7 @@ var ChatService = class {
|
|
|
61764
61978
|
});
|
|
61765
61979
|
}
|
|
61766
61980
|
this.agentTokenUsageTracker.noteAgentEvent(chatId, event);
|
|
61981
|
+
chat.slackActivity?.noteEvent(event);
|
|
61767
61982
|
const parentToolUseId = typeof event.payload.parent_tool_use_id === "string" ? event.payload.parent_tool_use_id : null;
|
|
61768
61983
|
const messages = parseDisplayMessages([event], chat.persisted.provider, { filter: false, parentToolUseId });
|
|
61769
61984
|
if (chat.hasActiveTurn) this.agentChatActivityTrackerService.noteSkillMcpCalls(chatId, messages);
|
|
@@ -61854,6 +62069,8 @@ var ChatService = class {
|
|
|
61854
62069
|
}
|
|
61855
62070
|
chat.hasActiveTurn = false;
|
|
61856
62071
|
chat.activeMessageId = null;
|
|
62072
|
+
chat.slackActivity?.finish();
|
|
62073
|
+
chat.slackActivity = null;
|
|
61857
62074
|
this.endTrackedTurn(chatId);
|
|
61858
62075
|
const completedAt = (/* @__PURE__ */ new Date()).toISOString();
|
|
61859
62076
|
const processing = chat.provider.getQueue().length > 0 || (chat.provider.hasActiveBackgroundTasks?.() ?? false);
|
|
@@ -64677,7 +64894,7 @@ async function startBackgroundServices(signal) {
|
|
|
64677
64894
|
heartbeatService.start(bootTimeMs);
|
|
64678
64895
|
if (!identityProxyStarted) {
|
|
64679
64896
|
identityProxyStarted = true;
|
|
64680
|
-
createIdentityProxy(workspaceIdentityTokens).on("error", (error) => console.error("[identity-proxy] failed to listen:", error)).listen(IDENTITY_PROXY_PORT, "127.0.0.1");
|
|
64897
|
+
createIdentityProxy(workspaceIdentityTokens, mcpOAuthTokens).on("error", (error) => console.error("[identity-proxy] failed to listen:", error)).listen(IDENTITY_PROXY_PORT, "127.0.0.1");
|
|
64681
64898
|
}
|
|
64682
64899
|
for (const manager of tokenManagers.slice(1)) {
|
|
64683
64900
|
if (signal.aborted) return;
|
|
@@ -3,13 +3,13 @@ import { createRequire as __createRequire } from 'node:module';
|
|
|
3
3
|
const require = __createRequire(import.meta.url);
|
|
4
4
|
import {
|
|
5
5
|
publishedPullRequestUrls
|
|
6
|
-
} from "./chunk-
|
|
6
|
+
} from "./chunk-ABUMJRPU.js";
|
|
7
7
|
import {
|
|
8
8
|
isRecord
|
|
9
9
|
} from "./chunk-UZSNFLDQ.js";
|
|
10
10
|
import {
|
|
11
11
|
shouldRefreshPullRequests
|
|
12
|
-
} from "./chunk-
|
|
12
|
+
} from "./chunk-5HLMUJTJ.js";
|
|
13
13
|
import "./chunk-VEQXQN22.js";
|
|
14
14
|
|
|
15
15
|
// src/services/post-tool-pr-notifier.ts
|
package/dist/src/subagent-mcp.js
CHANGED