@botiverse/raft-daemon 1.0.9 → 1.0.11
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/{chunk-56EVMMRV.js → chunk-RKNTK2UF.js} +535 -175
- package/dist/cli/index.js +163 -12
- package/dist/core.js +3 -3
- package/dist/{dist-HDPAZ76N.js → dist-A7Z6RP4K.js} +163 -12
- package/dist/index.js +1 -1
- package/package.json +1 -1
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
// src/core.ts
|
|
2
2
|
import path25 from "path";
|
|
3
3
|
import os11 from "os";
|
|
4
|
-
import { randomUUID as
|
|
4
|
+
import { randomUUID as randomUUID10 } from "crypto";
|
|
5
5
|
import { createRequire as createRequire3 } from "module";
|
|
6
6
|
import { accessSync, createReadStream as createReadStream4, createWriteStream as createWriteStream2 } from "fs";
|
|
7
7
|
import { mkdtemp, rm as rm4, stat as stat4 } from "fs/promises";
|
|
@@ -1709,15 +1709,22 @@ var TRACE_EVENT_ROW_V2_PROJECTION_COLUMNS = [
|
|
|
1709
1709
|
["shadow_action", "string"],
|
|
1710
1710
|
["shadow_reason", "string"],
|
|
1711
1711
|
["shadow_direction", "string"],
|
|
1712
|
-
["shadow_plan_kind", "string"]
|
|
1712
|
+
["shadow_plan_kind", "string"],
|
|
1713
|
+
["machine_affinity_route", "string"],
|
|
1714
|
+
["replay_status", "int"]
|
|
1713
1715
|
];
|
|
1716
|
+
var TRACE_EVENT_ROW_V2_LEGACY_PROJECTION_COLUMNS = Object.freeze(TRACE_EVENT_ROW_V2_PROJECTION_COLUMNS.slice(0, 57));
|
|
1714
1717
|
var TRACE_EVENT_ROW_V2_TABLE = "raft.trace_events_v2";
|
|
1715
|
-
|
|
1716
|
-
|
|
1717
|
-
|
|
1718
|
-
|
|
1719
|
-
|
|
1720
|
-
].join(" ")
|
|
1718
|
+
function buildTraceEventRowV2IngestStatement(columns) {
|
|
1719
|
+
return [
|
|
1720
|
+
"SELECT",
|
|
1721
|
+
columns.map(([column, type]) => `$0["${column}"]::${type} AS ${column}`).join(", "),
|
|
1722
|
+
`INSERT INTO ${TRACE_EVENT_ROW_V2_TABLE}`,
|
|
1723
|
+
`(${columns.map(([column]) => column).join(", ")})`
|
|
1724
|
+
].join(" ");
|
|
1725
|
+
}
|
|
1726
|
+
var TRACE_EVENT_ROW_V2_INGEST_STATEMENT = buildTraceEventRowV2IngestStatement(TRACE_EVENT_ROW_V2_PROJECTION_COLUMNS);
|
|
1727
|
+
var TRACE_EVENT_ROW_V2_LEGACY_INGEST_STATEMENT = buildTraceEventRowV2IngestStatement(TRACE_EVENT_ROW_V2_LEGACY_PROJECTION_COLUMNS);
|
|
1721
1728
|
var PROMOTED_IDENTITY_ATTRS = [
|
|
1722
1729
|
"server_id",
|
|
1723
1730
|
"machine_id",
|
|
@@ -1773,7 +1780,8 @@ var PROMOTED_CLOSED_ATTRS = [
|
|
|
1773
1780
|
"shadow_action",
|
|
1774
1781
|
"shadow_reason",
|
|
1775
1782
|
"shadow_direction",
|
|
1776
|
-
"shadow_plan_kind"
|
|
1783
|
+
"shadow_plan_kind",
|
|
1784
|
+
"machine_affinity_route"
|
|
1777
1785
|
];
|
|
1778
1786
|
var TRACE_EVENT_ROW_PROMOTED_ATTRS = [
|
|
1779
1787
|
...PROMOTED_IDENTITY_ATTRS,
|
|
@@ -2849,6 +2857,10 @@ var agentApiIntegrationAppUpdateBodySchema = passthroughObject({
|
|
|
2849
2857
|
scopes: optionalStringArraySchema,
|
|
2850
2858
|
unsafeDemoUrlOverride: optionalBooleanSchema
|
|
2851
2859
|
});
|
|
2860
|
+
var agentApiIntegrationAppStatusQuerySchema = passthroughObject({
|
|
2861
|
+
card: optionalStringSchema,
|
|
2862
|
+
client: optionalStringSchema
|
|
2863
|
+
});
|
|
2852
2864
|
var agentApiActionPrepareBodySchema = passthroughObject({
|
|
2853
2865
|
target: z3.string().trim().min(1),
|
|
2854
2866
|
action: actionCardActionSchema
|
|
@@ -3003,6 +3015,23 @@ var agentApiIntegrationAppUpdateResponseSchema = passthroughObject({
|
|
|
3003
3015
|
clientName: z3.string(),
|
|
3004
3016
|
updatedFields: z3.array(z3.string())
|
|
3005
3017
|
});
|
|
3018
|
+
var agentApiOwnedIntegrationAppSchema = z3.object({
|
|
3019
|
+
state: z3.enum(["card_pending", "committed"]),
|
|
3020
|
+
card: nullableStringSchema,
|
|
3021
|
+
name: z3.string(),
|
|
3022
|
+
clientKey: nullableStringSchema,
|
|
3023
|
+
createdAt: z3.string(),
|
|
3024
|
+
callbackUrl: nullableStringSchema,
|
|
3025
|
+
scopes: z3.array(z3.string()),
|
|
3026
|
+
category: nullableStringSchema,
|
|
3027
|
+
recoveryCommand: nullableStringSchema
|
|
3028
|
+
});
|
|
3029
|
+
var agentApiIntegrationAppListResponseSchema = z3.object({
|
|
3030
|
+
apps: z3.array(agentApiOwnedIntegrationAppSchema)
|
|
3031
|
+
});
|
|
3032
|
+
var agentApiIntegrationAppStatusResponseSchema = z3.object({
|
|
3033
|
+
app: agentApiOwnedIntegrationAppSchema
|
|
3034
|
+
});
|
|
3006
3035
|
var agentApiAttachmentEnvelopeSchema = passthroughObject({
|
|
3007
3036
|
id: z3.string(),
|
|
3008
3037
|
filename: z3.string()
|
|
@@ -3799,6 +3828,26 @@ var agentApiContract = {
|
|
|
3799
3828
|
request: { body: agentApiIntegrationAppUpdateBodySchema },
|
|
3800
3829
|
response: { body: agentApiIntegrationAppUpdateResponseSchema }
|
|
3801
3830
|
}),
|
|
3831
|
+
integrationAppList: route({
|
|
3832
|
+
key: "integrationAppList",
|
|
3833
|
+
method: "GET",
|
|
3834
|
+
path: "/integrations/app",
|
|
3835
|
+
client: { resource: "integrations", method: "listApps" },
|
|
3836
|
+
capability: "read",
|
|
3837
|
+
description: "List pending app registration cards requested by this agent and server-local apps this agent currently owns.",
|
|
3838
|
+
request: {},
|
|
3839
|
+
response: { body: agentApiIntegrationAppListResponseSchema }
|
|
3840
|
+
}),
|
|
3841
|
+
integrationAppStatus: route({
|
|
3842
|
+
key: "integrationAppStatus",
|
|
3843
|
+
method: "GET",
|
|
3844
|
+
path: "/integrations/app/status",
|
|
3845
|
+
client: { resource: "integrations", method: "getAppStatus" },
|
|
3846
|
+
capability: "read",
|
|
3847
|
+
description: "Get one requester-visible registration card or currently owned app without disclosing non-owned app existence.",
|
|
3848
|
+
request: { query: agentApiIntegrationAppStatusQuerySchema },
|
|
3849
|
+
response: { body: agentApiIntegrationAppStatusResponseSchema }
|
|
3850
|
+
}),
|
|
3802
3851
|
actionPrepare: route({
|
|
3803
3852
|
key: "actionPrepare",
|
|
3804
3853
|
method: "POST",
|
|
@@ -5045,9 +5094,8 @@ var TRIAL_DURATION_DAYS = (TRIAL_END_DATE.getTime() - TRIAL_START_DATE.getTime()
|
|
|
5045
5094
|
// src/agentProcessManager.ts
|
|
5046
5095
|
import { readFileSync as readFileSync7 } from "fs";
|
|
5047
5096
|
import { readdir as readdir2, stat as stat2, readFile, rm as rm2, lstat, realpath, open } from "fs/promises";
|
|
5048
|
-
import { createHash as
|
|
5097
|
+
import { createHash as createHash4, randomUUID as randomUUID7 } from "crypto";
|
|
5049
5098
|
import path16 from "path";
|
|
5050
|
-
import { gzipSync } from "zlib";
|
|
5051
5099
|
import os9 from "os";
|
|
5052
5100
|
|
|
5053
5101
|
// src/proxy.ts
|
|
@@ -5119,12 +5167,12 @@ function resolveProxyUrl(targetUrl, env) {
|
|
|
5119
5167
|
if (shouldBypassProxy(targetUrl, env)) return void 0;
|
|
5120
5168
|
return proxyUrl;
|
|
5121
5169
|
}
|
|
5122
|
-
function createProxyDispatcher(proxyUrl,
|
|
5170
|
+
function createProxyDispatcher(proxyUrl, connectTimeoutMs, headersTimeoutMs) {
|
|
5123
5171
|
return new ProxyAgent({
|
|
5124
5172
|
uri: proxyUrl,
|
|
5125
|
-
connect: { timeout:
|
|
5126
|
-
requestTls: { timeout:
|
|
5127
|
-
headersTimeout:
|
|
5173
|
+
connect: { timeout: connectTimeoutMs },
|
|
5174
|
+
requestTls: { timeout: connectTimeoutMs },
|
|
5175
|
+
headersTimeout: headersTimeoutMs
|
|
5128
5176
|
});
|
|
5129
5177
|
}
|
|
5130
5178
|
function closeDispatcherBestEffort(dispatcher) {
|
|
@@ -5137,29 +5185,40 @@ function buildFetchDispatcher(targetUrl, env) {
|
|
|
5137
5185
|
const cached = fetchDispatcherCache.get(proxyUrl);
|
|
5138
5186
|
if (cached) return cached;
|
|
5139
5187
|
const timeoutMs = getFetchPreResponseTimeoutMs(env);
|
|
5140
|
-
const dispatcher = createProxyDispatcher(proxyUrl, timeoutMs);
|
|
5188
|
+
const dispatcher = createProxyDispatcher(proxyUrl, timeoutMs, timeoutMs);
|
|
5141
5189
|
fetchDispatcherCache.set(proxyUrl, dispatcher);
|
|
5142
5190
|
return dispatcher;
|
|
5143
5191
|
}
|
|
5144
|
-
function getIsolatedDispatcherCacheKey(targetUrl, isolationKey, env) {
|
|
5192
|
+
function getIsolatedDispatcherCacheKey(targetUrl, isolationKey, env, headersTimeoutMs) {
|
|
5145
5193
|
const proxyUrl = resolveProxyUrl(targetUrl, env);
|
|
5146
5194
|
const routeKey = proxyUrl ? `proxy:${proxyUrl}` : `direct:${new URL(targetUrl).origin}`;
|
|
5147
|
-
|
|
5195
|
+
const connectTimeoutMs = getFetchPreResponseTimeoutMs(env);
|
|
5196
|
+
const effectiveHeadersTimeoutMs = headersTimeoutMs ?? connectTimeoutMs;
|
|
5197
|
+
return {
|
|
5198
|
+
cacheKey: `${isolationKey}\0${routeKey}\0connect:${connectTimeoutMs}\0headers:${effectiveHeadersTimeoutMs}`,
|
|
5199
|
+
proxyUrl,
|
|
5200
|
+
connectTimeoutMs,
|
|
5201
|
+
headersTimeoutMs: effectiveHeadersTimeoutMs
|
|
5202
|
+
};
|
|
5148
5203
|
}
|
|
5149
|
-
function buildIsolatedFetchDispatcher(targetUrl, isolationKey, env) {
|
|
5150
|
-
const {
|
|
5204
|
+
function buildIsolatedFetchDispatcher(targetUrl, isolationKey, env, headersTimeoutMs) {
|
|
5205
|
+
const {
|
|
5206
|
+
cacheKey,
|
|
5207
|
+
proxyUrl,
|
|
5208
|
+
connectTimeoutMs,
|
|
5209
|
+
headersTimeoutMs: effectiveHeadersTimeoutMs
|
|
5210
|
+
} = getIsolatedDispatcherCacheKey(targetUrl, isolationKey, env, headersTimeoutMs);
|
|
5151
5211
|
const cached = isolatedFetchDispatcherCache.get(cacheKey);
|
|
5152
5212
|
if (cached) return cached;
|
|
5153
|
-
const
|
|
5154
|
-
|
|
5155
|
-
|
|
5156
|
-
headersTimeout: timeoutMs
|
|
5213
|
+
const dispatcher = proxyUrl ? createProxyDispatcher(proxyUrl, connectTimeoutMs, effectiveHeadersTimeoutMs) : new Agent({
|
|
5214
|
+
connect: { timeout: connectTimeoutMs },
|
|
5215
|
+
headersTimeout: effectiveHeadersTimeoutMs
|
|
5157
5216
|
});
|
|
5158
5217
|
isolatedFetchDispatcherCache.set(cacheKey, dispatcher);
|
|
5159
5218
|
return dispatcher;
|
|
5160
5219
|
}
|
|
5161
|
-
function evictIsolatedFetchDispatcher(targetUrl, isolationKey, env) {
|
|
5162
|
-
const { cacheKey } = getIsolatedDispatcherCacheKey(targetUrl, isolationKey, env);
|
|
5220
|
+
function evictIsolatedFetchDispatcher(targetUrl, isolationKey, env, headersTimeoutMs) {
|
|
5221
|
+
const { cacheKey } = getIsolatedDispatcherCacheKey(targetUrl, isolationKey, env, headersTimeoutMs);
|
|
5163
5222
|
const cached = isolatedFetchDispatcherCache.get(cacheKey);
|
|
5164
5223
|
if (!cached) return false;
|
|
5165
5224
|
isolatedFetchDispatcherCache.delete(cacheKey);
|
|
@@ -5183,12 +5242,20 @@ function withDaemonFetchProxy(input, init = {}, env = process.env) {
|
|
|
5183
5242
|
}
|
|
5184
5243
|
async function daemonFetch(input, init, env = process.env, options = {}) {
|
|
5185
5244
|
const targetUrl = input.toString();
|
|
5186
|
-
const fetchInit = options.isolationKey ? {
|
|
5245
|
+
const fetchInit = options.isolationKey ? {
|
|
5246
|
+
...init,
|
|
5247
|
+
dispatcher: buildIsolatedFetchDispatcher(
|
|
5248
|
+
targetUrl,
|
|
5249
|
+
options.isolationKey,
|
|
5250
|
+
env,
|
|
5251
|
+
options.headersTimeoutMs
|
|
5252
|
+
)
|
|
5253
|
+
} : withDaemonFetchProxy(input, init, env);
|
|
5187
5254
|
try {
|
|
5188
5255
|
return await fetch(input, fetchInit);
|
|
5189
5256
|
} catch (err) {
|
|
5190
5257
|
if (options.isolationKey) {
|
|
5191
|
-
evictIsolatedFetchDispatcher(targetUrl, options.isolationKey, env);
|
|
5258
|
+
evictIsolatedFetchDispatcher(targetUrl, options.isolationKey, env, options.headersTimeoutMs);
|
|
5192
5259
|
} else {
|
|
5193
5260
|
evictFetchDispatcher(targetUrl, env);
|
|
5194
5261
|
}
|
|
@@ -5211,6 +5278,10 @@ function formatAttachmentSuffix(attachments, style = "slock_cli") {
|
|
|
5211
5278
|
return ` [${attachments.length} attachment${attachments.length > 1 ? "s" : ""}: ${attachmentList} \u2014 ${attachmentDownloadHint(style)}]`;
|
|
5212
5279
|
}
|
|
5213
5280
|
|
|
5281
|
+
// src/feedbackTranscriptCollector.ts
|
|
5282
|
+
import { createHash, randomUUID } from "crypto";
|
|
5283
|
+
import { gzipSync } from "zlib";
|
|
5284
|
+
|
|
5214
5285
|
// src/logger.ts
|
|
5215
5286
|
var listeners = /* @__PURE__ */ new Set();
|
|
5216
5287
|
function timestamp() {
|
|
@@ -5475,6 +5546,182 @@ async function uploadWithSignedCapability({
|
|
|
5475
5546
|
return { capability, session, uploadResponse };
|
|
5476
5547
|
}
|
|
5477
5548
|
|
|
5549
|
+
// src/feedbackTranscriptWindow.ts
|
|
5550
|
+
var FEEDBACK_TRANSCRIPT_REPORT_WINDOW_TOLERANCE_MS = 15 * 60 * 1e3;
|
|
5551
|
+
var TIMESTAMP_KEYS = /* @__PURE__ */ new Set([
|
|
5552
|
+
"timestamp",
|
|
5553
|
+
"createdAt",
|
|
5554
|
+
"created_at",
|
|
5555
|
+
"updatedAt",
|
|
5556
|
+
"updated_at",
|
|
5557
|
+
"startedAt",
|
|
5558
|
+
"started_at",
|
|
5559
|
+
"endedAt",
|
|
5560
|
+
"ended_at"
|
|
5561
|
+
]);
|
|
5562
|
+
var MAX_SCAN_DEPTH = 12;
|
|
5563
|
+
var MAX_SCANNED_NODES = 1e5;
|
|
5564
|
+
function assessFeedbackTranscriptWindow(input) {
|
|
5565
|
+
const toleranceMs = input.toleranceMs ?? FEEDBACK_TRANSCRIPT_REPORT_WINDOW_TOLERANCE_MS;
|
|
5566
|
+
const reportMs = parseTimestamp(input.reportGeneratedAt);
|
|
5567
|
+
if (reportMs === null) {
|
|
5568
|
+
return {
|
|
5569
|
+
reportGeneratedAt: input.reportGeneratedAt,
|
|
5570
|
+
reportTimeSource: input.reportTimeSource,
|
|
5571
|
+
reportWindowStartAt: input.reportGeneratedAt,
|
|
5572
|
+
toleranceMs,
|
|
5573
|
+
coverage: "report_time_invalid"
|
|
5574
|
+
};
|
|
5575
|
+
}
|
|
5576
|
+
const timestamps = extractTranscriptTimestamps(input.transcript);
|
|
5577
|
+
const reportWindowStartMs = reportMs - toleranceMs;
|
|
5578
|
+
const base = {
|
|
5579
|
+
reportGeneratedAt: new Date(reportMs).toISOString(),
|
|
5580
|
+
reportTimeSource: input.reportTimeSource,
|
|
5581
|
+
reportWindowStartAt: new Date(reportWindowStartMs).toISOString(),
|
|
5582
|
+
toleranceMs
|
|
5583
|
+
};
|
|
5584
|
+
if (timestamps.length === 0) {
|
|
5585
|
+
return { ...base, coverage: "timestamps_unavailable" };
|
|
5586
|
+
}
|
|
5587
|
+
let firstMs = timestamps[0];
|
|
5588
|
+
let lastMs = timestamps[0];
|
|
5589
|
+
for (const timestamp2 of timestamps) {
|
|
5590
|
+
if (timestamp2 < firstMs) firstMs = timestamp2;
|
|
5591
|
+
if (timestamp2 > lastMs) lastMs = timestamp2;
|
|
5592
|
+
}
|
|
5593
|
+
return {
|
|
5594
|
+
...base,
|
|
5595
|
+
coverage: lastMs >= reportWindowStartMs ? "covered" : "outside_report_window",
|
|
5596
|
+
transcriptFirstEventAt: new Date(firstMs).toISOString(),
|
|
5597
|
+
transcriptLastEventAt: new Date(lastMs).toISOString()
|
|
5598
|
+
};
|
|
5599
|
+
}
|
|
5600
|
+
function extractTranscriptTimestamps(transcript) {
|
|
5601
|
+
const timestamps = [];
|
|
5602
|
+
const budget = { visited: 0 };
|
|
5603
|
+
const trimmed = transcript.trim();
|
|
5604
|
+
if (!trimmed) return timestamps;
|
|
5605
|
+
try {
|
|
5606
|
+
collectTimestamps(JSON.parse(trimmed), timestamps, budget, 0);
|
|
5607
|
+
return timestamps;
|
|
5608
|
+
} catch {
|
|
5609
|
+
}
|
|
5610
|
+
for (const line of transcript.split(/\r?\n/)) {
|
|
5611
|
+
if (budget.visited >= MAX_SCANNED_NODES) break;
|
|
5612
|
+
const candidate = line.trim();
|
|
5613
|
+
if (!candidate) continue;
|
|
5614
|
+
try {
|
|
5615
|
+
collectTimestamps(JSON.parse(candidate), timestamps, budget, 0);
|
|
5616
|
+
} catch {
|
|
5617
|
+
}
|
|
5618
|
+
}
|
|
5619
|
+
return timestamps;
|
|
5620
|
+
}
|
|
5621
|
+
function collectTimestamps(value, timestamps, budget, depth) {
|
|
5622
|
+
if (depth > MAX_SCAN_DEPTH || budget.visited >= MAX_SCANNED_NODES) return;
|
|
5623
|
+
budget.visited += 1;
|
|
5624
|
+
if (Array.isArray(value)) {
|
|
5625
|
+
for (const item of value) collectTimestamps(item, timestamps, budget, depth + 1);
|
|
5626
|
+
return;
|
|
5627
|
+
}
|
|
5628
|
+
if (!value || typeof value !== "object") return;
|
|
5629
|
+
for (const [key, child] of Object.entries(value)) {
|
|
5630
|
+
if (TIMESTAMP_KEYS.has(key)) {
|
|
5631
|
+
const parsed = parseTimestamp(child);
|
|
5632
|
+
if (parsed !== null) timestamps.push(parsed);
|
|
5633
|
+
}
|
|
5634
|
+
collectTimestamps(child, timestamps, budget, depth + 1);
|
|
5635
|
+
}
|
|
5636
|
+
}
|
|
5637
|
+
function parseTimestamp(value) {
|
|
5638
|
+
if (typeof value !== "string" || !/^\d{4}-\d{2}-\d{2}T/.test(value)) return null;
|
|
5639
|
+
const parsed = Date.parse(value);
|
|
5640
|
+
return Number.isFinite(parsed) ? parsed : null;
|
|
5641
|
+
}
|
|
5642
|
+
|
|
5643
|
+
// src/feedbackTranscriptCollector.ts
|
|
5644
|
+
function defaultFeedbackTranscriptReportWindow() {
|
|
5645
|
+
return {
|
|
5646
|
+
reportGeneratedAt: currentDate().toISOString(),
|
|
5647
|
+
reportTimeSource: "server_request_received"
|
|
5648
|
+
};
|
|
5649
|
+
}
|
|
5650
|
+
async function collectFeedbackTranscriptAttachment(input) {
|
|
5651
|
+
const transcriptResult = await input.getSessionTranscript();
|
|
5652
|
+
if (!transcriptResult.reachable || !transcriptResult.transcript) {
|
|
5653
|
+
return {
|
|
5654
|
+
reachable: false,
|
|
5655
|
+
fallbackReason: transcriptResult.fallbackReason ?? "transcript not reachable"
|
|
5656
|
+
};
|
|
5657
|
+
}
|
|
5658
|
+
const transcriptWindow = assessFeedbackTranscriptWindow({
|
|
5659
|
+
transcript: transcriptResult.transcript,
|
|
5660
|
+
...input.reportWindow
|
|
5661
|
+
});
|
|
5662
|
+
if (!input.workerUrl) {
|
|
5663
|
+
return {
|
|
5664
|
+
reachable: true,
|
|
5665
|
+
fallbackReason: "daemon worker URL is not configured",
|
|
5666
|
+
transcriptWindow
|
|
5667
|
+
};
|
|
5668
|
+
}
|
|
5669
|
+
const span = input.tracer.startSpan("daemon.feedback_transcript.upload", {
|
|
5670
|
+
surface: "daemon",
|
|
5671
|
+
kind: "producer",
|
|
5672
|
+
attrs: {
|
|
5673
|
+
agentId: input.agentId,
|
|
5674
|
+
feedbackReportId: input.feedbackReportId,
|
|
5675
|
+
runtime: transcriptResult.runtime,
|
|
5676
|
+
sessionId: transcriptResult.sessionId,
|
|
5677
|
+
transcript_size_bytes: transcriptResult.sizeBytes,
|
|
5678
|
+
transcript_window_coverage: transcriptWindow.coverage,
|
|
5679
|
+
transcript_window_report_time_source: transcriptWindow.reportTimeSource
|
|
5680
|
+
}
|
|
5681
|
+
});
|
|
5682
|
+
try {
|
|
5683
|
+
const gzipped = gzipSync(Buffer.from(transcriptResult.transcript, "utf8"));
|
|
5684
|
+
const bundleSha256 = createHash("sha256").update(gzipped).digest("hex");
|
|
5685
|
+
const bundleSizeBytes = gzipped.byteLength;
|
|
5686
|
+
const bundleId = randomUUID();
|
|
5687
|
+
const uploadResult = await uploadWithSignedCapability({
|
|
5688
|
+
serverUrl: input.serverUrl,
|
|
5689
|
+
apiKey: input.daemonApiKey,
|
|
5690
|
+
workerUrl: input.workerUrl,
|
|
5691
|
+
scope: "daemon-trace-bundle:create",
|
|
5692
|
+
createPath: "/api/trace-bundles",
|
|
5693
|
+
createBody: { bundleSha256, bundleSizeBytes },
|
|
5694
|
+
attestationMetadata: {
|
|
5695
|
+
bundleId,
|
|
5696
|
+
bundleSha256,
|
|
5697
|
+
bundleSizeBytes,
|
|
5698
|
+
bundleContentType: "application/json",
|
|
5699
|
+
bundleContentEncoding: "gzip",
|
|
5700
|
+
feedbackReportId: input.feedbackReportId,
|
|
5701
|
+
agentId: input.agentId,
|
|
5702
|
+
feedbackReportGeneratedAt: transcriptWindow.reportGeneratedAt,
|
|
5703
|
+
feedbackReportTimeSource: transcriptWindow.reportTimeSource,
|
|
5704
|
+
feedbackReportWindowStartAt: transcriptWindow.reportWindowStartAt,
|
|
5705
|
+
feedbackTranscriptWindowToleranceMs: transcriptWindow.toleranceMs,
|
|
5706
|
+
feedbackTranscriptWindowCoverage: transcriptWindow.coverage,
|
|
5707
|
+
...transcriptWindow.transcriptFirstEventAt ? { feedbackTranscriptFirstEventAt: transcriptWindow.transcriptFirstEventAt } : {},
|
|
5708
|
+
...transcriptWindow.transcriptLastEventAt ? { feedbackTranscriptLastEventAt: transcriptWindow.transcriptLastEventAt } : {}
|
|
5709
|
+
},
|
|
5710
|
+
uploadBody: new Blob([new Uint8Array(gzipped)], { type: "application/json" }),
|
|
5711
|
+
fetchImpl: input.fetchImpl
|
|
5712
|
+
});
|
|
5713
|
+
const traceBundleId = typeof uploadResult.session.id === "string" ? uploadResult.session.id : bundleId;
|
|
5714
|
+
logger.info(`[FeedbackTranscript] uploaded for report=${input.feedbackReportId} agent=${input.agentId} traceBundleId=${traceBundleId} size=${bundleSizeBytes}`);
|
|
5715
|
+
span.end("ok", { attrs: { traceBundleId, bundleSizeBytes, transcript_window_coverage: transcriptWindow.coverage } });
|
|
5716
|
+
return { reachable: true, traceBundleId, transcriptWindow };
|
|
5717
|
+
} catch (err) {
|
|
5718
|
+
const message = err instanceof Error ? err.message : String(err);
|
|
5719
|
+
logger.warn(`[FeedbackTranscript] upload failed for report=${input.feedbackReportId} agent=${input.agentId}: ${message}`);
|
|
5720
|
+
span.end("error", { attrs: { error_class: err instanceof Error ? err.name : "Error", error_message: message } });
|
|
5721
|
+
return { reachable: true, error: message, transcriptWindow };
|
|
5722
|
+
}
|
|
5723
|
+
}
|
|
5724
|
+
|
|
5478
5725
|
// src/drivers/claude.ts
|
|
5479
5726
|
import { spawn } from "child_process";
|
|
5480
5727
|
|
|
@@ -6089,7 +6336,7 @@ import http from "http";
|
|
|
6089
6336
|
import { URL as URL2 } from "url";
|
|
6090
6337
|
|
|
6091
6338
|
// src/apmStateMachine.ts
|
|
6092
|
-
import { createHash } from "crypto";
|
|
6339
|
+
import { createHash as createHash2 } from "crypto";
|
|
6093
6340
|
var MAX_APM_GATED_STEERING_EVENTS = 12;
|
|
6094
6341
|
function reviewStatePatch(state) {
|
|
6095
6342
|
return state.reviewing !== void 0 ? { reviewing: state.reviewing } : {};
|
|
@@ -7062,6 +7309,21 @@ var LOCAL_HELD_CONTEXT_LIMIT = 3;
|
|
|
7062
7309
|
var AGENT_CREDENTIAL_PROXY_HOST = "127.0.0.1";
|
|
7063
7310
|
var AGENT_CREDENTIAL_PROXY_BIND_MAX_ATTEMPTS = 3;
|
|
7064
7311
|
var AGENT_CREDENTIAL_PROXY_FETCH_ISOLATION_KEY = "agent-credential-proxy";
|
|
7312
|
+
var AGENT_CREDENTIAL_PROXY_UPLOAD_FETCH_ISOLATION_KEY = "agent-credential-proxy:attachment-upload";
|
|
7313
|
+
var DEFAULT_AGENT_CREDENTIAL_PROXY_UPLOAD_HEADERS_TIMEOUT_MS = 5 * 6e4;
|
|
7314
|
+
function attachmentUploadHeadersTimeoutMs(env) {
|
|
7315
|
+
const parsed = Number.parseInt(env.SLOCK_DAEMON_ATTACHMENT_UPLOAD_HEADERS_TIMEOUT_MS || "", 10);
|
|
7316
|
+
return Number.isFinite(parsed) && parsed > 0 ? parsed : DEFAULT_AGENT_CREDENTIAL_PROXY_UPLOAD_HEADERS_TIMEOUT_MS;
|
|
7317
|
+
}
|
|
7318
|
+
function agentCredentialProxyFetchOptions(pathname, env) {
|
|
7319
|
+
if (pathname === "/internal/agent-api/upload") {
|
|
7320
|
+
return {
|
|
7321
|
+
isolationKey: AGENT_CREDENTIAL_PROXY_UPLOAD_FETCH_ISOLATION_KEY,
|
|
7322
|
+
headersTimeoutMs: attachmentUploadHeadersTimeoutMs(env)
|
|
7323
|
+
};
|
|
7324
|
+
}
|
|
7325
|
+
return { isolationKey: AGENT_CREDENTIAL_PROXY_FETCH_ISOLATION_KEY };
|
|
7326
|
+
}
|
|
7065
7327
|
function createProxyRequestHandler() {
|
|
7066
7328
|
return (req, res) => {
|
|
7067
7329
|
void handleProxyRequest(req, res);
|
|
@@ -7269,7 +7531,7 @@ async function handleProxyRequest(req, res) {
|
|
|
7269
7531
|
body
|
|
7270
7532
|
},
|
|
7271
7533
|
process.env,
|
|
7272
|
-
|
|
7534
|
+
agentCredentialProxyFetchOptions(target.pathname, process.env)
|
|
7273
7535
|
);
|
|
7274
7536
|
if (upstream.status >= 500) {
|
|
7275
7537
|
const transportError = transportNormalizedErrorForHttpStatus(target, upstream.status, registration.launchId);
|
|
@@ -7361,6 +7623,7 @@ function writeProxyFailureResponse(res, failure) {
|
|
|
7361
7623
|
if (failure.lifecycleInvalidContext) body.invariant_context = failure.lifecycleInvalidContext;
|
|
7362
7624
|
const headers = { "content-type": "application/json" };
|
|
7363
7625
|
if (failure.correlationId) headers["x-raft-correlation-id"] = failure.correlationId;
|
|
7626
|
+
if (failure.suggestedNextAction) body.suggested_next_action = failure.suggestedNextAction;
|
|
7364
7627
|
res.writeHead(failure.responseStatusCode ?? 502, headers);
|
|
7365
7628
|
res.end(JSON.stringify(body));
|
|
7366
7629
|
}
|
|
@@ -7413,6 +7676,11 @@ function proxyFailureForError(method, target, err, context = {}) {
|
|
|
7413
7676
|
}
|
|
7414
7677
|
const errorCause = describeProxyErrorCause(cause);
|
|
7415
7678
|
if (errorCause) failure.errorCause = errorCause;
|
|
7679
|
+
if (failure.routeFamily === "attachments/upload" && failure.upstreamLayer === "read_timeout" && failure.errorCause?.startsWith("UND_ERR_HEADERS_TIMEOUT")) {
|
|
7680
|
+
failure.responseCode = "ATTACHMENT_UPLOAD_TIMEOUT";
|
|
7681
|
+
failure.responseError = "Attachment upload timed out before the server responded";
|
|
7682
|
+
failure.suggestedNextAction = "The server may still have accepted the file. Wait briefly, then retry once if needed; if it fails again, share the Correlation value with an operator.";
|
|
7683
|
+
}
|
|
7416
7684
|
return failure;
|
|
7417
7685
|
}
|
|
7418
7686
|
function parseAgentNoProcessResidencyInvariant(message) {
|
|
@@ -9311,7 +9579,9 @@ function codexThreadStatusChangedEvents(message) {
|
|
|
9311
9579
|
const statusMessage = explicitReason ?? "Codex thread entered system error state";
|
|
9312
9580
|
const errorEvent = {
|
|
9313
9581
|
kind: "error",
|
|
9314
|
-
message: statusMessage
|
|
9582
|
+
message: statusMessage,
|
|
9583
|
+
nativeReasonPresent: Boolean(explicitReason),
|
|
9584
|
+
reasonProvenance: explicitReason ? "codex_native_reason" : "daemon_fallback"
|
|
9315
9585
|
};
|
|
9316
9586
|
if (explicitReason) return [errorEvent];
|
|
9317
9587
|
return [
|
|
@@ -10794,15 +11064,8 @@ var GrokEventNormalizer = class {
|
|
|
10794
11064
|
return [{ kind: "tool_output", name: existing.name }];
|
|
10795
11065
|
}
|
|
10796
11066
|
case "pending_interaction":
|
|
10797
|
-
|
|
10798
|
-
|
|
10799
|
-
severity: "warning",
|
|
10800
|
-
source: "grok_acp_notification",
|
|
10801
|
-
itemType: updateKind,
|
|
10802
|
-
message: "Grok Build is waiting for user interaction",
|
|
10803
|
-
payloadBytes: payloadBytes3(update),
|
|
10804
|
-
...this.sessionIdValue ? { sessionId: this.sessionIdValue } : {}
|
|
10805
|
-
}];
|
|
11067
|
+
case "interaction_resolved":
|
|
11068
|
+
return [internalProgress(updateKind, update)];
|
|
10806
11069
|
case "turn_completed": {
|
|
10807
11070
|
const promptId = nonEmptyString4(update.prompt_id);
|
|
10808
11071
|
const generation = promptId ? this.generationByPromptId.get(promptId) ?? this.activeTurnGeneration : this.activeTurnGeneration;
|
|
@@ -11447,7 +11710,7 @@ async function detectGrokModelsFromAcp(options = {}) {
|
|
|
11447
11710
|
}
|
|
11448
11711
|
|
|
11449
11712
|
// src/drivers/antigravity.ts
|
|
11450
|
-
import { randomUUID } from "crypto";
|
|
11713
|
+
import { randomUUID as randomUUID2 } from "crypto";
|
|
11451
11714
|
import { spawn as spawn4 } from "child_process";
|
|
11452
11715
|
var DEFAULT_PRINT_TIMEOUT = "30m";
|
|
11453
11716
|
var ANTIGRAVITY_ENV_OVERRIDES = {
|
|
@@ -11525,7 +11788,7 @@ var AntigravityDriver = class {
|
|
|
11525
11788
|
};
|
|
11526
11789
|
}
|
|
11527
11790
|
async spawn(ctx) {
|
|
11528
|
-
this.sessionId = ctx.config.sessionId ||
|
|
11791
|
+
this.sessionId = ctx.config.sessionId || randomUUID2();
|
|
11529
11792
|
this.sessionAnnounced = false;
|
|
11530
11793
|
const { command, args, shell } = resolveAntigravitySpawn(buildAntigravityArgs(ctx));
|
|
11531
11794
|
const { spawnEnv } = await prepareCliTransport(ctx, {
|
|
@@ -12066,7 +12329,7 @@ var GeminiDriver = class {
|
|
|
12066
12329
|
};
|
|
12067
12330
|
|
|
12068
12331
|
// src/drivers/kimi.ts
|
|
12069
|
-
import { randomUUID as
|
|
12332
|
+
import { randomUUID as randomUUID3 } from "crypto";
|
|
12070
12333
|
import { spawn as spawn8 } from "child_process";
|
|
12071
12334
|
import { existsSync as existsSync6, readFileSync as readFileSync3, writeFileSync as writeFileSync3 } from "fs";
|
|
12072
12335
|
import os6 from "os";
|
|
@@ -12114,9 +12377,9 @@ var KimiDriver = class {
|
|
|
12114
12377
|
promptRequestId = null;
|
|
12115
12378
|
async spawn(ctx) {
|
|
12116
12379
|
const isResume = !!ctx.config.sessionId;
|
|
12117
|
-
this.sessionId = ctx.config.sessionId ||
|
|
12380
|
+
this.sessionId = ctx.config.sessionId || randomUUID3();
|
|
12118
12381
|
this.sessionAnnounced = false;
|
|
12119
|
-
this.promptRequestId =
|
|
12382
|
+
this.promptRequestId = randomUUID3();
|
|
12120
12383
|
const systemPromptPath = path10.join(ctx.workingDirectory, KIMI_SYSTEM_PROMPT_FILE);
|
|
12121
12384
|
const agentFilePath = path10.join(ctx.workingDirectory, KIMI_AGENT_FILE);
|
|
12122
12385
|
if (!isResume || !existsSync6(systemPromptPath)) {
|
|
@@ -12155,7 +12418,7 @@ var KimiDriver = class {
|
|
|
12155
12418
|
});
|
|
12156
12419
|
proc.stdin?.write(JSON.stringify({
|
|
12157
12420
|
jsonrpc: "2.0",
|
|
12158
|
-
id:
|
|
12421
|
+
id: randomUUID3(),
|
|
12159
12422
|
method: "initialize",
|
|
12160
12423
|
params: {
|
|
12161
12424
|
protocol_version: KIMI_WIRE_PROTOCOL_VERSION,
|
|
@@ -12236,7 +12499,7 @@ var KimiDriver = class {
|
|
|
12236
12499
|
if (mode === "idle") {
|
|
12237
12500
|
return JSON.stringify({
|
|
12238
12501
|
jsonrpc: "2.0",
|
|
12239
|
-
id:
|
|
12502
|
+
id: randomUUID3(),
|
|
12240
12503
|
method: "prompt",
|
|
12241
12504
|
params: {
|
|
12242
12505
|
user_input: _text
|
|
@@ -12245,7 +12508,7 @@ var KimiDriver = class {
|
|
|
12245
12508
|
}
|
|
12246
12509
|
return JSON.stringify({
|
|
12247
12510
|
jsonrpc: "2.0",
|
|
12248
|
-
id:
|
|
12511
|
+
id: randomUUID3(),
|
|
12249
12512
|
method: "steer",
|
|
12250
12513
|
params: {
|
|
12251
12514
|
user_input: _text
|
|
@@ -12291,7 +12554,7 @@ function detectKimiModels(home = os6.homedir()) {
|
|
|
12291
12554
|
}
|
|
12292
12555
|
|
|
12293
12556
|
// src/drivers/kimi-sdk.ts
|
|
12294
|
-
import { randomUUID as
|
|
12557
|
+
import { randomUUID as randomUUID4 } from "crypto";
|
|
12295
12558
|
import { EventEmitter } from "events";
|
|
12296
12559
|
import { mkdirSync as mkdirSync2, readFileSync as readFileSync4 } from "fs";
|
|
12297
12560
|
import path11 from "path";
|
|
@@ -12564,7 +12827,7 @@ var KimiSdkRuntimeSession = class {
|
|
|
12564
12827
|
}
|
|
12565
12828
|
if (this.didClose) return { ok: false, reason: "closed" };
|
|
12566
12829
|
this.started = true;
|
|
12567
|
-
const sessionId = input.sessionId || this.ctx.config.sessionId ||
|
|
12830
|
+
const sessionId = input.sessionId || this.ctx.config.sessionId || randomUUID4();
|
|
12568
12831
|
this.mappingState.sessionId = sessionId;
|
|
12569
12832
|
this.setCurrentSessionId(sessionId);
|
|
12570
12833
|
const { harness, session, wrapperPath } = await this.sessionFactory(
|
|
@@ -13236,7 +13499,7 @@ var OpenCodeDriver = class {
|
|
|
13236
13499
|
};
|
|
13237
13500
|
|
|
13238
13501
|
// src/drivers/pi.ts
|
|
13239
|
-
import { randomUUID as
|
|
13502
|
+
import { randomUUID as randomUUID5 } from "crypto";
|
|
13240
13503
|
import { EventEmitter as EventEmitter2 } from "events";
|
|
13241
13504
|
import { mkdirSync as mkdirSync3, readdirSync as readdirSync3 } from "fs";
|
|
13242
13505
|
import path13 from "path";
|
|
@@ -13966,7 +14229,7 @@ var PiSdkRuntimeSession = class {
|
|
|
13966
14229
|
}
|
|
13967
14230
|
if (this.didClose) return { ok: false, reason: "closed" };
|
|
13968
14231
|
this.started = true;
|
|
13969
|
-
const sessionId = input.sessionId || this.ctx.config.sessionId ||
|
|
14232
|
+
const sessionId = input.sessionId || this.ctx.config.sessionId || randomUUID5();
|
|
13970
14233
|
this.mappingState.sessionId = sessionId;
|
|
13971
14234
|
this.setCurrentSessionId(sessionId);
|
|
13972
14235
|
const session = await this.sessionFactory({
|
|
@@ -14871,6 +15134,36 @@ async function deleteWorkspaceDirectory(dataDir, directoryName) {
|
|
|
14871
15134
|
}
|
|
14872
15135
|
}
|
|
14873
15136
|
|
|
15137
|
+
// src/onboardingSeedContent.ts
|
|
15138
|
+
var ONBOARDING_DAY2_RECAP_PROTOCOL = `## Day-2 10:00 Recap Protocol
|
|
15139
|
+
|
|
15140
|
+
When the system wakes you with a reminder whose title starts \`D2 recap:\`, this is the
|
|
15141
|
+
one proactive return after onboarding \u2014 not permission to begin a daily cadence.
|
|
15142
|
+
|
|
15143
|
+
1. Read the reminder's anchor surface, your current objective statuses, and relevant
|
|
15144
|
+
server history since the opener. Treat only observable receipts as activity: an
|
|
15145
|
+
owner-authored request or decision, a completed setup objective, a delivered agent
|
|
15146
|
+
result, or a newly created agent/channel/invite.
|
|
15147
|
+
2. Search the anchor first. If a Day-2 recap was already posted, do not duplicate it.
|
|
15148
|
+
3. Always send exactly one short recap in the anchor surface. If there is no observable
|
|
15149
|
+
activity, say that plainly; never invent progress or turn an empty day into
|
|
15150
|
+
motivational copy.
|
|
15151
|
+
4. The recap has four parts, in this order:
|
|
15152
|
+
- Briefly explain that a system-set reminder just woke you to recap the prior day,
|
|
15153
|
+
and explain in plain language that Raft reminders can wake an agent at a chosen
|
|
15154
|
+
time to follow up on a specific conversation or task. Keep this to one warm
|
|
15155
|
+
sentence; do not turn the recap into a reminder tutorial.
|
|
15156
|
+
- Recap yesterday's observable activity and what it unlocked, or honestly say no
|
|
15157
|
+
verified progress was recorded.
|
|
15158
|
+
- Prompt one useful next step the owner can continue today.
|
|
15159
|
+
- Ask whether the owner would like this recap every day. Do not create a recurring
|
|
15160
|
+
reminder until the owner explicitly says yes.
|
|
15161
|
+
5. Do not suggest inviting anyone in this recap.
|
|
15162
|
+
6. If the owner later says yes, schedule a daily 10:00 reminder in the same anchor
|
|
15163
|
+
using the owner's timezone; if they say no or do not answer, schedule nothing.
|
|
15164
|
+
7. Honor \`skipped\` and \`later\`. The recap never reopens a declined ask or repeats the
|
|
15165
|
+
language/survey/opener questions.`;
|
|
15166
|
+
|
|
14874
15167
|
// src/agentStartCoordinator.ts
|
|
14875
15168
|
var AgentStartCoordinator = class {
|
|
14876
15169
|
starting = /* @__PURE__ */ new Set();
|
|
@@ -15156,7 +15449,7 @@ var AgentStartPendingDeliveryBuffer = class {
|
|
|
15156
15449
|
};
|
|
15157
15450
|
|
|
15158
15451
|
// src/agentNoProcessResidency.ts
|
|
15159
|
-
import { randomUUID as
|
|
15452
|
+
import { randomUUID as randomUUID6 } from "crypto";
|
|
15160
15453
|
var AgentNoProcessResidencyTransitions = class {
|
|
15161
15454
|
open = /* @__PURE__ */ new Map();
|
|
15162
15455
|
transitionSeq = 0;
|
|
@@ -15179,7 +15472,7 @@ var AgentNoProcessResidencyTransitions = class {
|
|
|
15179
15472
|
driver: input.driver,
|
|
15180
15473
|
launchSource: input.launchSource,
|
|
15181
15474
|
state: input.state,
|
|
15182
|
-
stateInstanceId:
|
|
15475
|
+
stateInstanceId: randomUUID6(),
|
|
15183
15476
|
isWaitState: input.isWaitState,
|
|
15184
15477
|
fenceKind: input.fenceKind,
|
|
15185
15478
|
deadlineUnixMs: typeof input.deadlineUnixMs === "number" ? input.deadlineUnixMs : void 0,
|
|
@@ -15819,7 +16112,7 @@ var AgentVisibleDeliveryLedger = class {
|
|
|
15819
16112
|
};
|
|
15820
16113
|
|
|
15821
16114
|
// src/runtimeErrorDiagnostics.ts
|
|
15822
|
-
import { createHash as
|
|
16115
|
+
import { createHash as createHash3 } from "crypto";
|
|
15823
16116
|
var MAX_RUNTIME_ERROR_MESSAGE_EXCERPT_CHARS = 4096;
|
|
15824
16117
|
var RUNTIME_AUTH_ACTION_REQUIRED_PATTERNS = [
|
|
15825
16118
|
/access token could not be refreshed/i,
|
|
@@ -15877,6 +16170,50 @@ function buildRuntimeErrorDiagnosticEnvelope(message) {
|
|
|
15877
16170
|
}
|
|
15878
16171
|
};
|
|
15879
16172
|
}
|
|
16173
|
+
function buildRuntimeErrorActivityDiagnostic(message, metadata = {}) {
|
|
16174
|
+
const envelope = buildRuntimeErrorDiagnosticEnvelope(message);
|
|
16175
|
+
return {
|
|
16176
|
+
errorClass: normalizeRuntimeErrorClass(envelope.spanAttrs.runtime_error_class),
|
|
16177
|
+
errorReason: normalizeRuntimeErrorReason(envelope.spanAttrs.turn_reason),
|
|
16178
|
+
fingerprint: String(envelope.spanAttrs.runtime_error_fingerprint),
|
|
16179
|
+
reasonProvenance: metadata.reasonProvenance ?? "runtime_error_event",
|
|
16180
|
+
...typeof metadata.nativeReasonPresent === "boolean" ? { nativeReasonPresent: metadata.nativeReasonPresent } : {}
|
|
16181
|
+
};
|
|
16182
|
+
}
|
|
16183
|
+
function normalizeRuntimeErrorClass(value) {
|
|
16184
|
+
switch (value) {
|
|
16185
|
+
case "InputTooLargeError":
|
|
16186
|
+
case "RateLimitError":
|
|
16187
|
+
case "AuthError":
|
|
16188
|
+
case "NotFoundError":
|
|
16189
|
+
case "ModelConfigError":
|
|
16190
|
+
case "TimeoutError":
|
|
16191
|
+
case "ProviderConnectionError":
|
|
16192
|
+
case "ProviderStreamError":
|
|
16193
|
+
case "ProviderServerError":
|
|
16194
|
+
case "ProviderApiError":
|
|
16195
|
+
return value;
|
|
16196
|
+
default:
|
|
16197
|
+
return "RuntimeError";
|
|
16198
|
+
}
|
|
16199
|
+
}
|
|
16200
|
+
function normalizeRuntimeErrorReason(value) {
|
|
16201
|
+
switch (value) {
|
|
16202
|
+
case "input_too_large":
|
|
16203
|
+
case "rate_limited":
|
|
16204
|
+
case "auth_failed":
|
|
16205
|
+
case "not_found":
|
|
16206
|
+
case "model_config_error":
|
|
16207
|
+
case "provider_timeout":
|
|
16208
|
+
case "provider_connection_error":
|
|
16209
|
+
case "provider_stream_error":
|
|
16210
|
+
case "provider_server_error":
|
|
16211
|
+
case "provider_api_error":
|
|
16212
|
+
return value;
|
|
16213
|
+
default:
|
|
16214
|
+
return "unclassified_runtime_error";
|
|
16215
|
+
}
|
|
16216
|
+
}
|
|
15880
16217
|
function formatRuntimeLoginRequiredMessage(runtimeId) {
|
|
15881
16218
|
if (runtimeId === "builtin") {
|
|
15882
16219
|
return "Built-in provider authentication failed. Check this agent's provider API key and region/provider selection, then retry starting this agent.";
|
|
@@ -16025,7 +16362,7 @@ function runtimeDisplayName(runtimeId) {
|
|
|
16025
16362
|
}
|
|
16026
16363
|
function fingerprintRuntimeError(value) {
|
|
16027
16364
|
const normalized = value.toLowerCase().replace(/[0-9a-f]{12,}/g, "<hex>").replace(/\b\d+\b/g, "<num>").replace(/\s+/g, " ").trim();
|
|
16028
|
-
return
|
|
16365
|
+
return createHash3("sha256").update(normalized).digest("hex").slice(0, 16);
|
|
16029
16366
|
}
|
|
16030
16367
|
function bucketLength(length) {
|
|
16031
16368
|
if (length === 0) return "0";
|
|
@@ -17069,6 +17406,8 @@ Know that you can ask me anything, anytime \u2014 that's the whole point of me.
|
|
|
17069
17406
|
- Manual-first when stuck: use the embedded recipes below, then \`raft manual get recipes/index\`, then \`raft manual get recipes/<slug>\` when available. Every \`raft manual get\` / \`raft manual search\` call requires two short natural-language fields in the same command: \`--intent\` says what the user ultimately wants to accomplish with Raft; \`--reason\` says why Manual is needed now. The recipe references below omit those flags only for readability. Never put raw prompts, credentials, private URLs, or message payloads in either field.
|
|
17070
17407
|
- Do not read, summarize, paste, or store provider API keys, raw tokens, secrets, or credential files.
|
|
17071
17408
|
|
|
17409
|
+
${ONBOARDING_DAY2_RECAP_PROTOCOL}
|
|
17410
|
+
|
|
17072
17411
|
## Branch Behaviors
|
|
17073
17412
|
|
|
17074
17413
|
### Owner says they already have workflows
|
|
@@ -17305,7 +17644,7 @@ function runtimeProfileNotificationTitle(kind) {
|
|
|
17305
17644
|
}
|
|
17306
17645
|
function hashRuntimeProfileKey(key) {
|
|
17307
17646
|
if (!key) return void 0;
|
|
17308
|
-
return
|
|
17647
|
+
return createHash4("sha256").update(key).digest("hex").slice(0, 16);
|
|
17309
17648
|
}
|
|
17310
17649
|
function runtimeProfileTurnControl(kind, key, source) {
|
|
17311
17650
|
return {
|
|
@@ -19405,7 +19744,7 @@ Use \`raft message read\` to catch up on the channels listed above, then stop. R
|
|
|
19405
19744
|
};
|
|
19406
19745
|
const initialSessionId = this.initialAgentProcessSessionId(driver, liveProcessConfig);
|
|
19407
19746
|
const restartSessionId = initialSessionId || (driver.requiresSessionInitForDelivery ? liveProcessConfig.sessionId || null : null);
|
|
19408
|
-
const processInstanceId =
|
|
19747
|
+
const processInstanceId = randomUUID7();
|
|
19409
19748
|
const startupInputMessages = wakeMessageDeliveredAsInboxUpdate && wakeMessage ? [wakeMessage, ...startingInboxMessages] : resumeCatchupDeliveredAsInput ? resumeCatchupInputMessages : startingInboxMessages;
|
|
19410
19749
|
agentProcess = {
|
|
19411
19750
|
runtime,
|
|
@@ -21318,75 +21657,18 @@ Use \`raft message read\` to catch up on the channels listed above, then stop. R
|
|
|
21318
21657
|
* bundle linked to a feedback report. The transcript is read using only the
|
|
21319
21658
|
* sessionId bound to the agent; no caller-supplied session id is accepted.
|
|
21320
21659
|
*/
|
|
21321
|
-
async collectFeedbackTranscript(agentId, feedbackReportId) {
|
|
21322
|
-
|
|
21323
|
-
|
|
21324
|
-
|
|
21325
|
-
|
|
21326
|
-
|
|
21327
|
-
|
|
21328
|
-
|
|
21329
|
-
|
|
21330
|
-
|
|
21331
|
-
|
|
21332
|
-
fallbackReason: "daemon worker URL is not configured"
|
|
21333
|
-
};
|
|
21334
|
-
}
|
|
21335
|
-
const span = this.tracer.startSpan("daemon.feedback_transcript.upload", {
|
|
21336
|
-
surface: "daemon",
|
|
21337
|
-
kind: "producer",
|
|
21338
|
-
attrs: {
|
|
21339
|
-
agentId,
|
|
21340
|
-
feedbackReportId,
|
|
21341
|
-
runtime: transcriptResult.runtime,
|
|
21342
|
-
sessionId: transcriptResult.sessionId,
|
|
21343
|
-
transcript_size_bytes: transcriptResult.sizeBytes
|
|
21344
|
-
}
|
|
21660
|
+
async collectFeedbackTranscript(agentId, feedbackReportId, reportWindow = defaultFeedbackTranscriptReportWindow()) {
|
|
21661
|
+
return collectFeedbackTranscriptAttachment({
|
|
21662
|
+
agentId,
|
|
21663
|
+
feedbackReportId,
|
|
21664
|
+
reportWindow,
|
|
21665
|
+
getSessionTranscript: () => this.getSessionTranscript(agentId),
|
|
21666
|
+
serverUrl: this.serverUrl,
|
|
21667
|
+
daemonApiKey: this.daemonApiKey,
|
|
21668
|
+
workerUrl: this.workerUrl,
|
|
21669
|
+
tracer: this.tracer,
|
|
21670
|
+
fetchImpl: this.fetchImpl
|
|
21345
21671
|
});
|
|
21346
|
-
try {
|
|
21347
|
-
const raw = Buffer.from(transcriptResult.transcript, "utf8");
|
|
21348
|
-
const gzipped = gzipSync(raw);
|
|
21349
|
-
const bundleSha256 = createHash3("sha256").update(gzipped).digest("hex");
|
|
21350
|
-
const bundleSizeBytes = gzipped.byteLength;
|
|
21351
|
-
const bundleId = randomUUID6();
|
|
21352
|
-
const uploadResult = await uploadWithSignedCapability({
|
|
21353
|
-
serverUrl: this.serverUrl,
|
|
21354
|
-
apiKey: this.daemonApiKey,
|
|
21355
|
-
workerUrl: this.workerUrl,
|
|
21356
|
-
scope: "daemon-trace-bundle:create",
|
|
21357
|
-
createPath: "/api/trace-bundles",
|
|
21358
|
-
createBody: {
|
|
21359
|
-
bundleSha256,
|
|
21360
|
-
bundleSizeBytes
|
|
21361
|
-
},
|
|
21362
|
-
attestationMetadata: {
|
|
21363
|
-
bundleId,
|
|
21364
|
-
bundleSha256,
|
|
21365
|
-
bundleSizeBytes,
|
|
21366
|
-
bundleContentType: "application/json",
|
|
21367
|
-
bundleContentEncoding: "gzip",
|
|
21368
|
-
feedbackReportId,
|
|
21369
|
-
agentId
|
|
21370
|
-
},
|
|
21371
|
-
uploadBody: new Blob([new Uint8Array(gzipped)], { type: "application/json" }),
|
|
21372
|
-
fetchImpl: this.fetchImpl
|
|
21373
|
-
});
|
|
21374
|
-
const traceBundleId = typeof uploadResult.session.id === "string" ? uploadResult.session.id : bundleId;
|
|
21375
|
-
logger.info(`[FeedbackTranscript] uploaded for report=${feedbackReportId} agent=${agentId} traceBundleId=${traceBundleId} size=${bundleSizeBytes}`);
|
|
21376
|
-
span.end("ok", { attrs: { traceBundleId, bundleSizeBytes } });
|
|
21377
|
-
return {
|
|
21378
|
-
reachable: true,
|
|
21379
|
-
traceBundleId
|
|
21380
|
-
};
|
|
21381
|
-
} catch (err) {
|
|
21382
|
-
const message = err instanceof Error ? err.message : String(err);
|
|
21383
|
-
logger.warn(`[FeedbackTranscript] upload failed for report=${feedbackReportId} agent=${agentId}: ${message}`);
|
|
21384
|
-
span.end("error", { attrs: { error_class: err instanceof Error ? err.name : "Error", error_message: message } });
|
|
21385
|
-
return {
|
|
21386
|
-
reachable: true,
|
|
21387
|
-
error: message
|
|
21388
|
-
};
|
|
21389
|
-
}
|
|
21390
21672
|
}
|
|
21391
21673
|
async listSkills(agentId, runtimeHint) {
|
|
21392
21674
|
const agent = this.agents.get(agentId);
|
|
@@ -21490,7 +21772,7 @@ Use \`raft message read\` to catch up on the channels listed above, then stop. R
|
|
|
21490
21772
|
* should carry explicit reason/correlation/window attrs so the server no
|
|
21491
21773
|
* longer infers lifecycle semantics from generic activity strings.
|
|
21492
21774
|
*/
|
|
21493
|
-
broadcastActivity(agentId, activityKind, detail, extraTrajectory = [], launchIdOverride, detailKind = "other", activityDisplay = activityKind, subagentLineage) {
|
|
21775
|
+
broadcastActivity(agentId, activityKind, detail, extraTrajectory = [], launchIdOverride, detailKind = "other", activityDisplay = activityKind, subagentLineage, runtimeError) {
|
|
21494
21776
|
const ap = this.agents.get(agentId);
|
|
21495
21777
|
const entries = [...extraTrajectory];
|
|
21496
21778
|
const hasToolStart = entries.some((e) => e.kind === "tool_start");
|
|
@@ -21522,7 +21804,8 @@ Use \`raft message read\` to catch up on the channels listed above, then stop. R
|
|
|
21522
21804
|
clientSeq,
|
|
21523
21805
|
producerFactId,
|
|
21524
21806
|
observedAtMs,
|
|
21525
|
-
isHeartbeat: false
|
|
21807
|
+
isHeartbeat: false,
|
|
21808
|
+
...runtimeError ? { runtimeError } : {}
|
|
21526
21809
|
});
|
|
21527
21810
|
this.recordActivityProducedTrace(agentId, activityKind, detail, detailKind, entries, ap, launchId, clientSeq, producerFactId, false);
|
|
21528
21811
|
if (ap) {
|
|
@@ -22251,7 +22534,7 @@ Use \`raft message read\` to catch up on the channels listed above, then stop. R
|
|
|
22251
22534
|
if (ap.readinessTransition) return;
|
|
22252
22535
|
const identity = this.launchIdentityAttrs(agentId, ap, launchSource);
|
|
22253
22536
|
const state = {
|
|
22254
|
-
stateInstanceId:
|
|
22537
|
+
stateInstanceId: randomUUID7(),
|
|
22255
22538
|
enterSeq: this.launchTransitionSeq++,
|
|
22256
22539
|
identity,
|
|
22257
22540
|
fenceKind,
|
|
@@ -22287,7 +22570,7 @@ Use \`raft message read\` to catch up on the channels listed above, then stop. R
|
|
|
22287
22570
|
if (ap.activation.kind !== "idle") return;
|
|
22288
22571
|
const identity = this.launchIdentityAttrs(agentId, ap, launchSource);
|
|
22289
22572
|
const state = {
|
|
22290
|
-
stateInstanceId:
|
|
22573
|
+
stateInstanceId: randomUUID7(),
|
|
22291
22574
|
enterSeq: this.launchTransitionSeq++,
|
|
22292
22575
|
identity,
|
|
22293
22576
|
negativeEvidenceBucket: launchReadinessNegativeEvidence(identity)
|
|
@@ -22975,7 +23258,13 @@ Use \`raft message read\` to catch up on the channels listed above, then stop. R
|
|
|
22975
23258
|
visibleErrorMessage,
|
|
22976
23259
|
visibleErrorEntries ?? [{ kind: "text", text: `Error: ${visibleErrorMessage}` }],
|
|
22977
23260
|
void 0,
|
|
22978
|
-
"runtime_error"
|
|
23261
|
+
"runtime_error",
|
|
23262
|
+
"error",
|
|
23263
|
+
void 0,
|
|
23264
|
+
buildRuntimeErrorActivityDiagnostic(event.message, {
|
|
23265
|
+
...typeof event.nativeReasonPresent === "boolean" ? { nativeReasonPresent: event.nativeReasonPresent } : {},
|
|
23266
|
+
...event.reasonProvenance ? { reasonProvenance: event.reasonProvenance } : {}
|
|
23267
|
+
})
|
|
22979
23268
|
);
|
|
22980
23269
|
break;
|
|
22981
23270
|
}
|
|
@@ -24012,7 +24301,7 @@ var ReminderCache = class {
|
|
|
24012
24301
|
};
|
|
24013
24302
|
|
|
24014
24303
|
// src/machineLock.ts
|
|
24015
|
-
import { createHash as
|
|
24304
|
+
import { createHash as createHash5, randomUUID as randomUUID8 } from "crypto";
|
|
24016
24305
|
import { mkdirSync as mkdirSync5, readFileSync as readFileSync8, rmSync as rmSync3, statSync as statSync2, writeFileSync as writeFileSync5 } from "fs";
|
|
24017
24306
|
import os10 from "os";
|
|
24018
24307
|
import path17 from "path";
|
|
@@ -24028,7 +24317,7 @@ var DaemonMachineLockConflictError = class extends Error {
|
|
|
24028
24317
|
}
|
|
24029
24318
|
};
|
|
24030
24319
|
function apiKeyFingerprint(apiKey) {
|
|
24031
|
-
return
|
|
24320
|
+
return createHash5("sha256").update(apiKey).digest("hex");
|
|
24032
24321
|
}
|
|
24033
24322
|
function getDaemonMachineLockId(apiKey) {
|
|
24034
24323
|
return `machine-${apiKeyFingerprint(apiKey).slice(0, 16)}`;
|
|
@@ -24069,7 +24358,7 @@ function acquireDaemonMachineLock(options) {
|
|
|
24069
24358
|
const lockId = getDaemonMachineLockId(options.apiKey);
|
|
24070
24359
|
const machineDir = path17.join(rootDir, lockId);
|
|
24071
24360
|
const lockDir = path17.join(machineDir, "daemon.lock");
|
|
24072
|
-
const token =
|
|
24361
|
+
const token = randomUUID8();
|
|
24073
24362
|
mkdirSync5(machineDir, { recursive: true });
|
|
24074
24363
|
for (let attempt = 0; attempt < 2; attempt += 1) {
|
|
24075
24364
|
try {
|
|
@@ -24307,12 +24596,12 @@ function isDiagnosticErrorAttr(key) {
|
|
|
24307
24596
|
}
|
|
24308
24597
|
|
|
24309
24598
|
// ../trace-client/src/traceJitter.ts
|
|
24310
|
-
import { createHash as
|
|
24599
|
+
import { createHash as createHash6 } from "crypto";
|
|
24311
24600
|
var INITIAL_UPLOAD_DELAY_SPAN_MS = 3e4;
|
|
24312
24601
|
var UPLOAD_INTERVAL_JITTER_SPAN_MS = 6e4;
|
|
24313
24602
|
var MAX_FILE_AGE_JITTER_SPAN_MS = 6e4;
|
|
24314
24603
|
function computeTraceJitter(lockId) {
|
|
24315
|
-
const seed =
|
|
24604
|
+
const seed = createHash6("sha256").update(lockId).digest();
|
|
24316
24605
|
return {
|
|
24317
24606
|
initialUploadDelayMs: seed.readUInt32BE(0) % INITIAL_UPLOAD_DELAY_SPAN_MS,
|
|
24318
24607
|
uploadIntervalJitterMs: seed.readUInt32BE(4) % UPLOAD_INTERVAL_JITTER_SPAN_MS,
|
|
@@ -24393,7 +24682,7 @@ function createTraceClient(options) {
|
|
|
24393
24682
|
}
|
|
24394
24683
|
|
|
24395
24684
|
// src/traceBundleUpload.ts
|
|
24396
|
-
import { createHash as
|
|
24685
|
+
import { createHash as createHash7, randomUUID as randomUUID9 } from "crypto";
|
|
24397
24686
|
import { gzipSync as gzipSync2 } from "zlib";
|
|
24398
24687
|
import { mkdir as mkdir2, readFile as readFile2, readdir as readdir3, stat as stat3, writeFile as writeFile2 } from "fs/promises";
|
|
24399
24688
|
import path19 from "path";
|
|
@@ -24524,7 +24813,7 @@ var DaemonTraceBundleUploader = class {
|
|
|
24524
24813
|
}
|
|
24525
24814
|
const gzipped = gzipSync2(raw);
|
|
24526
24815
|
const bundleSha256 = sha256Hex(gzipped);
|
|
24527
|
-
const bundleId =
|
|
24816
|
+
const bundleId = randomUUID9();
|
|
24528
24817
|
await uploadWithSignedCapability({
|
|
24529
24818
|
serverUrl: this.options.serverUrl,
|
|
24530
24819
|
apiKey: this.options.apiKey,
|
|
@@ -24593,7 +24882,7 @@ var DaemonTraceBundleUploader = class {
|
|
|
24593
24882
|
}
|
|
24594
24883
|
};
|
|
24595
24884
|
function sha256Hex(body) {
|
|
24596
|
-
return
|
|
24885
|
+
return createHash7("sha256").update(body).digest("hex");
|
|
24597
24886
|
}
|
|
24598
24887
|
function readPositiveIntegerEnv2(name, fallback) {
|
|
24599
24888
|
const value = process.env[name];
|
|
@@ -24833,7 +25122,7 @@ function assertLegacyDaemonKeyNotAdoptedByComputer(options) {
|
|
|
24833
25122
|
}
|
|
24834
25123
|
|
|
24835
25124
|
// src/agentMigrationHttpTransport.ts
|
|
24836
|
-
import { createHash as
|
|
25125
|
+
import { createHash as createHash8, randomBytes as randomBytes2, timingSafeEqual } from "crypto";
|
|
24837
25126
|
import http2 from "http";
|
|
24838
25127
|
import { Readable } from "stream";
|
|
24839
25128
|
var AGENT_MIGRATION_TRANSPORT_HOST_ENV = "SLOCK_AGENT_MIGRATION_TRANSPORT_HOST";
|
|
@@ -25327,7 +25616,7 @@ function verifyTokenHash(token, expectedHashHex) {
|
|
|
25327
25616
|
return timingSafeEqual(actual, expected);
|
|
25328
25617
|
}
|
|
25329
25618
|
function sha256Buffer(buffer) {
|
|
25330
|
-
return
|
|
25619
|
+
return createHash8("sha256").update(buffer).digest("hex");
|
|
25331
25620
|
}
|
|
25332
25621
|
function canonicalJsonBuffer(value) {
|
|
25333
25622
|
return Buffer.from(canonicalJson(value), "utf8");
|
|
@@ -25348,9 +25637,9 @@ function onceDrain(res) {
|
|
|
25348
25637
|
}
|
|
25349
25638
|
|
|
25350
25639
|
// src/agentMigrationObjectStoreBundle.ts
|
|
25351
|
-
import { createHash as
|
|
25640
|
+
import { createHash as createHash10 } from "crypto";
|
|
25352
25641
|
import { createReadStream as createReadStream2, createWriteStream } from "fs";
|
|
25353
|
-
import { lstat as lstat3, mkdir as mkdir3, readlink as readlink2, rm as rm3, symlink } from "fs/promises";
|
|
25642
|
+
import { lstat as lstat3, mkdir as mkdir3, readlink as readlink2, rm as rm3, statfs, symlink } from "fs/promises";
|
|
25354
25643
|
import path22 from "path";
|
|
25355
25644
|
import { Transform } from "stream";
|
|
25356
25645
|
import { pipeline } from "stream/promises";
|
|
@@ -25358,7 +25647,7 @@ import { createGunzip, createGzip } from "zlib";
|
|
|
25358
25647
|
import { extract, pack } from "tar-stream";
|
|
25359
25648
|
|
|
25360
25649
|
// src/agentMigrationExport.ts
|
|
25361
|
-
import { createHash as
|
|
25650
|
+
import { createHash as createHash9 } from "crypto";
|
|
25362
25651
|
import { createReadStream } from "fs";
|
|
25363
25652
|
import { lstat as lstat2, readdir as readdir4, readFile as readFile3, readlink } from "fs/promises";
|
|
25364
25653
|
import path21 from "path";
|
|
@@ -25576,7 +25865,7 @@ async function buildCrossTreeRefs(refs) {
|
|
|
25576
25865
|
return result;
|
|
25577
25866
|
}
|
|
25578
25867
|
async function sha256File(filePath) {
|
|
25579
|
-
const hash =
|
|
25868
|
+
const hash = createHash9("sha256");
|
|
25580
25869
|
await new Promise((resolve, reject) => {
|
|
25581
25870
|
const stream = createReadStream(filePath);
|
|
25582
25871
|
stream.on("data", (chunk) => hash.update(chunk));
|
|
@@ -25688,6 +25977,9 @@ var AGENT_MIGRATION_OBJECT_STORE_CONTENT_TYPE = "application/vnd.raft.agent-migr
|
|
|
25688
25977
|
var ARCHIVE_MANIFEST_PATH = "manifest.json";
|
|
25689
25978
|
var ARCHIVE_WORKSPACE_PREFIX = "workspace/";
|
|
25690
25979
|
var MAX_ARCHIVE_MANIFEST_BYTES = 64 * 1024 * 1024;
|
|
25980
|
+
var MAX_OBJECT_STORE_BUNDLE_ENTRIES = 25e4;
|
|
25981
|
+
var TARGET_ADOPTION_COPY_MULTIPLIER = 2n;
|
|
25982
|
+
var TARGET_DISK_RESERVE_BYTES = 512n * 1024n * 1024n;
|
|
25691
25983
|
var MAX_BUNDLE_TOO_LARGE_ACCOUNTING_ENTRIES = 3;
|
|
25692
25984
|
var MAX_ENCODED_ACCOUNTING_PATH_LENGTH = 96;
|
|
25693
25985
|
var AgentMigrationObjectStoreBundleTooLargeError = class extends Error {
|
|
@@ -25700,6 +25992,18 @@ var AgentMigrationObjectStoreBundleTooLargeError = class extends Error {
|
|
|
25700
25992
|
}
|
|
25701
25993
|
code = "MIGRATION_OBJECT_STORE_BUNDLE_TOO_LARGE";
|
|
25702
25994
|
};
|
|
25995
|
+
var AgentMigrationObjectStoreInsufficientDiskError = class extends Error {
|
|
25996
|
+
constructor(requiredBytes, availableBytes, contentBytes) {
|
|
25997
|
+
super(
|
|
25998
|
+
`MIGRATION_OBJECT_STORE_INSUFFICIENT_DISK:requiredBytes=${requiredBytes}:availableBytes=${availableBytes}:contentBytes=${contentBytes}`
|
|
25999
|
+
);
|
|
26000
|
+
this.requiredBytes = requiredBytes;
|
|
26001
|
+
this.availableBytes = availableBytes;
|
|
26002
|
+
this.contentBytes = contentBytes;
|
|
26003
|
+
this.name = "AgentMigrationObjectStoreInsufficientDiskError";
|
|
26004
|
+
}
|
|
26005
|
+
code = "MIGRATION_OBJECT_STORE_INSUFFICIENT_DISK";
|
|
26006
|
+
};
|
|
25703
26007
|
async function buildAgentMigrationObjectStoreBundle(input) {
|
|
25704
26008
|
assertPositiveMaxBytes(input.maxBytes);
|
|
25705
26009
|
const workspacePath = path22.resolve(input.workspacePath);
|
|
@@ -25709,7 +26013,7 @@ async function buildAgentMigrationObjectStoreBundle(input) {
|
|
|
25709
26013
|
workspacePath,
|
|
25710
26014
|
mode: "forensic"
|
|
25711
26015
|
});
|
|
25712
|
-
const contentBytes =
|
|
26016
|
+
const contentBytes = agentMigrationObjectStoreContentBytes(manifest);
|
|
25713
26017
|
const archiveManifest = {
|
|
25714
26018
|
schemaVersion: AGENT_MIGRATION_OBJECT_STORE_BUNDLE_SCHEMA_VERSION,
|
|
25715
26019
|
manifest
|
|
@@ -25721,8 +26025,17 @@ async function buildAgentMigrationObjectStoreBundle(input) {
|
|
|
25721
26025
|
}
|
|
25722
26026
|
const tarPack = pack();
|
|
25723
26027
|
const gzip = createGzip();
|
|
25724
|
-
const
|
|
26028
|
+
const compressedSizeLimit = createCompressedSizeLimit(
|
|
26029
|
+
input.maxBytes,
|
|
26030
|
+
largestWorkspaceEntries(manifest)
|
|
26031
|
+
);
|
|
26032
|
+
const bundle = tarPack.pipe(gzip).pipe(compressedSizeLimit);
|
|
25725
26033
|
tarPack.on("error", (error) => gzip.destroy(error));
|
|
26034
|
+
gzip.on("error", (error) => compressedSizeLimit.destroy(error));
|
|
26035
|
+
compressedSizeLimit.on("error", (error) => {
|
|
26036
|
+
gzip.destroy(error);
|
|
26037
|
+
tarPack.destroy(error);
|
|
26038
|
+
});
|
|
25726
26039
|
void writeArchive(tarPack, manifestBuffer, manifest, workspacePath).catch((error) => {
|
|
25727
26040
|
tarPack.destroy(error instanceof Error ? error : new Error(String(error)));
|
|
25728
26041
|
});
|
|
@@ -25747,13 +26060,13 @@ async function stageAgentMigrationObjectStoreBundle(input) {
|
|
|
25747
26060
|
let expectedEntries = /* @__PURE__ */ new Map();
|
|
25748
26061
|
const extractedEntries = /* @__PURE__ */ new Set();
|
|
25749
26062
|
let contentBytes = 0;
|
|
26063
|
+
const compressedSizeLimit = createCompressedSizeLimit(input.maxBytes);
|
|
25750
26064
|
const tarExtract = extract();
|
|
25751
26065
|
tarExtract.on("entry", (header, stream, next) => {
|
|
25752
26066
|
void handleArchiveEntry({
|
|
25753
26067
|
header,
|
|
25754
26068
|
stream,
|
|
25755
26069
|
stagingWorkspacePath,
|
|
25756
|
-
maxBytes: input.maxBytes,
|
|
25757
26070
|
getArchiveManifest: () => archiveManifest,
|
|
25758
26071
|
setArchiveManifest: (value) => {
|
|
25759
26072
|
archiveManifest = value;
|
|
@@ -25763,18 +26076,14 @@ async function stageAgentMigrationObjectStoreBundle(input) {
|
|
|
25763
26076
|
extractedEntries,
|
|
25764
26077
|
addContentBytes: (value) => {
|
|
25765
26078
|
contentBytes += value;
|
|
25766
|
-
if (contentBytes
|
|
25767
|
-
throw new
|
|
25768
|
-
contentBytes,
|
|
25769
|
-
input.maxBytes,
|
|
25770
|
-
archiveManifest ? largestWorkspaceEntries(archiveManifest.manifest) : []
|
|
25771
|
-
);
|
|
26079
|
+
if (!Number.isSafeInteger(contentBytes)) {
|
|
26080
|
+
throw new Error("MIGRATION_OBJECT_STORE_FILE_SIZE_INVALID");
|
|
25772
26081
|
}
|
|
25773
26082
|
}
|
|
25774
26083
|
}).then(() => next(), next);
|
|
25775
26084
|
});
|
|
25776
26085
|
try {
|
|
25777
|
-
await pipeline(input.bundle, createGunzip(), tarExtract);
|
|
26086
|
+
await pipeline(input.bundle, compressedSizeLimit, createGunzip(), tarExtract);
|
|
25778
26087
|
const completedManifest = archiveManifest;
|
|
25779
26088
|
if (!completedManifest) throw new Error("MIGRATION_OBJECT_STORE_MANIFEST_MISSING");
|
|
25780
26089
|
for (const relativePath of expectedEntries.keys()) {
|
|
@@ -25841,7 +26150,9 @@ async function handleArchiveEntry(input) {
|
|
|
25841
26150
|
if (input.getArchiveManifest()) throw new Error("MIGRATION_OBJECT_STORE_MANIFEST_DUPLICATE");
|
|
25842
26151
|
if (input.header.type !== "file") throw new Error("MIGRATION_OBJECT_STORE_MANIFEST_INVALID");
|
|
25843
26152
|
const manifestBuffer = await readEntryBuffer(input.stream, MAX_ARCHIVE_MANIFEST_BYTES);
|
|
25844
|
-
|
|
26153
|
+
const archiveManifest2 = parseArchiveManifest(manifestBuffer);
|
|
26154
|
+
await assertTargetWorkspaceResourceBudget(input.stagingWorkspacePath, archiveManifest2.manifest);
|
|
26155
|
+
input.setArchiveManifest(archiveManifest2);
|
|
25845
26156
|
return;
|
|
25846
26157
|
}
|
|
25847
26158
|
const archiveManifest = input.getArchiveManifest();
|
|
@@ -25872,7 +26183,7 @@ async function handleArchiveEntry(input) {
|
|
|
25872
26183
|
throw new Error(`MIGRATION_OBJECT_STORE_FILE_SIZE_MISMATCH:${relativePath}`);
|
|
25873
26184
|
}
|
|
25874
26185
|
input.addContentBytes(input.header.size ?? 0);
|
|
25875
|
-
const hash =
|
|
26186
|
+
const hash = createHash10("sha256");
|
|
25876
26187
|
const hashPassThrough = new Transform({
|
|
25877
26188
|
transform(chunk, _encoding, callback) {
|
|
25878
26189
|
hash.update(chunk);
|
|
@@ -25921,8 +26232,10 @@ function expectedWorkspaceEntries(manifest) {
|
|
|
25921
26232
|
}
|
|
25922
26233
|
return result;
|
|
25923
26234
|
}
|
|
25924
|
-
function
|
|
25925
|
-
|
|
26235
|
+
function agentMigrationObjectStoreContentBytes(manifest) {
|
|
26236
|
+
if (manifest.files.length > MAX_OBJECT_STORE_BUNDLE_ENTRIES) {
|
|
26237
|
+
throw new Error("MIGRATION_OBJECT_STORE_ENTRY_COUNT_LIMIT_EXCEEDED");
|
|
26238
|
+
}
|
|
25926
26239
|
let total = 0;
|
|
25927
26240
|
for (const entry of manifest.files) {
|
|
25928
26241
|
if (entry.source !== "workspace" || !entry.workspaceRelativePath) {
|
|
@@ -25935,14 +26248,42 @@ function assertAgentMigrationObjectStoreBundleSize(manifest, maxBytes) {
|
|
|
25935
26248
|
total += entry.sizeBytes ?? 0;
|
|
25936
26249
|
if (!Number.isSafeInteger(total)) throw new Error("MIGRATION_OBJECT_STORE_FILE_SIZE_INVALID");
|
|
25937
26250
|
}
|
|
25938
|
-
|
|
25939
|
-
|
|
25940
|
-
|
|
25941
|
-
|
|
25942
|
-
|
|
26251
|
+
return total;
|
|
26252
|
+
}
|
|
26253
|
+
async function assertTargetWorkspaceResourceBudget(stagingWorkspacePath, manifest) {
|
|
26254
|
+
const contentBytes = agentMigrationObjectStoreContentBytes(manifest);
|
|
26255
|
+
const volume = await statfs(stagingWorkspacePath, { bigint: true });
|
|
26256
|
+
const availableBytes = volume.bavail * volume.bsize;
|
|
26257
|
+
const requiredBytes = BigInt(contentBytes) * TARGET_ADOPTION_COPY_MULTIPLIER + TARGET_DISK_RESERVE_BYTES;
|
|
26258
|
+
if (availableBytes < requiredBytes) {
|
|
26259
|
+
throw new AgentMigrationObjectStoreInsufficientDiskError(
|
|
26260
|
+
requiredBytes,
|
|
26261
|
+
availableBytes,
|
|
26262
|
+
contentBytes
|
|
25943
26263
|
);
|
|
25944
26264
|
}
|
|
25945
|
-
|
|
26265
|
+
}
|
|
26266
|
+
function createCompressedSizeLimit(maxBytes, largestEntries = []) {
|
|
26267
|
+
assertPositiveMaxBytes(maxBytes);
|
|
26268
|
+
let compressedBytes = 0;
|
|
26269
|
+
return new Transform({
|
|
26270
|
+
transform(chunk, _encoding, callback) {
|
|
26271
|
+
compressedBytes += chunk.byteLength;
|
|
26272
|
+
if (!Number.isSafeInteger(compressedBytes)) {
|
|
26273
|
+
callback(new Error("MIGRATION_OBJECT_STORE_BUNDLE_SIZE_INVALID"));
|
|
26274
|
+
return;
|
|
26275
|
+
}
|
|
26276
|
+
if (compressedBytes > maxBytes) {
|
|
26277
|
+
callback(new AgentMigrationObjectStoreBundleTooLargeError(
|
|
26278
|
+
compressedBytes,
|
|
26279
|
+
maxBytes,
|
|
26280
|
+
largestEntries
|
|
26281
|
+
));
|
|
26282
|
+
return;
|
|
26283
|
+
}
|
|
26284
|
+
callback(null, chunk);
|
|
26285
|
+
}
|
|
26286
|
+
});
|
|
25946
26287
|
}
|
|
25947
26288
|
function largestWorkspaceEntries(manifest, limit = MAX_BUNDLE_TOO_LARGE_ACCOUNTING_ENTRIES) {
|
|
25948
26289
|
if (!Number.isSafeInteger(limit) || limit <= 0) return [];
|
|
@@ -26028,14 +26369,14 @@ function sortJsonValue2(value) {
|
|
|
26028
26369
|
}, {});
|
|
26029
26370
|
}
|
|
26030
26371
|
function sha256Buffer2(buffer) {
|
|
26031
|
-
return
|
|
26372
|
+
return createHash10("sha256").update(buffer).digest("hex");
|
|
26032
26373
|
}
|
|
26033
26374
|
function sanitizePathSegment(value) {
|
|
26034
26375
|
return value.replace(/[^a-zA-Z0-9._-]/g, "_").slice(0, 128) || "migration";
|
|
26035
26376
|
}
|
|
26036
26377
|
|
|
26037
26378
|
// src/agentMigrationImport.ts
|
|
26038
|
-
import { createHash as
|
|
26379
|
+
import { createHash as createHash11 } from "crypto";
|
|
26039
26380
|
import { createReadStream as createReadStream3 } from "fs";
|
|
26040
26381
|
import { access as access2, cp, lstat as lstat4, mkdir as mkdir4, readlink as readlink3, rename, writeFile as writeFile3 } from "fs/promises";
|
|
26041
26382
|
import path23 from "path";
|
|
@@ -26243,7 +26584,7 @@ async function writeArrivalReport(reportPath, report) {
|
|
|
26243
26584
|
return sha256Buffer3(Buffer.from(payload, "utf8"));
|
|
26244
26585
|
}
|
|
26245
26586
|
async function sha256File2(filePath) {
|
|
26246
|
-
const hash =
|
|
26587
|
+
const hash = createHash11("sha256");
|
|
26247
26588
|
const stream = createReadStream3(filePath);
|
|
26248
26589
|
for await (const chunk of stream) {
|
|
26249
26590
|
hash.update(chunk);
|
|
@@ -26251,7 +26592,7 @@ async function sha256File2(filePath) {
|
|
|
26251
26592
|
return hash.digest("hex");
|
|
26252
26593
|
}
|
|
26253
26594
|
function sha256Buffer3(buffer) {
|
|
26254
|
-
return
|
|
26595
|
+
return createHash11("sha256").update(buffer).digest("hex");
|
|
26255
26596
|
}
|
|
26256
26597
|
function canonicalJson3(value) {
|
|
26257
26598
|
return JSON.stringify(sortJsonValue3(value));
|
|
@@ -26505,7 +26846,10 @@ function migrationTransferFailureMessage(err) {
|
|
|
26505
26846
|
return message.slice(0, 500);
|
|
26506
26847
|
}
|
|
26507
26848
|
function migrationTransferFailureCode(err) {
|
|
26508
|
-
|
|
26849
|
+
if (err instanceof AgentMigrationObjectStoreBundleTooLargeError || err instanceof AgentMigrationObjectStoreInsufficientDiskError) {
|
|
26850
|
+
return err.code;
|
|
26851
|
+
}
|
|
26852
|
+
return void 0;
|
|
26509
26853
|
}
|
|
26510
26854
|
var MigrationObjectStoreUploadHttpError = class extends Error {
|
|
26511
26855
|
constructor(status, archiveBytes) {
|
|
@@ -26593,7 +26937,7 @@ function resolveSlockCliPathOrEmpty(moduleUrl = import.meta.url) {
|
|
|
26593
26937
|
}
|
|
26594
26938
|
async function runBundledSlockCli(argv) {
|
|
26595
26939
|
process.argv = [process.execPath, "slock", ...argv];
|
|
26596
|
-
await import("./dist-
|
|
26940
|
+
await import("./dist-A7Z6RP4K.js");
|
|
26597
26941
|
}
|
|
26598
26942
|
function detectRuntimes(tracer = noopTracer) {
|
|
26599
26943
|
const ids = [];
|
|
@@ -26742,7 +27086,7 @@ function summarizeIncomingMessage(msg) {
|
|
|
26742
27086
|
var DaemonCore = class {
|
|
26743
27087
|
options;
|
|
26744
27088
|
daemonVersion;
|
|
26745
|
-
daemonInstanceId =
|
|
27089
|
+
daemonInstanceId = randomUUID10();
|
|
26746
27090
|
// When this runner is launched by a managed Computer service, the
|
|
26747
27091
|
// service exports RAFT_COMPUTER_VERSION (the `@botiverse/raft-computer`
|
|
26748
27092
|
// bundle version). Reported in `ready` so the server can surface the
|
|
@@ -27786,7 +28130,10 @@ var DaemonCore = class {
|
|
|
27786
28130
|
});
|
|
27787
28131
|
break;
|
|
27788
28132
|
case "agent:diagnostic:feedback_transcript":
|
|
27789
|
-
this.agentManager.collectFeedbackTranscript(msg.agentId, msg.feedbackReportId
|
|
28133
|
+
this.agentManager.collectFeedbackTranscript(msg.agentId, msg.feedbackReportId, {
|
|
28134
|
+
reportGeneratedAt: msg.feedbackReportGeneratedAt ?? currentDate().toISOString(),
|
|
28135
|
+
reportTimeSource: msg.feedbackReportTimeSource ?? "server_request_received"
|
|
28136
|
+
}).then((result) => {
|
|
27790
28137
|
this.connection.send({
|
|
27791
28138
|
type: "agent:diagnostic:feedback_transcript_result",
|
|
27792
28139
|
agentId: msg.agentId,
|
|
@@ -27929,9 +28276,22 @@ var DaemonCore = class {
|
|
|
27929
28276
|
}
|
|
27930
28277
|
};
|
|
27931
28278
|
void Promise.resolve().then(() => this.options.onComputerControl(action, ctx)).catch((err) => {
|
|
28279
|
+
const message = err instanceof Error ? err.message : String(err);
|
|
28280
|
+
const failure = /(?:^|\b)CONTROL_BUSY(?:\b|:)/.test(message) ? "control_busy" : /(?:^|\b)SELF_RELAUNCH_UNAVAILABLE(?:\b|:)/.test(message) ? "self_relaunch_unavailable" : "computer_control_failed";
|
|
27932
28281
|
logger.error(
|
|
27933
|
-
`[Daemon] computer:${action} control handler failed: ${
|
|
28282
|
+
`[Daemon] computer:${action} control handler failed: ${message}`
|
|
27934
28283
|
);
|
|
28284
|
+
if (!requestId) return;
|
|
28285
|
+
if (action === "restart") {
|
|
28286
|
+
this.connection.send({
|
|
28287
|
+
type: "computer:restart:done",
|
|
28288
|
+
requestId,
|
|
28289
|
+
ok: false,
|
|
28290
|
+
error: failure
|
|
28291
|
+
});
|
|
28292
|
+
} else {
|
|
28293
|
+
ctx.emitUpgradeDone({ ok: false, error: failure });
|
|
28294
|
+
}
|
|
27935
28295
|
});
|
|
27936
28296
|
} else {
|
|
27937
28297
|
logger.info(`[Daemon] Ignoring computer:${action} \u2014 not launched by a Computer service.`);
|
|
@@ -28141,9 +28501,9 @@ export {
|
|
|
28141
28501
|
AGENT_MIGRATION_OBJECT_STORE_BUNDLE_SCHEMA_VERSION,
|
|
28142
28502
|
AGENT_MIGRATION_OBJECT_STORE_CONTENT_TYPE,
|
|
28143
28503
|
AgentMigrationObjectStoreBundleTooLargeError,
|
|
28504
|
+
AgentMigrationObjectStoreInsufficientDiskError,
|
|
28144
28505
|
buildAgentMigrationObjectStoreBundle,
|
|
28145
28506
|
stageAgentMigrationObjectStoreBundle,
|
|
28146
|
-
assertAgentMigrationObjectStoreBundleSize,
|
|
28147
28507
|
largestWorkspaceEntries,
|
|
28148
28508
|
buildAgentMigrationAdoptPlan,
|
|
28149
28509
|
verifyAgentMigrationAdoptPlan,
|