@deepagents/context 4.1.0 → 4.2.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +18 -13
- package/dist/browser.js.map +2 -2
- package/dist/index.js +576 -57
- package/dist/index.js.map +4 -4
- package/dist/lib/agent.d.ts.map +1 -1
- package/dist/lib/engine.d.ts +17 -3
- package/dist/lib/engine.d.ts.map +1 -1
- package/dist/lib/fragments/message/user.d.ts +12 -0
- package/dist/lib/fragments/message/user.d.ts.map +1 -1
- package/dist/lib/sandbox/agent-os-sandbox.d.ts +2 -2
- package/dist/lib/sandbox/agent-os-sandbox.d.ts.map +1 -1
- package/dist/lib/sandbox/apple-container-sandbox.d.ts +8 -0
- package/dist/lib/sandbox/apple-container-sandbox.d.ts.map +1 -1
- package/dist/lib/sandbox/bash-meta.d.ts +0 -3
- package/dist/lib/sandbox/bash-meta.d.ts.map +1 -1
- package/dist/lib/sandbox/bash-tool.d.ts +3 -3
- package/dist/lib/sandbox/bash-tool.d.ts.map +1 -1
- package/dist/lib/sandbox/container-engine.d.ts +2 -2
- package/dist/lib/sandbox/container-engine.d.ts.map +1 -1
- package/dist/lib/sandbox/container-sandbox.d.ts.map +1 -1
- package/dist/lib/sandbox/daytona-sandbox.d.ts +2 -2
- package/dist/lib/sandbox/daytona-sandbox.d.ts.map +1 -1
- package/dist/lib/sandbox/docker-sandbox.d.ts.map +1 -1
- package/dist/lib/sandbox/index.d.ts +1 -0
- package/dist/lib/sandbox/index.d.ts.map +1 -1
- package/dist/lib/sandbox/microsandbox-sandbox.d.ts +93 -0
- package/dist/lib/sandbox/microsandbox-sandbox.d.ts.map +1 -0
- package/dist/lib/sandbox/types.d.ts +19 -0
- package/dist/lib/sandbox/types.d.ts.map +1 -1
- package/dist/lib/sandbox/virtual-sandbox.d.ts +2 -2
- package/dist/lib/sandbox/virtual-sandbox.d.ts.map +1 -1
- package/dist/lib/save/save-pipeline.d.ts +13 -1
- package/dist/lib/save/save-pipeline.d.ts.map +1 -1
- package/dist/lib/store/postgres.store.d.ts +2 -1
- package/dist/lib/store/postgres.store.d.ts.map +1 -1
- package/dist/lib/store/sqlite.store.d.ts +2 -1
- package/dist/lib/store/sqlite.store.d.ts.map +1 -1
- package/dist/lib/store/sqlserver.store.d.ts +2 -1
- package/dist/lib/store/sqlserver.store.d.ts.map +1 -1
- package/dist/lib/store/store.d.ts +17 -2
- package/dist/lib/store/store.d.ts.map +1 -1
- package/package.json +12 -8
package/dist/index.js
CHANGED
|
@@ -1595,6 +1595,7 @@ var Agent = class _Agent {
|
|
|
1595
1595
|
),
|
|
1596
1596
|
toolChoice: this.#options.toolChoice,
|
|
1597
1597
|
onStepFinish: (step) => {
|
|
1598
|
+
if (!this.#options.logging) return;
|
|
1598
1599
|
const toolCall2 = step.toolCalls.at(-1);
|
|
1599
1600
|
if (toolCall2) {
|
|
1600
1601
|
console.log(
|
|
@@ -1672,6 +1673,7 @@ var Agent = class _Agent {
|
|
|
1672
1673
|
experimental_context: contextVariables,
|
|
1673
1674
|
toolChoice: this.#options.toolChoice,
|
|
1674
1675
|
onStepFinish: (step) => {
|
|
1676
|
+
if (!this.#options.logging) return;
|
|
1675
1677
|
const toolCall2 = step.toolCalls.at(-1);
|
|
1676
1678
|
if (toolCall2) {
|
|
1677
1679
|
console.log(
|
|
@@ -1932,7 +1934,10 @@ function wrapToolsWithOutputReminders(tools, context) {
|
|
|
1932
1934
|
execute: async (input, options) => {
|
|
1933
1935
|
const result = await execute.call(toolDef, input, options);
|
|
1934
1936
|
if (isAsyncIterable(result)) return result;
|
|
1935
|
-
return context.applyToolOutputReminders(result
|
|
1937
|
+
return context.applyToolOutputReminders(result, {
|
|
1938
|
+
toolName: name,
|
|
1939
|
+
input
|
|
1940
|
+
});
|
|
1936
1941
|
},
|
|
1937
1942
|
toModelOutput: (args) => {
|
|
1938
1943
|
const project = (output) => originalToModelOutput ? originalToModelOutput({
|
|
@@ -2611,7 +2616,15 @@ async function evaluateFiredReminders(configs, whenCtx) {
|
|
|
2611
2616
|
}
|
|
2612
2617
|
|
|
2613
2618
|
// packages/context/src/lib/save/save-pipeline.ts
|
|
2614
|
-
var
|
|
2619
|
+
var HeadConflictError = class extends Error {
|
|
2620
|
+
constructor(chatId, headMessageId) {
|
|
2621
|
+
super(
|
|
2622
|
+
`Could not commit head "${headMessageId}" for chat "${chatId}": concurrent writers kept moving the branch head`
|
|
2623
|
+
);
|
|
2624
|
+
this.name = "HeadConflictError";
|
|
2625
|
+
}
|
|
2626
|
+
};
|
|
2627
|
+
var SavePipeline = class _SavePipeline {
|
|
2615
2628
|
#engine;
|
|
2616
2629
|
#pending;
|
|
2617
2630
|
#shouldBranch = true;
|
|
@@ -2667,9 +2680,49 @@ var SavePipeline = class {
|
|
|
2667
2680
|
);
|
|
2668
2681
|
}
|
|
2669
2682
|
await this.#engine.store.addMessages(messages);
|
|
2670
|
-
await this.#
|
|
2683
|
+
await this.#commitHead(messages[0], parentId);
|
|
2671
2684
|
return { headMessageId: parentId };
|
|
2672
2685
|
}
|
|
2686
|
+
static #maxCommitAttempts = 5;
|
|
2687
|
+
/**
|
|
2688
|
+
* Advance the branch head to `newHead` through the store's CAS. A stale
|
|
2689
|
+
* cached head must never rewind the branch (that silently orphans turns
|
|
2690
|
+
* committed in between), so a rejected CAS re-reads the store head and
|
|
2691
|
+
* reconciles:
|
|
2692
|
+
* - the store head already descends from `newHead` (an in-place assistant
|
|
2693
|
+
* fill whose turn was built past): content is on the chain, keep the
|
|
2694
|
+
* store head;
|
|
2695
|
+
* - `newHead` descends from the store head: fast-forward, retry against it;
|
|
2696
|
+
* - true fork (another turn won the same head): graft this turn onto the
|
|
2697
|
+
* winning head by re-parenting the first pending message, then retry.
|
|
2698
|
+
* Grafting applies only to messages chained off the stale head — an
|
|
2699
|
+
* in-place fill keeps its original parent and its content already landed.
|
|
2700
|
+
*/
|
|
2701
|
+
async #commitHead(first2, newHead) {
|
|
2702
|
+
let expected = this.#engine.getActiveBranch().headMessageId;
|
|
2703
|
+
for (let i = 0; i < _SavePipeline.#maxCommitAttempts; i++) {
|
|
2704
|
+
if (await this.#engine.commitHead(newHead, expected)) return;
|
|
2705
|
+
const fresh = (await this.#engine.refreshBranch()).headMessageId;
|
|
2706
|
+
if (fresh === null || fresh === expected) {
|
|
2707
|
+
expected = fresh;
|
|
2708
|
+
continue;
|
|
2709
|
+
}
|
|
2710
|
+
if (await this.#chainContains(fresh, newHead)) return;
|
|
2711
|
+
if (await this.#chainContains(newHead, fresh)) {
|
|
2712
|
+
expected = fresh;
|
|
2713
|
+
continue;
|
|
2714
|
+
}
|
|
2715
|
+
if (first2.parentId !== expected) return;
|
|
2716
|
+
await this.#engine.store.setMessageParent(first2.id, fresh);
|
|
2717
|
+
first2.parentId = fresh;
|
|
2718
|
+
expected = fresh;
|
|
2719
|
+
}
|
|
2720
|
+
throw new HeadConflictError(this.#engine.chatId, newHead);
|
|
2721
|
+
}
|
|
2722
|
+
async #chainContains(headId, messageId) {
|
|
2723
|
+
const chain = await this.#engine.store.getMessageChain(headId);
|
|
2724
|
+
return chain.some((message2) => message2.id === messageId);
|
|
2725
|
+
}
|
|
2673
2726
|
};
|
|
2674
2727
|
|
|
2675
2728
|
// packages/context/src/lib/store/sqlite.store.ts
|
|
@@ -2937,6 +2990,17 @@ var SqliteContextStore = class extends ContextStore {
|
|
|
2937
2990
|
}
|
|
2938
2991
|
});
|
|
2939
2992
|
}
|
|
2993
|
+
async setMessageParent(messageId, parentId) {
|
|
2994
|
+
if (parentId === messageId) {
|
|
2995
|
+
throw new Error(`Message ${messageId} cannot be its own parent`);
|
|
2996
|
+
}
|
|
2997
|
+
const result = this.#stmt(
|
|
2998
|
+
"UPDATE messages SET parentId = ? WHERE id = ?"
|
|
2999
|
+
).run(parentId, messageId);
|
|
3000
|
+
if (result.changes === 0) {
|
|
3001
|
+
throw new Error(`Message ${messageId} not found`);
|
|
3002
|
+
}
|
|
3003
|
+
}
|
|
2940
3004
|
async getMessage(messageId) {
|
|
2941
3005
|
const row = this.#stmt("SELECT * FROM messages WHERE id = ?").get(
|
|
2942
3006
|
messageId
|
|
@@ -3043,11 +3107,11 @@ var SqliteContextStore = class extends ContextStore {
|
|
|
3043
3107
|
this.#db.prepare("UPDATE branches SET isActive = 0 WHERE chatId = ?").run(chatId);
|
|
3044
3108
|
this.#db.prepare("UPDATE branches SET isActive = 1 WHERE id = ?").run(branchId);
|
|
3045
3109
|
}
|
|
3046
|
-
async updateBranchHead(branchId, messageId) {
|
|
3047
|
-
|
|
3048
|
-
|
|
3049
|
-
|
|
3050
|
-
|
|
3110
|
+
async updateBranchHead(branchId, messageId, expectedHeadMessageId) {
|
|
3111
|
+
const result = this.#stmt(
|
|
3112
|
+
"UPDATE branches SET headMessageId = ? WHERE id = ? AND headMessageId IS ?"
|
|
3113
|
+
).run(messageId, branchId, expectedHeadMessageId);
|
|
3114
|
+
return result.changes > 0;
|
|
3051
3115
|
}
|
|
3052
3116
|
async listBranches(chatId) {
|
|
3053
3117
|
const rows = this.#db.prepare(
|
|
@@ -3916,6 +3980,10 @@ var ContextEngine = class _ContextEngine {
|
|
|
3916
3980
|
* return the (possibly wrapped) output.
|
|
3917
3981
|
*
|
|
3918
3982
|
* Called by the agent's tool wrapper right after each `execute()` resolves.
|
|
3983
|
+
* The wrapper passes the executing `call`, surfaced as
|
|
3984
|
+
* {@link WhenContext.executingTool}, so a predicate can gate on the live
|
|
3985
|
+
* tool's name/input/result — the only point at which the call being wrapped
|
|
3986
|
+
* is observable.
|
|
3919
3987
|
* The store keeps the wrapped value with a host-only marker; the model-facing
|
|
3920
3988
|
* projection strips that marker while preserving `result` + `systemReminder`.
|
|
3921
3989
|
*
|
|
@@ -3924,17 +3992,22 @@ var ContextEngine = class _ContextEngine {
|
|
|
3924
3992
|
* (e.g. asTool forks that set a pending user without saving), so the output
|
|
3925
3993
|
* passes through untouched.
|
|
3926
3994
|
*/
|
|
3927
|
-
async applyToolOutputReminders(output) {
|
|
3995
|
+
async applyToolOutputReminders(output, call) {
|
|
3928
3996
|
const configs = this.#remindersFor("tool-output");
|
|
3929
3997
|
if (configs.length === 0) return output;
|
|
3930
3998
|
await this.#ensureInitialized();
|
|
3931
3999
|
const chain = await this.#getChainContext();
|
|
3932
4000
|
const currentMessage = chain.lastMessage;
|
|
3933
4001
|
if (!currentMessage) return output;
|
|
3934
|
-
const
|
|
3935
|
-
|
|
3936
|
-
|
|
3937
|
-
|
|
4002
|
+
const whenCtx = this.#buildWhenCtx(chain, currentMessage);
|
|
4003
|
+
if (call) {
|
|
4004
|
+
whenCtx.executingTool = {
|
|
4005
|
+
name: call.toolName,
|
|
4006
|
+
input: call.input,
|
|
4007
|
+
output
|
|
4008
|
+
};
|
|
4009
|
+
}
|
|
4010
|
+
const matched = await evaluateFiredReminders(configs, whenCtx);
|
|
3938
4011
|
if (matched.length === 0) return output;
|
|
3939
4012
|
return applyRemindersToToolOutput(
|
|
3940
4013
|
output,
|
|
@@ -3949,12 +4022,29 @@ var ContextEngine = class _ContextEngine {
|
|
|
3949
4022
|
id: this.#activeBranch.id,
|
|
3950
4023
|
headMessageId: this.#activeBranch.headMessageId
|
|
3951
4024
|
}),
|
|
3952
|
-
commitHead: async (headMessageId) => {
|
|
3953
|
-
await this.#store.updateBranchHead(
|
|
4025
|
+
commitHead: async (headMessageId, expectedHeadMessageId) => {
|
|
4026
|
+
const committed = await this.#store.updateBranchHead(
|
|
3954
4027
|
this.#activeBranch.id,
|
|
3955
|
-
headMessageId
|
|
4028
|
+
headMessageId,
|
|
4029
|
+
expectedHeadMessageId
|
|
4030
|
+
);
|
|
4031
|
+
if (committed) {
|
|
4032
|
+
this.#activeBranch.headMessageId = headMessageId;
|
|
4033
|
+
}
|
|
4034
|
+
return committed;
|
|
4035
|
+
},
|
|
4036
|
+
refreshBranch: async () => {
|
|
4037
|
+
const fresh = await this.#store.getBranch(
|
|
4038
|
+
this.#chatId,
|
|
4039
|
+
this.#activeBranch.name
|
|
3956
4040
|
);
|
|
3957
|
-
|
|
4041
|
+
if (!fresh) {
|
|
4042
|
+
throw new Error(
|
|
4043
|
+
`Branch "${this.#activeBranch.name}" not found for chat "${this.#chatId}"`
|
|
4044
|
+
);
|
|
4045
|
+
}
|
|
4046
|
+
this.#branch = fresh;
|
|
4047
|
+
return { id: fresh.id, headMessageId: fresh.headMessageId };
|
|
3958
4048
|
},
|
|
3959
4049
|
rewindForUpdate: (parentId) => this.#rewindForUpdate(parentId)
|
|
3960
4050
|
};
|
|
@@ -4055,8 +4145,14 @@ var ContextEngine = class _ContextEngine {
|
|
|
4055
4145
|
*
|
|
4056
4146
|
* @example
|
|
4057
4147
|
* ```ts
|
|
4058
|
-
* context.set(
|
|
4059
|
-
*
|
|
4148
|
+
* context.set(
|
|
4149
|
+
* user({
|
|
4150
|
+
* id: 'q1',
|
|
4151
|
+
* role: 'user',
|
|
4152
|
+
* parts: [{ type: 'text', text: 'What is 2 + 2?' }],
|
|
4153
|
+
* }),
|
|
4154
|
+
* );
|
|
4155
|
+
* context.set(assistantText('The answer is 5.', { id: 'wrong' })); // Oops!
|
|
4060
4156
|
* await context.save();
|
|
4061
4157
|
*
|
|
4062
4158
|
* // Rewind to the question, creates new branch
|
|
@@ -4894,7 +4990,7 @@ async function chat(agent2, options = {}) {
|
|
|
4894
4990
|
execute: async ({ writer }) => {
|
|
4895
4991
|
writer.merge(uiStream);
|
|
4896
4992
|
if (title) {
|
|
4897
|
-
writer.write({ type: "data-chat-title", data: title });
|
|
4993
|
+
writer.write({ type: "data-chat-title", data: title, transient: true });
|
|
4898
4994
|
}
|
|
4899
4995
|
}
|
|
4900
4996
|
});
|
|
@@ -6132,14 +6228,15 @@ function bindAbort(signal, onAbort) {
|
|
|
6132
6228
|
}
|
|
6133
6229
|
async function createAgentOsSandbox(options = {}) {
|
|
6134
6230
|
const { AgentOs } = await importAgentOs();
|
|
6231
|
+
const { readiness, ...kernelOptions } = options;
|
|
6135
6232
|
let os;
|
|
6136
6233
|
try {
|
|
6137
|
-
os = await AgentOs.create(
|
|
6234
|
+
os = await AgentOs.create(kernelOptions);
|
|
6138
6235
|
} catch (error) {
|
|
6139
6236
|
const err = error instanceof Error ? error : new Error(String(error));
|
|
6140
6237
|
throw new AgentOsCreationError(err.message, err);
|
|
6141
6238
|
}
|
|
6142
|
-
|
|
6239
|
+
const sandbox = {
|
|
6143
6240
|
async executeCommand(command, { signal } = {}) {
|
|
6144
6241
|
if (signal?.aborted) {
|
|
6145
6242
|
return { stdout: "", stderr: "", exitCode: SIGKILL_EXIT_CODE };
|
|
@@ -6219,6 +6316,16 @@ async function createAgentOsSandbox(options = {}) {
|
|
|
6219
6316
|
return this.dispose();
|
|
6220
6317
|
}
|
|
6221
6318
|
};
|
|
6319
|
+
if (readiness) {
|
|
6320
|
+
try {
|
|
6321
|
+
await readiness(sandbox);
|
|
6322
|
+
} catch (error) {
|
|
6323
|
+
await sandbox.dispose().catch(() => {
|
|
6324
|
+
});
|
|
6325
|
+
throw error;
|
|
6326
|
+
}
|
|
6327
|
+
}
|
|
6328
|
+
return sandbox;
|
|
6222
6329
|
}
|
|
6223
6330
|
async function useAgentOsSandbox(options, fn) {
|
|
6224
6331
|
const sandbox = await createAgentOsSandbox(options);
|
|
@@ -6672,7 +6779,17 @@ var ContainerSandboxStrategy = class {
|
|
|
6672
6779
|
await this.cleanupCreatedVolumesAfterFailure(error);
|
|
6673
6780
|
throw error;
|
|
6674
6781
|
}
|
|
6675
|
-
|
|
6782
|
+
const sandbox = this.createSandboxMethods();
|
|
6783
|
+
if (this.opts.readiness) {
|
|
6784
|
+
try {
|
|
6785
|
+
await this.opts.readiness(sandbox);
|
|
6786
|
+
} catch (error) {
|
|
6787
|
+
await sandbox.dispose().catch(() => {
|
|
6788
|
+
});
|
|
6789
|
+
throw error;
|
|
6790
|
+
}
|
|
6791
|
+
}
|
|
6792
|
+
return sandbox;
|
|
6676
6793
|
}
|
|
6677
6794
|
namedContainerId() {
|
|
6678
6795
|
return `sandbox-${this.name}`;
|
|
@@ -7045,15 +7162,13 @@ function isAppleContainerfileOptions(opts) {
|
|
|
7045
7162
|
}
|
|
7046
7163
|
function buildMountArg(volume) {
|
|
7047
7164
|
const readOnly = volume.readOnly !== false;
|
|
7048
|
-
|
|
7165
|
+
if (volume.type === "volume") {
|
|
7166
|
+
return `${volume.name}:${volume.containerPath}${readOnly ? ":ro" : ""}`;
|
|
7167
|
+
}
|
|
7168
|
+
const parts = [
|
|
7049
7169
|
"type=bind",
|
|
7050
7170
|
`source=${volume.hostPath}`,
|
|
7051
7171
|
`target=${volume.containerPath}`
|
|
7052
|
-
] : [
|
|
7053
|
-
// Named volumes mount as virtiofs; `container` has no `type=volume`.
|
|
7054
|
-
"type=virtiofs",
|
|
7055
|
-
`source=${volume.name}`,
|
|
7056
|
-
`target=${volume.containerPath}`
|
|
7057
7172
|
];
|
|
7058
7173
|
if (readOnly) {
|
|
7059
7174
|
parts.push("readonly");
|
|
@@ -7073,8 +7188,9 @@ function safeParseArray(stdout) {
|
|
|
7073
7188
|
}
|
|
7074
7189
|
}
|
|
7075
7190
|
function readContainerStatus(entry) {
|
|
7191
|
+
const raw = entry?.status;
|
|
7076
7192
|
const status = String(
|
|
7077
|
-
|
|
7193
|
+
(typeof raw === "object" && raw !== null ? raw.state : raw) ?? ""
|
|
7078
7194
|
).toLowerCase();
|
|
7079
7195
|
if (status === "running" || status === "booted") return "running";
|
|
7080
7196
|
if (status === "stopped") return "stopped";
|
|
@@ -7104,7 +7220,10 @@ var appleEngine = {
|
|
|
7104
7220
|
args.push("--env", `${key}=${value}`);
|
|
7105
7221
|
}
|
|
7106
7222
|
for (const volume of opts.volumes ?? []) {
|
|
7107
|
-
args.push(
|
|
7223
|
+
args.push(
|
|
7224
|
+
volume.type === "volume" ? "--volume" : "--mount",
|
|
7225
|
+
buildMountArg(volume)
|
|
7226
|
+
);
|
|
7108
7227
|
}
|
|
7109
7228
|
args.push(image);
|
|
7110
7229
|
if (opts.command === void 0) {
|
|
@@ -7131,7 +7250,6 @@ var appleEngine = {
|
|
|
7131
7250
|
inspectArgs(containerId) {
|
|
7132
7251
|
return ["inspect", containerId];
|
|
7133
7252
|
},
|
|
7134
|
-
mountArg: buildMountArg,
|
|
7135
7253
|
parseStatus(stdout) {
|
|
7136
7254
|
const entries = safeParseArray(stdout);
|
|
7137
7255
|
if (entries.length === 0) return "absent";
|
|
@@ -7356,12 +7474,6 @@ function useBashMeta() {
|
|
|
7356
7474
|
return {
|
|
7357
7475
|
setHidden(patch) {
|
|
7358
7476
|
state.hidden = { ...state.hidden, ...patch };
|
|
7359
|
-
},
|
|
7360
|
-
setReminder(text) {
|
|
7361
|
-
state.reminder = text;
|
|
7362
|
-
},
|
|
7363
|
-
clearReminder() {
|
|
7364
|
-
state.reminder = void 0;
|
|
7365
7477
|
}
|
|
7366
7478
|
};
|
|
7367
7479
|
}
|
|
@@ -7571,14 +7683,8 @@ async function createBashTool(options) {
|
|
|
7571
7683
|
const result = await originalExecute({ command }, execOptions);
|
|
7572
7684
|
const state = readBashMeta();
|
|
7573
7685
|
if (!state) return result;
|
|
7574
|
-
|
|
7575
|
-
|
|
7576
|
-
if (!hasHidden && !hasReminder) return result;
|
|
7577
|
-
return {
|
|
7578
|
-
...result,
|
|
7579
|
-
...hasHidden ? { meta: state.hidden } : {},
|
|
7580
|
-
...hasReminder ? { reminder: state.reminder } : {}
|
|
7581
|
-
};
|
|
7686
|
+
if (Object.keys(state.hidden).length === 0) return result;
|
|
7687
|
+
return { ...result, meta: state.hidden };
|
|
7582
7688
|
})
|
|
7583
7689
|
);
|
|
7584
7690
|
},
|
|
@@ -7752,10 +7858,20 @@ async function createDaytonaSandbox(client, options = {}) {
|
|
|
7752
7858
|
} catch (error) {
|
|
7753
7859
|
throw normalizeDaytonaError(error, sdk);
|
|
7754
7860
|
}
|
|
7755
|
-
|
|
7861
|
+
const backend = createDaytonaSandboxMethods({
|
|
7756
7862
|
sandbox,
|
|
7757
7863
|
commandTimeout: options.commandTimeout
|
|
7758
7864
|
});
|
|
7865
|
+
if (options.readiness) {
|
|
7866
|
+
try {
|
|
7867
|
+
await options.readiness(backend);
|
|
7868
|
+
} catch (error) {
|
|
7869
|
+
await backend.dispose().catch(() => {
|
|
7870
|
+
});
|
|
7871
|
+
throw error;
|
|
7872
|
+
}
|
|
7873
|
+
}
|
|
7874
|
+
return backend;
|
|
7759
7875
|
}
|
|
7760
7876
|
var UNRECOVERABLE_SANDBOX_STATES = /* @__PURE__ */ new Set([
|
|
7761
7877
|
"error",
|
|
@@ -8393,7 +8509,6 @@ var dockerEngine = {
|
|
|
8393
8509
|
containerId
|
|
8394
8510
|
];
|
|
8395
8511
|
},
|
|
8396
|
-
mountArg: dockerMountArg,
|
|
8397
8512
|
parseStatus(status) {
|
|
8398
8513
|
return status === "running" ? "running" : "stopped";
|
|
8399
8514
|
},
|
|
@@ -9233,6 +9348,359 @@ function formatVersion(version) {
|
|
|
9233
9348
|
return /^[<>=!~]/.test(version) ? version : `==${version}`;
|
|
9234
9349
|
}
|
|
9235
9350
|
|
|
9351
|
+
// packages/context/src/lib/sandbox/microsandbox-sandbox.ts
|
|
9352
|
+
import "bash-tool";
|
|
9353
|
+
import { randomUUID as randomUUID3 } from "node:crypto";
|
|
9354
|
+
var MICROSANDBOX_DEFAULT_DESTINATION = "/workspace";
|
|
9355
|
+
var MICROSANDBOX_DEFAULT_IMAGE = "alpine";
|
|
9356
|
+
var MICROSANDBOX_MAX_NAME_BYTES = 128;
|
|
9357
|
+
var COMMAND_TIMEOUT_EXIT_CODE = 124;
|
|
9358
|
+
var MicrosandboxSandboxError = class extends Error {
|
|
9359
|
+
constructor(message2, cause) {
|
|
9360
|
+
super(message2);
|
|
9361
|
+
this.name = "MicrosandboxSandboxError";
|
|
9362
|
+
this.cause = cause;
|
|
9363
|
+
}
|
|
9364
|
+
};
|
|
9365
|
+
var MicrosandboxNotAvailableError = class extends MicrosandboxSandboxError {
|
|
9366
|
+
constructor(cause) {
|
|
9367
|
+
super(
|
|
9368
|
+
"microsandbox is not installed or its runtime is unavailable. Install it with: npm install microsandbox (requires Node >= 22 and hardware virtualization: Apple silicon, Linux with KVM, or Windows with WHP)",
|
|
9369
|
+
cause
|
|
9370
|
+
);
|
|
9371
|
+
this.name = "MicrosandboxNotAvailableError";
|
|
9372
|
+
}
|
|
9373
|
+
};
|
|
9374
|
+
var MicrosandboxCreationError = class extends MicrosandboxSandboxError {
|
|
9375
|
+
constructor(message2, cause) {
|
|
9376
|
+
super(`Failed to create microsandbox: ${message2}`, cause);
|
|
9377
|
+
this.name = "MicrosandboxCreationError";
|
|
9378
|
+
}
|
|
9379
|
+
};
|
|
9380
|
+
var MicrosandboxCommandError = class extends MicrosandboxSandboxError {
|
|
9381
|
+
constructor(message2, cause) {
|
|
9382
|
+
super(message2, cause);
|
|
9383
|
+
this.name = "MicrosandboxCommandError";
|
|
9384
|
+
}
|
|
9385
|
+
};
|
|
9386
|
+
async function createMicrosandboxSandbox(options = {}) {
|
|
9387
|
+
validateMicrosandboxOptions(options);
|
|
9388
|
+
const sdk = await importMicrosandbox();
|
|
9389
|
+
const ephemeral = options.name === void 0;
|
|
9390
|
+
const name = options.name ?? `deepagents-msb-${randomUUID3()}`;
|
|
9391
|
+
const workdir = options.workdir ?? MICROSANDBOX_DEFAULT_DESTINATION;
|
|
9392
|
+
let vm;
|
|
9393
|
+
try {
|
|
9394
|
+
vm = await acquireSandbox(sdk, { ...options, name, ephemeral, workdir });
|
|
9395
|
+
await vm.fs().mkdir(workdir);
|
|
9396
|
+
} catch (error) {
|
|
9397
|
+
throw normalizeMicrosandboxError(error, sdk);
|
|
9398
|
+
}
|
|
9399
|
+
const backend = createMicrosandboxMethods({
|
|
9400
|
+
sdk,
|
|
9401
|
+
vm,
|
|
9402
|
+
name,
|
|
9403
|
+
ephemeral,
|
|
9404
|
+
commandTimeout: options.commandTimeout
|
|
9405
|
+
});
|
|
9406
|
+
if (options.readiness) {
|
|
9407
|
+
try {
|
|
9408
|
+
await options.readiness(backend);
|
|
9409
|
+
} catch (error) {
|
|
9410
|
+
await backend.dispose().catch(() => {
|
|
9411
|
+
});
|
|
9412
|
+
throw error;
|
|
9413
|
+
}
|
|
9414
|
+
}
|
|
9415
|
+
return backend;
|
|
9416
|
+
}
|
|
9417
|
+
async function importMicrosandbox() {
|
|
9418
|
+
try {
|
|
9419
|
+
return await import("microsandbox");
|
|
9420
|
+
} catch (error) {
|
|
9421
|
+
throw new MicrosandboxNotAvailableError(toError2(error));
|
|
9422
|
+
}
|
|
9423
|
+
}
|
|
9424
|
+
async function acquireSandbox(sdk, options) {
|
|
9425
|
+
if (options.ephemeral || options.replace) {
|
|
9426
|
+
return buildSandbox(sdk, options);
|
|
9427
|
+
}
|
|
9428
|
+
let handle;
|
|
9429
|
+
try {
|
|
9430
|
+
handle = await sdk.Sandbox.get(options.name);
|
|
9431
|
+
} catch (error) {
|
|
9432
|
+
if (error instanceof sdk.SandboxNotFoundError) {
|
|
9433
|
+
return createFreshSandbox(sdk, options);
|
|
9434
|
+
}
|
|
9435
|
+
throw error;
|
|
9436
|
+
}
|
|
9437
|
+
if (handle.status === "running") {
|
|
9438
|
+
return handle.connect();
|
|
9439
|
+
}
|
|
9440
|
+
if (handle.status === "draining") {
|
|
9441
|
+
await handle.waitUntilStopped();
|
|
9442
|
+
}
|
|
9443
|
+
try {
|
|
9444
|
+
return await handle.start();
|
|
9445
|
+
} catch {
|
|
9446
|
+
await sdk.Sandbox.remove(options.name).catch(() => {
|
|
9447
|
+
});
|
|
9448
|
+
return buildSandbox(sdk, options);
|
|
9449
|
+
}
|
|
9450
|
+
}
|
|
9451
|
+
async function createFreshSandbox(sdk, options) {
|
|
9452
|
+
try {
|
|
9453
|
+
return await buildSandbox(sdk, options);
|
|
9454
|
+
} catch (error) {
|
|
9455
|
+
if (error instanceof sdk.SandboxAlreadyExistsError) {
|
|
9456
|
+
const handle = await sdk.Sandbox.get(options.name);
|
|
9457
|
+
return handle.status === "running" ? handle.connect() : handle.start();
|
|
9458
|
+
}
|
|
9459
|
+
throw error;
|
|
9460
|
+
}
|
|
9461
|
+
}
|
|
9462
|
+
function buildSandbox(sdk, options) {
|
|
9463
|
+
let builder = sdk.Sandbox.builder(options.name).image(options.image ?? MICROSANDBOX_DEFAULT_IMAGE).patch((patch) => patch.mkdir(options.workdir)).workdir(options.workdir);
|
|
9464
|
+
if (options.ephemeral) builder = builder.ephemeral(true);
|
|
9465
|
+
if (options.replace) builder = builder.replace();
|
|
9466
|
+
if (options.cpus !== void 0) builder = builder.cpus(options.cpus);
|
|
9467
|
+
if (options.memory !== void 0) builder = builder.memory(options.memory);
|
|
9468
|
+
if (options.env) builder = builder.envs(options.env);
|
|
9469
|
+
if (options.configure) builder = options.configure(builder);
|
|
9470
|
+
return builder.create();
|
|
9471
|
+
}
|
|
9472
|
+
function normalizeMicrosandboxError(error, sdk) {
|
|
9473
|
+
const err = toError2(error);
|
|
9474
|
+
if (err instanceof sdk.LibkrunfwNotFoundError) {
|
|
9475
|
+
return new MicrosandboxNotAvailableError(err);
|
|
9476
|
+
}
|
|
9477
|
+
if (err instanceof sdk.MicrosandboxError) {
|
|
9478
|
+
return err;
|
|
9479
|
+
}
|
|
9480
|
+
return new MicrosandboxCreationError(err.message, err);
|
|
9481
|
+
}
|
|
9482
|
+
function validateMicrosandboxOptions(options) {
|
|
9483
|
+
if (options.name !== void 0 && Buffer.byteLength(options.name, "utf-8") > MICROSANDBOX_MAX_NAME_BYTES) {
|
|
9484
|
+
throw new MicrosandboxSandboxError(
|
|
9485
|
+
`Microsandbox names are limited to ${MICROSANDBOX_MAX_NAME_BYTES} UTF-8 bytes.`
|
|
9486
|
+
);
|
|
9487
|
+
}
|
|
9488
|
+
if (options.replace && options.name === void 0) {
|
|
9489
|
+
throw new MicrosandboxSandboxError(
|
|
9490
|
+
'Microsandbox options can only include "replace" together with "name" \u2014 an unnamed sandbox is always created fresh.'
|
|
9491
|
+
);
|
|
9492
|
+
}
|
|
9493
|
+
}
|
|
9494
|
+
function createMicrosandboxMethods(args) {
|
|
9495
|
+
const { sdk, vm, name, ephemeral, commandTimeout } = args;
|
|
9496
|
+
const spawn7 = (command, options = {}) => {
|
|
9497
|
+
return spawnMicrosandboxProcess(sdk, vm, command, {
|
|
9498
|
+
...options,
|
|
9499
|
+
commandTimeout
|
|
9500
|
+
});
|
|
9501
|
+
};
|
|
9502
|
+
return {
|
|
9503
|
+
// `executeCommand` lowers onto the same streaming pump as `spawn` so a
|
|
9504
|
+
// single code path supports real cancellation. Cooperative abort (abandon
|
|
9505
|
+
// the promise, Daytona-style) is not an option here: the SDK is an
|
|
9506
|
+
// in-process native binding, so an abandoned exec keeps the guest process
|
|
9507
|
+
// and its libuv handle alive.
|
|
9508
|
+
async executeCommand(command, options) {
|
|
9509
|
+
const proc = spawn7(command, { signal: options?.signal });
|
|
9510
|
+
const [stdout, stderr, info] = await Promise.all([
|
|
9511
|
+
readAllText(proc.stdout),
|
|
9512
|
+
readAllText(proc.stderr),
|
|
9513
|
+
proc.exit
|
|
9514
|
+
]);
|
|
9515
|
+
if (info.signal === "SIGKILL") {
|
|
9516
|
+
return abortedCommandResult2();
|
|
9517
|
+
}
|
|
9518
|
+
return { stdout, stderr, exitCode: info.code ?? 1 };
|
|
9519
|
+
},
|
|
9520
|
+
spawn: spawn7,
|
|
9521
|
+
async readFile(path5) {
|
|
9522
|
+
try {
|
|
9523
|
+
return await vm.fs().readToString(path5);
|
|
9524
|
+
} catch (error) {
|
|
9525
|
+
throw new MicrosandboxCommandError(
|
|
9526
|
+
`Failed to read file "${path5}": ${toError2(error).message}`,
|
|
9527
|
+
toError2(error)
|
|
9528
|
+
);
|
|
9529
|
+
}
|
|
9530
|
+
},
|
|
9531
|
+
async writeFiles(files) {
|
|
9532
|
+
try {
|
|
9533
|
+
const fs2 = vm.fs();
|
|
9534
|
+
for (const dir of uniqueParentDirectories2(files.map((f) => f.path))) {
|
|
9535
|
+
await fs2.mkdir(dir);
|
|
9536
|
+
}
|
|
9537
|
+
for (const file of files) {
|
|
9538
|
+
await fs2.write(file.path, file.content);
|
|
9539
|
+
}
|
|
9540
|
+
} catch (error) {
|
|
9541
|
+
const err = toError2(error);
|
|
9542
|
+
throw new MicrosandboxCommandError(
|
|
9543
|
+
`Failed to write files: ${err.message}`,
|
|
9544
|
+
err
|
|
9545
|
+
);
|
|
9546
|
+
}
|
|
9547
|
+
},
|
|
9548
|
+
async dispose() {
|
|
9549
|
+
try {
|
|
9550
|
+
await vm.stop();
|
|
9551
|
+
} catch {
|
|
9552
|
+
}
|
|
9553
|
+
if (ephemeral) {
|
|
9554
|
+
await sdk.Sandbox.remove(name).catch(() => {
|
|
9555
|
+
});
|
|
9556
|
+
}
|
|
9557
|
+
},
|
|
9558
|
+
[Symbol.asyncDispose]() {
|
|
9559
|
+
return this.dispose();
|
|
9560
|
+
}
|
|
9561
|
+
};
|
|
9562
|
+
}
|
|
9563
|
+
function spawnMicrosandboxProcess(sdk, vm, command, options) {
|
|
9564
|
+
const stdout = createByteReadable();
|
|
9565
|
+
const stderr = createByteReadable();
|
|
9566
|
+
const exit = pumpExecStream({ sdk, vm, command, options, stdout, stderr });
|
|
9567
|
+
return { stdout: stdout.stream, stderr: stderr.stream, exit };
|
|
9568
|
+
}
|
|
9569
|
+
async function pumpExecStream(args) {
|
|
9570
|
+
const { sdk, vm, command, options, stdout, stderr } = args;
|
|
9571
|
+
const { signal } = options;
|
|
9572
|
+
let handle;
|
|
9573
|
+
let aborted = signal?.aborted ?? false;
|
|
9574
|
+
let timedOut = false;
|
|
9575
|
+
let timeoutTimer;
|
|
9576
|
+
const abort = () => {
|
|
9577
|
+
aborted = true;
|
|
9578
|
+
handle?.kill().catch(() => {
|
|
9579
|
+
});
|
|
9580
|
+
};
|
|
9581
|
+
if (aborted) {
|
|
9582
|
+
stdout.close();
|
|
9583
|
+
stderr.close();
|
|
9584
|
+
return abortedExitInfo2();
|
|
9585
|
+
}
|
|
9586
|
+
signal?.addEventListener("abort", abort, { once: true });
|
|
9587
|
+
try {
|
|
9588
|
+
handle = await vm.execStreamWith("sh", (builder) => {
|
|
9589
|
+
builder.args(["-lc", command]).stdinNull();
|
|
9590
|
+
if (options.cwd) builder.cwd(options.cwd);
|
|
9591
|
+
if (options.env) builder.envs(options.env);
|
|
9592
|
+
return builder;
|
|
9593
|
+
});
|
|
9594
|
+
if (aborted) {
|
|
9595
|
+
return abortedExitInfo2();
|
|
9596
|
+
}
|
|
9597
|
+
if (options.commandTimeout) {
|
|
9598
|
+
const startedHandle = handle;
|
|
9599
|
+
timeoutTimer = setTimeout(() => {
|
|
9600
|
+
timedOut = true;
|
|
9601
|
+
startedHandle.kill().catch(() => {
|
|
9602
|
+
});
|
|
9603
|
+
}, options.commandTimeout);
|
|
9604
|
+
timeoutTimer.unref();
|
|
9605
|
+
}
|
|
9606
|
+
let code = null;
|
|
9607
|
+
for await (const event of handle) {
|
|
9608
|
+
if (event.kind === "stdout") stdout.enqueue(event.data);
|
|
9609
|
+
else if (event.kind === "stderr") stderr.enqueue(event.data);
|
|
9610
|
+
else if (event.kind === "exited") code = event.code;
|
|
9611
|
+
}
|
|
9612
|
+
if (aborted) {
|
|
9613
|
+
return abortedExitInfo2();
|
|
9614
|
+
}
|
|
9615
|
+
if (timedOut) {
|
|
9616
|
+
stderr.enqueue(new TextEncoder().encode("Command timed out"));
|
|
9617
|
+
return { code: COMMAND_TIMEOUT_EXIT_CODE, signal: null, success: false };
|
|
9618
|
+
}
|
|
9619
|
+
return { code, signal: null, success: code === 0 };
|
|
9620
|
+
} catch (error) {
|
|
9621
|
+
if (aborted) {
|
|
9622
|
+
return abortedExitInfo2();
|
|
9623
|
+
}
|
|
9624
|
+
if (timedOut || error instanceof sdk.ExecTimeoutError) {
|
|
9625
|
+
stderr.enqueue(new TextEncoder().encode("Command timed out"));
|
|
9626
|
+
return { code: COMMAND_TIMEOUT_EXIT_CODE, signal: null, success: false };
|
|
9627
|
+
}
|
|
9628
|
+
const err = toError2(error);
|
|
9629
|
+
stdout.error(err);
|
|
9630
|
+
stderr.error(err);
|
|
9631
|
+
throw err;
|
|
9632
|
+
} finally {
|
|
9633
|
+
clearTimeout(timeoutTimer);
|
|
9634
|
+
signal?.removeEventListener("abort", abort);
|
|
9635
|
+
stdout.close();
|
|
9636
|
+
stderr.close();
|
|
9637
|
+
await handle?.[Symbol.asyncDispose]();
|
|
9638
|
+
}
|
|
9639
|
+
}
|
|
9640
|
+
function createByteReadable() {
|
|
9641
|
+
let controller;
|
|
9642
|
+
let closed = false;
|
|
9643
|
+
return {
|
|
9644
|
+
stream: new ReadableStream({
|
|
9645
|
+
start(streamController) {
|
|
9646
|
+
controller = streamController;
|
|
9647
|
+
},
|
|
9648
|
+
cancel() {
|
|
9649
|
+
closed = true;
|
|
9650
|
+
}
|
|
9651
|
+
}),
|
|
9652
|
+
enqueue(chunk) {
|
|
9653
|
+
if (closed || chunk.length === 0) return;
|
|
9654
|
+
controller?.enqueue(chunk);
|
|
9655
|
+
},
|
|
9656
|
+
close() {
|
|
9657
|
+
if (closed) return;
|
|
9658
|
+
closed = true;
|
|
9659
|
+
controller?.close();
|
|
9660
|
+
},
|
|
9661
|
+
error(error) {
|
|
9662
|
+
if (closed) return;
|
|
9663
|
+
closed = true;
|
|
9664
|
+
controller?.error(error);
|
|
9665
|
+
}
|
|
9666
|
+
};
|
|
9667
|
+
}
|
|
9668
|
+
async function readAllText(stream) {
|
|
9669
|
+
const decoder2 = new TextDecoder();
|
|
9670
|
+
let text = "";
|
|
9671
|
+
for await (const chunk of stream) {
|
|
9672
|
+
text += decoder2.decode(chunk, { stream: true });
|
|
9673
|
+
}
|
|
9674
|
+
return text + decoder2.decode();
|
|
9675
|
+
}
|
|
9676
|
+
function abortedCommandResult2() {
|
|
9677
|
+
return {
|
|
9678
|
+
stdout: "",
|
|
9679
|
+
stderr: "Command aborted",
|
|
9680
|
+
exitCode: 1
|
|
9681
|
+
};
|
|
9682
|
+
}
|
|
9683
|
+
function abortedExitInfo2() {
|
|
9684
|
+
return {
|
|
9685
|
+
code: null,
|
|
9686
|
+
signal: "SIGKILL",
|
|
9687
|
+
success: false
|
|
9688
|
+
};
|
|
9689
|
+
}
|
|
9690
|
+
function uniqueParentDirectories2(paths) {
|
|
9691
|
+
const dirs = /* @__PURE__ */ new Set();
|
|
9692
|
+
for (const path5 of paths) {
|
|
9693
|
+
const index = path5.lastIndexOf("/");
|
|
9694
|
+
if (index > 0) {
|
|
9695
|
+
dirs.add(path5.slice(0, index));
|
|
9696
|
+
}
|
|
9697
|
+
}
|
|
9698
|
+
return [...dirs];
|
|
9699
|
+
}
|
|
9700
|
+
function toError2(error) {
|
|
9701
|
+
return error instanceof Error ? error : new Error(String(error));
|
|
9702
|
+
}
|
|
9703
|
+
|
|
9236
9704
|
// packages/context/src/lib/sandbox/subcommand.ts
|
|
9237
9705
|
import {
|
|
9238
9706
|
defineCommand as defineCommand2,
|
|
@@ -9314,7 +9782,7 @@ async function createVirtualSandbox(options) {
|
|
|
9314
9782
|
env: options.env,
|
|
9315
9783
|
customCommands: options.customCommands
|
|
9316
9784
|
});
|
|
9317
|
-
|
|
9785
|
+
const sandbox = {
|
|
9318
9786
|
async executeCommand(command, options2) {
|
|
9319
9787
|
const result = await bash.exec(
|
|
9320
9788
|
command,
|
|
@@ -9343,6 +9811,16 @@ async function createVirtualSandbox(options) {
|
|
|
9343
9811
|
return this.dispose();
|
|
9344
9812
|
}
|
|
9345
9813
|
};
|
|
9814
|
+
if (options.readiness) {
|
|
9815
|
+
try {
|
|
9816
|
+
await options.readiness(sandbox);
|
|
9817
|
+
} catch (error) {
|
|
9818
|
+
await sandbox.dispose().catch(() => {
|
|
9819
|
+
});
|
|
9820
|
+
throw error;
|
|
9821
|
+
}
|
|
9822
|
+
}
|
|
9823
|
+
return sandbox;
|
|
9346
9824
|
}
|
|
9347
9825
|
|
|
9348
9826
|
// packages/context/src/lib/skills/fragments.ts
|
|
@@ -9806,6 +10284,18 @@ var PostgresContextStore = class _PostgresContextStore extends ContextStore {
|
|
|
9806
10284
|
);
|
|
9807
10285
|
});
|
|
9808
10286
|
}
|
|
10287
|
+
async setMessageParent(messageId, parentId) {
|
|
10288
|
+
if (parentId === messageId) {
|
|
10289
|
+
throw new Error(`Message ${messageId} cannot be its own parent`);
|
|
10290
|
+
}
|
|
10291
|
+
const rows = await this.#query(
|
|
10292
|
+
`UPDATE ${this.#t("messages")} SET parentId = $1 WHERE id = $2 RETURNING id`,
|
|
10293
|
+
[parentId, messageId]
|
|
10294
|
+
);
|
|
10295
|
+
if (rows.length === 0) {
|
|
10296
|
+
throw new Error(`Message ${messageId} not found`);
|
|
10297
|
+
}
|
|
10298
|
+
}
|
|
9809
10299
|
async getMessage(messageId) {
|
|
9810
10300
|
const rows = await this.#query(`SELECT * FROM ${this.#t("messages")} WHERE id = $1`, [messageId]);
|
|
9811
10301
|
if (rows.length === 0) {
|
|
@@ -9928,11 +10418,14 @@ var PostgresContextStore = class _PostgresContextStore extends ContextStore {
|
|
|
9928
10418
|
);
|
|
9929
10419
|
});
|
|
9930
10420
|
}
|
|
9931
|
-
async updateBranchHead(branchId, messageId) {
|
|
9932
|
-
await this.#query(
|
|
9933
|
-
`UPDATE ${this.#t("branches")} SET headMessageId = $1
|
|
9934
|
-
|
|
10421
|
+
async updateBranchHead(branchId, messageId, expectedHeadMessageId) {
|
|
10422
|
+
const rows = await this.#query(
|
|
10423
|
+
`UPDATE ${this.#t("branches")} SET headMessageId = $1
|
|
10424
|
+
WHERE id = $2 AND headMessageId IS NOT DISTINCT FROM $3
|
|
10425
|
+
RETURNING id`,
|
|
10426
|
+
[messageId, branchId, expectedHeadMessageId]
|
|
9935
10427
|
);
|
|
10428
|
+
return rows.length > 0;
|
|
9936
10429
|
}
|
|
9937
10430
|
async listBranches(chatId) {
|
|
9938
10431
|
const branches = await this.#query(
|
|
@@ -10595,6 +11088,20 @@ var SqlServerContextStore = class _SqlServerContextStore extends ContextStore {
|
|
|
10595
11088
|
`);
|
|
10596
11089
|
});
|
|
10597
11090
|
}
|
|
11091
|
+
async setMessageParent(messageId, parentId) {
|
|
11092
|
+
if (parentId === messageId) {
|
|
11093
|
+
throw new Error(`Message ${messageId} cannot be its own parent`);
|
|
11094
|
+
}
|
|
11095
|
+
const rows = await this.#query(
|
|
11096
|
+
`UPDATE ${this.#t("messages")} SET parentId = @p0
|
|
11097
|
+
OUTPUT INSERTED.id
|
|
11098
|
+
WHERE id = @p1`,
|
|
11099
|
+
[parentId, messageId]
|
|
11100
|
+
);
|
|
11101
|
+
if (rows.length === 0) {
|
|
11102
|
+
throw new Error(`Message ${messageId} not found`);
|
|
11103
|
+
}
|
|
11104
|
+
}
|
|
10598
11105
|
async getMessage(messageId) {
|
|
10599
11106
|
const rows = await this.#query(`SELECT * FROM ${this.#t("messages")} WHERE id = @p0`, [messageId]);
|
|
10600
11107
|
if (rows.length === 0) {
|
|
@@ -10720,11 +11227,15 @@ var SqlServerContextStore = class _SqlServerContextStore extends ContextStore {
|
|
|
10720
11227
|
);
|
|
10721
11228
|
});
|
|
10722
11229
|
}
|
|
10723
|
-
async updateBranchHead(branchId, messageId) {
|
|
10724
|
-
await this.#query(
|
|
10725
|
-
`UPDATE ${this.#t("branches")} SET headMessageId = @p0
|
|
10726
|
-
|
|
11230
|
+
async updateBranchHead(branchId, messageId, expectedHeadMessageId) {
|
|
11231
|
+
const rows = await this.#query(
|
|
11232
|
+
`UPDATE ${this.#t("branches")} SET headMessageId = @p0
|
|
11233
|
+
OUTPUT INSERTED.id
|
|
11234
|
+
WHERE id = @p1
|
|
11235
|
+
AND (headMessageId = @p2 OR (headMessageId IS NULL AND @p2 IS NULL))`,
|
|
11236
|
+
[messageId, branchId, expectedHeadMessageId]
|
|
10727
11237
|
);
|
|
11238
|
+
return rows.length > 0;
|
|
10728
11239
|
}
|
|
10729
11240
|
async listBranches(chatId) {
|
|
10730
11241
|
const branches = await this.#query(
|
|
@@ -12576,12 +13087,18 @@ export {
|
|
|
12576
13087
|
FunctionResolver,
|
|
12577
13088
|
GeneratorResolver,
|
|
12578
13089
|
GithubReleaseInstaller,
|
|
13090
|
+
HeadConflictError,
|
|
12579
13091
|
InMemoryContextStore,
|
|
12580
13092
|
InstallError,
|
|
12581
13093
|
Installer,
|
|
12582
13094
|
IterableResolver,
|
|
12583
13095
|
LOCALE_METADATA_KEY,
|
|
13096
|
+
MICROSANDBOX_DEFAULT_DESTINATION,
|
|
12584
13097
|
MarkdownRenderer,
|
|
13098
|
+
MicrosandboxCommandError,
|
|
13099
|
+
MicrosandboxCreationError,
|
|
13100
|
+
MicrosandboxNotAvailableError,
|
|
13101
|
+
MicrosandboxSandboxError,
|
|
12585
13102
|
MissingRuntimeError,
|
|
12586
13103
|
ModelsRegistry,
|
|
12587
13104
|
NpmInstaller,
|
|
@@ -12618,6 +13135,7 @@ export {
|
|
|
12618
13135
|
analogy,
|
|
12619
13136
|
and,
|
|
12620
13137
|
anyToolCalled,
|
|
13138
|
+
appleEngine,
|
|
12621
13139
|
applyInlineReminder,
|
|
12622
13140
|
applyPartReminder,
|
|
12623
13141
|
applyReminderToMessage,
|
|
@@ -12647,6 +13165,7 @@ export {
|
|
|
12647
13165
|
createDaytonaSandbox,
|
|
12648
13166
|
createDockerSandbox,
|
|
12649
13167
|
createInstallerContext,
|
|
13168
|
+
createMicrosandboxSandbox,
|
|
12650
13169
|
createRepairToolCall,
|
|
12651
13170
|
createVirtualSandbox,
|
|
12652
13171
|
dateReminder,
|