@codeworksh/harness 0.2.0-dev.20261013042837 → 0.2.0-dev.20261013124604
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/{daytona-ByTHZelc.mjs → daytona-D4sNwzSr.mjs} +13 -7
- package/daytona-D4sNwzSr.mjs.map +1 -0
- package/effect.d.mts +25 -2
- package/effect.mjs +304 -179
- package/effect.mjs.map +1 -1
- package/package.json +3 -3
- package/resize-D34zcVQl.mjs +461 -0
- package/resize-D34zcVQl.mjs.map +1 -0
- package/sandboxes/daytona/index.mjs +1 -1
- package/tool/image/worker.mjs +1 -1
- package/daytona-ByTHZelc.mjs.map +0 -1
- package/resize-Dwv5dCgY.mjs +0 -263
- package/resize-Dwv5dCgY.mjs.map +0 -1
package/effect.mjs
CHANGED
|
@@ -1,10 +1,10 @@
|
|
|
1
1
|
import { n as __reExport, t as __exportAll } from "./rolldown-runtime-B4FMCO8f.mjs";
|
|
2
2
|
import { a as io_exports, i as errors_exports, n as shell_exports, o as instance_exports, r as filesystem_exports, s as posix } from "./resource-DFZh0e-s.mjs";
|
|
3
|
-
import "./
|
|
3
|
+
import { a as decode, c as importModule, d as share, l as lendResolve, n as dimensionNote, o as load$5, r as resize, s as load$4, u as resolveModule } from "./resize-D34zcVQl.mjs";
|
|
4
|
+
import "./daytona-D4sNwzSr.mjs";
|
|
4
5
|
import "./vercel-3GouQSJI.mjs";
|
|
5
|
-
import {
|
|
6
|
-
import {
|
|
7
|
-
import { Cause, Clock, Config, Context, Crypto, DateTime, Deferred, Duration, Effect, Exit, Fiber, FiberSet, FileSystem, Layer, LayerMap, Option, Path, Predicate, PubSub, Queue, Random, Ref, Result, Schedule, Schema, SchemaIssue, Scope, Semaphore, Stream, String as String$1 } from "effect";
|
|
6
|
+
import { createRequire } from "node:module";
|
|
7
|
+
import { Cause, Clock, Config, Context, Crypto, Data, DateTime, Deferred, Duration, Effect, Exit, Fiber, FiberSet, FileSystem, Layer, LayerMap, Metric, Option, Path, Predicate, PubSub, Queue, Random, Ref, Result, Schedule, Schema, SchemaIssue, Scope, Semaphore, Stream, String as String$1 } from "effect";
|
|
8
8
|
import { Message, Model, getEnvApiKey, llm, normalizeOptionalNulls, stream } from "@codeworksh/aikit";
|
|
9
9
|
import { MessageID as ID, SessionID as ID$1 } from "@codeworksh/plugin/ids";
|
|
10
10
|
import { Migrator, SqlClient, SqlClient as SqlClient$1, SqlError, SqlSchema, SqlSchema as SqlSchema$1 } from "effect/sql";
|
|
@@ -16,10 +16,10 @@ import { NodeChildProcessSpawner, NodeCrypto, NodeFileSystem, NodePath } from "@
|
|
|
16
16
|
import { Model as Model$1, VariantSchema } from "effect/schema";
|
|
17
17
|
import { Hex } from "effect/encoding";
|
|
18
18
|
import { MemoryProvider, RealFSProvider, SqliteProvider, create } from "@platformatic/vfs";
|
|
19
|
-
import fs
|
|
19
|
+
import fs from "node:fs";
|
|
20
20
|
import { ChildProcess, ChildProcessSpawner } from "effect/process";
|
|
21
21
|
import { Buffer as Buffer$1 } from "node:buffer";
|
|
22
|
-
import {
|
|
22
|
+
import { fileURLToPath, pathToFileURL } from "node:url";
|
|
23
23
|
import { DirectoryNotFoundError, DirectoryNotFoundError as DirectoryNotFoundError$1, Info, Info as Info$1, NotDirectoryError, NotDirectoryError as NotDirectoryError$1, Service, Service as Service$8 } from "@codeworksh/plugin/location";
|
|
24
24
|
import { generateModels } from "@codeworksh/aikit/modelgen";
|
|
25
25
|
import { JsonGitHubCopilotAuthStorage, getGitHubCopilotApiKey } from "@codeworksh/aikit/oauth/github/copilot";
|
|
@@ -28,9 +28,6 @@ import { parse, printParseErrorCode } from "jsonc-parser";
|
|
|
28
28
|
import * as Section from "@codeworksh/plugin/plugin/section";
|
|
29
29
|
import * as Diff from "diff";
|
|
30
30
|
import { FetchHttpClient, HttpClient } from "effect/http";
|
|
31
|
-
import { fileURLToPath, pathToFileURL } from "node:url";
|
|
32
|
-
import path from "node:path";
|
|
33
|
-
import { Script, constants } from "node:vm";
|
|
34
31
|
import npa from "npm-package-arg";
|
|
35
32
|
import * as AikitFailure from "@codeworksh/aikit/failure";
|
|
36
33
|
import "@codeworksh/plugin/tool/error";
|
|
@@ -380,7 +377,7 @@ var db_exports = /* @__PURE__ */ __exportAll({
|
|
|
380
377
|
defaultLayer: () => defaultLayer$1,
|
|
381
378
|
layer: () => layer$26,
|
|
382
379
|
locationConfig: () => locationConfig,
|
|
383
|
-
path: () => path$
|
|
380
|
+
path: () => path$1,
|
|
384
381
|
resolveDatabaseLocation: () => resolveDatabaseLocation
|
|
385
382
|
});
|
|
386
383
|
const setup = Effect.gen(function* () {
|
|
@@ -407,11 +404,11 @@ function resolveDatabaseLocation(configured, data) {
|
|
|
407
404
|
if (configured === ":memory:" || posix.isAbsolute(configured)) return configured;
|
|
408
405
|
return posix.join(data, configured);
|
|
409
406
|
}
|
|
410
|
-
const path$
|
|
407
|
+
const path$1 = Effect.fn("Database.path")(function* (data) {
|
|
411
408
|
const directory = data ?? (yield* resolve$4()).data;
|
|
412
409
|
return resolveDatabaseLocation(yield* locationConfig, directory);
|
|
413
410
|
});
|
|
414
|
-
const defaultLayer$1 = Layer.unwrap(path$
|
|
411
|
+
const defaultLayer$1 = Layer.unwrap(path$1().pipe(Effect.map(layer$26)));
|
|
415
412
|
//#endregion
|
|
416
413
|
//#region src/event/schema.ts
|
|
417
414
|
var schema_exports$7 = /* @__PURE__ */ __exportAll({});
|
|
@@ -2643,6 +2640,114 @@ const layer$22 = Layer.effect(Service$13, Effect.gen(function* () {
|
|
|
2643
2640
|
return Service$13.of({ assemble });
|
|
2644
2641
|
}));
|
|
2645
2642
|
//#endregion
|
|
2643
|
+
//#region src/telemetry/telemetry.ts
|
|
2644
|
+
const durationBuckets = Metric.boundariesFromIterable([
|
|
2645
|
+
.01,
|
|
2646
|
+
.02,
|
|
2647
|
+
.04,
|
|
2648
|
+
.08,
|
|
2649
|
+
.16,
|
|
2650
|
+
.32,
|
|
2651
|
+
.64,
|
|
2652
|
+
1.28,
|
|
2653
|
+
2.56,
|
|
2654
|
+
5.12,
|
|
2655
|
+
10.24,
|
|
2656
|
+
20.48,
|
|
2657
|
+
40.96,
|
|
2658
|
+
81.92
|
|
2659
|
+
]);
|
|
2660
|
+
const llmDuration = Metric.histogram("codework.llm.duration", {
|
|
2661
|
+
description: "Provider request duration",
|
|
2662
|
+
attributes: { unit: "s" },
|
|
2663
|
+
boundaries: durationBuckets
|
|
2664
|
+
});
|
|
2665
|
+
const llmTtft = Metric.histogram("codework.llm.ttft", {
|
|
2666
|
+
description: "Time to first token: from request start to the first streamed content",
|
|
2667
|
+
attributes: { unit: "s" },
|
|
2668
|
+
boundaries: Metric.boundariesFromIterable([
|
|
2669
|
+
.001,
|
|
2670
|
+
.005,
|
|
2671
|
+
.01,
|
|
2672
|
+
.02,
|
|
2673
|
+
.04,
|
|
2674
|
+
.06,
|
|
2675
|
+
.08,
|
|
2676
|
+
.1,
|
|
2677
|
+
.25,
|
|
2678
|
+
.5,
|
|
2679
|
+
.75,
|
|
2680
|
+
1,
|
|
2681
|
+
2.5,
|
|
2682
|
+
5,
|
|
2683
|
+
7.5,
|
|
2684
|
+
10
|
|
2685
|
+
])
|
|
2686
|
+
});
|
|
2687
|
+
const llmTokens = Metric.counter("codework.llm.tokens", {
|
|
2688
|
+
description: "Tokens used, by type; cache and reasoning tokens are part of input and output",
|
|
2689
|
+
attributes: { unit: "{token}" },
|
|
2690
|
+
incremental: true
|
|
2691
|
+
});
|
|
2692
|
+
const llmCost = Metric.counter("codework.llm.cost", {
|
|
2693
|
+
description: "Provider request cost from the model catalog's prices",
|
|
2694
|
+
attributes: { unit: "USD" },
|
|
2695
|
+
incremental: true
|
|
2696
|
+
});
|
|
2697
|
+
const agentDuration = Metric.histogram("codework.agent.duration", {
|
|
2698
|
+
description: "Session run duration, across every turn it drains",
|
|
2699
|
+
attributes: { unit: "s" },
|
|
2700
|
+
boundaries: Metric.boundariesFromIterable([
|
|
2701
|
+
.1,
|
|
2702
|
+
.2,
|
|
2703
|
+
.4,
|
|
2704
|
+
.8,
|
|
2705
|
+
1.6,
|
|
2706
|
+
3.2,
|
|
2707
|
+
6.4,
|
|
2708
|
+
12.8,
|
|
2709
|
+
25.6,
|
|
2710
|
+
51.2,
|
|
2711
|
+
102.4,
|
|
2712
|
+
204.8,
|
|
2713
|
+
409.6
|
|
2714
|
+
])
|
|
2715
|
+
});
|
|
2716
|
+
const toolDuration = Metric.histogram("codework.tool.duration", {
|
|
2717
|
+
description: "Tool execution duration",
|
|
2718
|
+
attributes: { unit: "s" },
|
|
2719
|
+
boundaries: durationBuckets
|
|
2720
|
+
});
|
|
2721
|
+
const sandboxProvisionDuration = Metric.histogram("codework.sandbox.provision.duration", {
|
|
2722
|
+
description: "Sandbox driver create and wake duration",
|
|
2723
|
+
attributes: { unit: "s" },
|
|
2724
|
+
boundaries: durationBuckets
|
|
2725
|
+
});
|
|
2726
|
+
const sandboxExecDuration = Metric.histogram("codework.sandbox.exec.duration", {
|
|
2727
|
+
description: "Sandbox shell command duration",
|
|
2728
|
+
attributes: { unit: "s" },
|
|
2729
|
+
boundaries: durationBuckets
|
|
2730
|
+
});
|
|
2731
|
+
const sandboxActive = Metric.gauge("codework.sandbox.active", {
|
|
2732
|
+
description: "Managed and remote sandboxes with at least one mount",
|
|
2733
|
+
attributes: { unit: "{sandbox}" }
|
|
2734
|
+
});
|
|
2735
|
+
const record$1 = (metric, value, attributes) => Metric.update(Metric.withAttributes(metric, attributes), value);
|
|
2736
|
+
const adjust = (metric, delta, attributes) => Metric.modify(Metric.withAttributes(metric, attributes), delta);
|
|
2737
|
+
const errorType = (cause) => {
|
|
2738
|
+
if (Cause.hasInterruptsOnly(cause)) return "interrupted";
|
|
2739
|
+
const error = Cause.squash(cause);
|
|
2740
|
+
return typeof error === "object" && error !== null && "_tag" in error && typeof error._tag === "string" ? error._tag : "_OTHER";
|
|
2741
|
+
};
|
|
2742
|
+
const withError = (attributes, exit) => Exit.isSuccess(exit) ? attributes : {
|
|
2743
|
+
...attributes,
|
|
2744
|
+
error: errorType(exit.cause)
|
|
2745
|
+
};
|
|
2746
|
+
const timed = (self, observe) => Effect.clockWith((clock) => {
|
|
2747
|
+
const start = clock.currentTimeMillisUnsafe();
|
|
2748
|
+
return self.pipe(Effect.onExit((exit) => observe((clock.currentTimeMillisUnsafe() - start) / 1e3, exit)));
|
|
2749
|
+
});
|
|
2750
|
+
//#endregion
|
|
2646
2751
|
//#region src/sandbox/driver.ts
|
|
2647
2752
|
var driver_exports = /* @__PURE__ */ __exportAll({});
|
|
2648
2753
|
import * as import__codeworksh_plugin_sandbox_driver from "@codeworksh/plugin/sandbox/driver";
|
|
@@ -3029,6 +3134,22 @@ const parseJson = (driver, operation, value) => decodeUnknownJson(value).pipe(Ef
|
|
|
3029
3134
|
operation,
|
|
3030
3135
|
cause
|
|
3031
3136
|
})));
|
|
3137
|
+
const provision = (driver, operation, self) => timed(self, (seconds, exit) => record$1(sandboxProvisionDuration, seconds, withError({
|
|
3138
|
+
driver,
|
|
3139
|
+
operation
|
|
3140
|
+
}, exit)));
|
|
3141
|
+
const timedShell = (shell, driver) => {
|
|
3142
|
+
const time = (self) => timed(self, (seconds, exit) => record$1(sandboxExecDuration, seconds, withError({ driver }, exit)));
|
|
3143
|
+
const stream = shell.stream;
|
|
3144
|
+
return {
|
|
3145
|
+
exec: (command, options) => time(shell.exec(command, options)),
|
|
3146
|
+
execArgv: (argv, options) => time(shell.execArgv(argv, options)),
|
|
3147
|
+
...stream === void 0 ? {} : { stream: (command, options) => Stream.unwrap(Effect.clockWith((clock) => {
|
|
3148
|
+
const start = clock.currentTimeMillisUnsafe();
|
|
3149
|
+
return Effect.succeed(stream(command, options).pipe(Stream.onExit((exit) => record$1(sandboxExecDuration, (clock.currentTimeMillisUnsafe() - start) / 1e3, withError({ driver }, exit)))));
|
|
3150
|
+
})) }
|
|
3151
|
+
};
|
|
3152
|
+
};
|
|
3032
3153
|
const make$14 = Effect.fn("Sandbox.Controller.make")(function* (options) {
|
|
3033
3154
|
const sql = yield* SqlClient.SqlClient;
|
|
3034
3155
|
const registry = yield* Registry;
|
|
@@ -3039,20 +3160,22 @@ const make$14 = Effect.fn("Sandbox.Controller.make")(function* (options) {
|
|
|
3039
3160
|
const hostCreatedAt = asDate(yield* DateTime.now);
|
|
3040
3161
|
const refCount = (id) => refs.get(id) ?? 0;
|
|
3041
3162
|
const usage = (id, count = refCount(id)) => id === instance_exports.SandboxInstance.ID.local ? "pinned" : count > 0 ? "busy" : "idle";
|
|
3163
|
+
const activeChanged = (lease, delta) => lease.driver === void 0 ? Effect.void : adjust(sandboxActive, delta, { driver: lease.driver });
|
|
3042
3164
|
const acquireLease = (id, lease) => gate.withPermits(1)(Effect.sync(() => {
|
|
3043
3165
|
const wasIdle = refCount(id) === 0;
|
|
3044
3166
|
refs.set(id, refCount(id) + 1);
|
|
3045
3167
|
lease.held = true;
|
|
3046
3168
|
return wasIdle;
|
|
3047
|
-
}));
|
|
3169
|
+
})).pipe(Effect.tap((wasIdle) => wasIdle ? activeChanged(lease, 1) : Effect.void));
|
|
3048
3170
|
const releaseLease = (id, lease) => Effect.gen(function* () {
|
|
3049
3171
|
if (!lease.held) return;
|
|
3050
|
-
yield* gate.withPermits(1)(Effect.sync(() => {
|
|
3172
|
+
if (yield* gate.withPermits(1)(Effect.sync(() => {
|
|
3051
3173
|
const next = Math.max(0, refCount(id) - 1);
|
|
3052
3174
|
if (next === 0) refs.delete(id);
|
|
3053
3175
|
else refs.set(id, next);
|
|
3054
3176
|
lease.held = false;
|
|
3055
|
-
|
|
3177
|
+
return next === 0;
|
|
3178
|
+
}))) yield* activeChanged(lease, -1);
|
|
3056
3179
|
if (!lease.mounted) return;
|
|
3057
3180
|
const now = yield* Effect.clockWith((clock) => clock.currentTimeMillis);
|
|
3058
3181
|
yield* sql`
|
|
@@ -3222,7 +3345,7 @@ const make$14 = Effect.fn("Sandbox.Controller.make")(function* (options) {
|
|
|
3222
3345
|
const attached = yield* runtime(row, "resolveCwd");
|
|
3223
3346
|
return driver_exports.SandboxDriver.AbsolutePath.make(io_exports.SandboxIO.resolveMountCwd(attached.input.runtimeConfig.defaultCwd, override));
|
|
3224
3347
|
});
|
|
3225
|
-
const create = Effect.fn("Sandbox.Controller.create")(function* (input) {
|
|
3348
|
+
const create = Effect.fn("Sandbox.Controller.create", { level: "Info" })(function* (input) {
|
|
3226
3349
|
const driver = yield* registry.get(input.driver.name);
|
|
3227
3350
|
const config = yield* registry.decodeCreateConfig(input.driver.name, input.config);
|
|
3228
3351
|
const id = input.instanceId ?? instance_exports.SandboxInstance.ID.create();
|
|
@@ -3238,10 +3361,10 @@ const make$14 = Effect.fn("Sandbox.Controller.make")(function* (options) {
|
|
|
3238
3361
|
status: "provisioning",
|
|
3239
3362
|
metadata: input.metadata
|
|
3240
3363
|
});
|
|
3241
|
-
const provisioned = yield* driver.create({
|
|
3364
|
+
const provisioned = yield* provision(driver.name, "create", driver.create({
|
|
3242
3365
|
instanceId: id,
|
|
3243
3366
|
config
|
|
3244
|
-
}).pipe(Effect.catch((error) => persistProviderFailure(id, "faulted", error)));
|
|
3367
|
+
})).pipe(Effect.catch((error) => persistProviderFailure(id, "faulted", error)));
|
|
3245
3368
|
return yield* Effect.gen(function* () {
|
|
3246
3369
|
const encoded = yield* registry.encodeRuntimeConfig(driver.name, provisioned.runtimeConfig);
|
|
3247
3370
|
const runtimeConfig = yield* encodeUnknownJson$1(encoded).pipe(Effect.mapError((cause) => (0, errors_exports.providerError)({
|
|
@@ -3330,7 +3453,8 @@ const make$14 = Effect.fn("Sandbox.Controller.make")(function* (options) {
|
|
|
3330
3453
|
let invalidateBeforeAttach = false;
|
|
3331
3454
|
const lease = reserved ?? {
|
|
3332
3455
|
held: false,
|
|
3333
|
-
mounted: false
|
|
3456
|
+
mounted: false,
|
|
3457
|
+
driver: void 0
|
|
3334
3458
|
};
|
|
3335
3459
|
if (id === instance_exports.SandboxInstance.ID.local) identity = {
|
|
3336
3460
|
id,
|
|
@@ -3355,6 +3479,7 @@ const make$14 = Effect.fn("Sandbox.Controller.make")(function* (options) {
|
|
|
3355
3479
|
});
|
|
3356
3480
|
invalidateBeforeAttach = row.status !== "online";
|
|
3357
3481
|
const attached = yield* runtime(row, "mount");
|
|
3482
|
+
lease.driver = attached.driver.name;
|
|
3358
3483
|
identity = {
|
|
3359
3484
|
id,
|
|
3360
3485
|
driver: attached.driver.name,
|
|
@@ -3377,7 +3502,10 @@ const make$14 = Effect.fn("Sandbox.Controller.make")(function* (options) {
|
|
|
3377
3502
|
lease.held = true;
|
|
3378
3503
|
return idle;
|
|
3379
3504
|
}));
|
|
3380
|
-
if (reserved === void 0)
|
|
3505
|
+
if (reserved === void 0) {
|
|
3506
|
+
yield* Effect.addFinalizer(() => releaseLease(id, lease));
|
|
3507
|
+
if (wasIdle) yield* activeChanged(lease, 1);
|
|
3508
|
+
}
|
|
3381
3509
|
if (wasIdle && invalidateBeforeAttach) yield* transports.invalidate(id);
|
|
3382
3510
|
}
|
|
3383
3511
|
const handleTransportError = (error) => {
|
|
@@ -3407,7 +3535,7 @@ const make$14 = Effect.fn("Sandbox.Controller.make")(function* (options) {
|
|
|
3407
3535
|
WHERE id = ${id}
|
|
3408
3536
|
`.pipe(Effect.orDie);
|
|
3409
3537
|
}
|
|
3410
|
-
return Layer.mergeAll(Layer.succeed(io_exports.SandboxIO.Current, identity), Layer.succeed(io_exports.SandboxIO.FileSystem, filesystem_exports.SandboxFileSystem.withCwd(fs, identity.cwd)), Layer.succeed(io_exports.SandboxIO.Shell, (0, shell_exports.withCwd)(shell, identity.cwd))).pipe(io_exports.SandboxIO.withMutation);
|
|
3538
|
+
return Layer.mergeAll(Layer.succeed(io_exports.SandboxIO.Current, identity), Layer.succeed(io_exports.SandboxIO.FileSystem, filesystem_exports.SandboxFileSystem.withCwd(fs, identity.cwd)), Layer.succeed(io_exports.SandboxIO.Shell, timedShell((0, shell_exports.withCwd)(shell, identity.cwd), identity.driver))).pipe(io_exports.SandboxIO.withMutation);
|
|
3411
3539
|
}));
|
|
3412
3540
|
const mount = (id, mountOptions) => mountLayer(id, mountOptions);
|
|
3413
3541
|
const withMount = (id, use, mountOptions) => use.pipe(Effect.provide(mount(id, mountOptions)), Effect.scoped);
|
|
@@ -3434,7 +3562,7 @@ const make$14 = Effect.fn("Sandbox.Controller.make")(function* (options) {
|
|
|
3434
3562
|
});
|
|
3435
3563
|
return yield* reload(id);
|
|
3436
3564
|
});
|
|
3437
|
-
const wake = Effect.fn("Sandbox.Controller.wake")(function* (id) {
|
|
3565
|
+
const wake = Effect.fn("Sandbox.Controller.wake", { level: "Info" })(function* (id) {
|
|
3438
3566
|
if (id === instance_exports.SandboxInstance.ID.local) return hostInfo();
|
|
3439
3567
|
const row = yield* requireRow(id);
|
|
3440
3568
|
if (row.status === "removed") return yield* new errors_exports.SandboxRemovedError({
|
|
@@ -3448,7 +3576,7 @@ const make$14 = Effect.fn("Sandbox.Controller.make")(function* (options) {
|
|
|
3448
3576
|
operation: "wake"
|
|
3449
3577
|
});
|
|
3450
3578
|
if (refCount(id) === 0) yield* transports.invalidate(id);
|
|
3451
|
-
const observed = yield* attached.driver.wake(attached.input).pipe(Effect.catch((error) => (0, errors_exports.providerErrorIsNotFound)(error) ? markUnavailable(id, error) : persistProviderFailure(id, "faulted", error)));
|
|
3579
|
+
const observed = yield* provision(attached.driver.name, "wake", attached.driver.wake(attached.input)).pipe(Effect.catch((error) => (0, errors_exports.providerErrorIsNotFound)(error) ? markUnavailable(id, error) : persistProviderFailure(id, "faulted", error)));
|
|
3452
3580
|
yield* updateObservation({
|
|
3453
3581
|
id,
|
|
3454
3582
|
status: observed.status,
|
|
@@ -3607,7 +3735,8 @@ const make$14 = Effect.fn("Sandbox.Controller.make")(function* (options) {
|
|
|
3607
3735
|
const id = input.instanceId ?? instance_exports.SandboxInstance.ID.create();
|
|
3608
3736
|
const lease = {
|
|
3609
3737
|
held: false,
|
|
3610
|
-
mounted: false
|
|
3738
|
+
mounted: false,
|
|
3739
|
+
driver: input.driver.name
|
|
3611
3740
|
};
|
|
3612
3741
|
return Layer.unwrap(Effect.gen(function* () {
|
|
3613
3742
|
yield* acquireLease(id, lease);
|
|
@@ -3875,7 +4004,8 @@ const fromBash = (bash) => {
|
|
|
3875
4004
|
});
|
|
3876
4005
|
return shell_exports.Shell.of((0, shell_exports.fromExec)({ exec }));
|
|
3877
4006
|
};
|
|
3878
|
-
const
|
|
4007
|
+
const JustBash = load$4("just-bash").pipe(Effect.map((module) => module), Effect.orDie);
|
|
4008
|
+
const make$12 = (module, vfs, cwd) => fromBash(new module.Bash({
|
|
3879
4009
|
fs: bridge(vfs, cwd),
|
|
3880
4010
|
cwd
|
|
3881
4011
|
}));
|
|
@@ -3884,9 +4014,10 @@ const make$12 = (vfs, cwd) => fromBash(new Bash({
|
|
|
3884
4014
|
* mount binds its cwd. This matches Flue's BashFactory ownership: mounts share
|
|
3885
4015
|
* the VFS, but shell state (functions, options, command hashes) is mount-local.
|
|
3886
4016
|
*/
|
|
3887
|
-
const transport$1 = (inner) => Layer.provideMerge(Layer.effect(shell_exports.Shell, Effect.
|
|
3888
|
-
const
|
|
3889
|
-
|
|
4017
|
+
const transport$1 = (inner) => Layer.provideMerge(Layer.effect(shell_exports.Shell, Effect.gen(function* () {
|
|
4018
|
+
const module = yield* JustBash;
|
|
4019
|
+
const vfs = yield* Vfs;
|
|
4020
|
+
return (0, shell_exports.perMount)(make$12(module, vfs, "/"), (cwd) => make$12(module, vfs, cwd));
|
|
3890
4021
|
})), inner);
|
|
3891
4022
|
//#endregion
|
|
3892
4023
|
//#region src/sandbox/virtual.ts
|
|
@@ -5650,7 +5781,7 @@ const ancestors = (directory) => {
|
|
|
5650
5781
|
* Which of `paths` are files. Absence is the expected answer and stays silent; any other failure
|
|
5651
5782
|
* (permissions, a remote blip) is logged so a dropped file is not a mystery, then counts as absent.
|
|
5652
5783
|
*/
|
|
5653
|
-
const present$1 = (fs, paths) => Effect.forEach(paths, (path) => fs.stat(path).pipe(Effect.map((stat) => stat.isFile), Effect.catch((error) => filesystem_exports.SandboxFileSystem.isNotFoundError(error.cause) ? Effect.succeed(false) : Effect.logWarning(`could not stat instruction file ${path}`, error.cause).pipe(Effect.as(false)))), { concurrency: "unbounded" }).pipe(Effect.map((hits) => new Set(paths.filter((_, index) => hits[index]))));
|
|
5784
|
+
const present$1 = (fs, paths) => Effect.forEach(paths, (path) => fs.exists(path).pipe(Effect.flatMap((exists) => exists ? fs.stat(path).pipe(Effect.map((stat) => stat.isFile)) : Effect.succeed(false)), Effect.catch((error) => filesystem_exports.SandboxFileSystem.isNotFoundError(error.cause) ? Effect.succeed(false) : Effect.logWarning(`could not stat instruction file ${path}`, error.cause).pipe(Effect.as(false)))), { concurrency: "unbounded" }).pipe(Effect.map((hits) => new Set(paths.filter((_, index) => hits[index]))));
|
|
5654
5785
|
/** A file that stats but does not read falls through to the next candidate. */
|
|
5655
5786
|
const first = Effect.fnUntraced(function* (fs, directory, files) {
|
|
5656
5787
|
for (const name of names) {
|
|
@@ -6002,7 +6133,7 @@ var Accumulator = class {
|
|
|
6002
6133
|
//#endregion
|
|
6003
6134
|
//#region src/tool/output.ts
|
|
6004
6135
|
/** A new, unused output file path under `spillPath`. */
|
|
6005
|
-
const path
|
|
6136
|
+
const path = (spillPath, prefix) => crypto.randomBytes(8).pipe(Effect.map((bytes) => posix.join(spillPath, `${prefix}-${Hex.encode(bytes)}.log`)), Effect.orDie);
|
|
6006
6137
|
/** First line printed when the output file cannot be created; the command then runs unsaved. */
|
|
6007
6138
|
const unsaved = (file) => `codework: output not saved, cannot create ${file}`;
|
|
6008
6139
|
const HEADER = "codework-output";
|
|
@@ -6390,7 +6521,7 @@ const runStreaming = (shell, stream, params, file) => Effect.gen(function* () {
|
|
|
6390
6521
|
});
|
|
6391
6522
|
const bashHandler = (params) => Effect.gen(function* () {
|
|
6392
6523
|
const shell = yield* ToolShell;
|
|
6393
|
-
const file = yield* path
|
|
6524
|
+
const file = yield* path((yield* io_exports.SandboxIO.Current).spillPath, "codework-bash");
|
|
6394
6525
|
return yield* (shell.stream !== void 0 ? runStreaming(shell, shell.stream, params, file) : runBuffered(shell, params, file)).pipe(Effect.onInterrupt(() => cleanUp(shell, file, {
|
|
6395
6526
|
output: "",
|
|
6396
6527
|
truncated: false
|
|
@@ -7220,7 +7351,7 @@ const grepHandler = (params) => Effect.gen(function* () {
|
|
|
7220
7351
|
const isDirectory = stat.value.isDirectory;
|
|
7221
7352
|
const context = params.context && params.context > 0 ? Math.trunc(params.context) : 0;
|
|
7222
7353
|
const limit = Math.max(1, Math.trunc(params.limit ?? DEFAULT_LIMIT$1));
|
|
7223
|
-
const errors = yield* path
|
|
7354
|
+
const errors = yield* path(sandbox.spillPath, "codework-grep");
|
|
7224
7355
|
const run = yield* withCommand("rg", sandbox, shell, fs, (command) => Effect.gen(function* () {
|
|
7225
7356
|
const argv = [
|
|
7226
7357
|
command,
|
|
@@ -7495,7 +7626,7 @@ const INLINE = /* @__PURE__ */ new Set([
|
|
|
7495
7626
|
"image/gif",
|
|
7496
7627
|
"image/webp"
|
|
7497
7628
|
]);
|
|
7498
|
-
const toPng = (bytes) => load$
|
|
7629
|
+
const toPng = (bytes) => load$5.pipe(Effect.map((photon) => {
|
|
7499
7630
|
if (photon === void 0) return void 0;
|
|
7500
7631
|
try {
|
|
7501
7632
|
const image = decode(photon, bytes);
|
|
@@ -7803,124 +7934,6 @@ const builtins = Object.freeze([
|
|
|
7803
7934
|
instructionPlugin
|
|
7804
7935
|
]);
|
|
7805
7936
|
//#endregion
|
|
7806
|
-
//#region src/util/module.ts
|
|
7807
|
-
/*!
|
|
7808
|
-
* Adapted from OpenCode packages/util/src/runtime/import.node.ts.
|
|
7809
|
-
*
|
|
7810
|
-
* MIT License
|
|
7811
|
-
*
|
|
7812
|
-
* Copyright (c) 2025 opencode
|
|
7813
|
-
*
|
|
7814
|
-
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
7815
|
-
* of this software and associated documentation files (the "Software"), to deal
|
|
7816
|
-
* in the Software without restriction, including without limitation the rights
|
|
7817
|
-
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
7818
|
-
* copies of the Software, and to permit persons to whom the Software is
|
|
7819
|
-
* furnished to do so, subject to the following conditions:
|
|
7820
|
-
*
|
|
7821
|
-
* The above copyright notice and this permission notice shall be included in all
|
|
7822
|
-
* copies or substantial portions of the Software.
|
|
7823
|
-
*
|
|
7824
|
-
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
7825
|
-
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
7826
|
-
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
7827
|
-
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
7828
|
-
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
7829
|
-
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
7830
|
-
* SOFTWARE.
|
|
7831
|
-
*/
|
|
7832
|
-
/**
|
|
7833
|
-
* Packages a plugin must share with the harness instead of using the copy installed beside it.
|
|
7834
|
-
*
|
|
7835
|
-
* A plugin is installed into the store as its own npm tree, so `effect` and the plugin SDK land
|
|
7836
|
-
* there a second time. Two copies of the *same version* are still two module instances, and
|
|
7837
|
-
* Effect Schema's checks do not survive the crossing: a schema built by one copy and evaluated by
|
|
7838
|
-
* the other reports every check as failed, so a tool whose success type is `Schema.Finite` dies
|
|
7839
|
-
* on "Expected a finite number" for `22800`. Nothing about that is visible at registration --
|
|
7840
|
-
* `Schema.isSchema` passes, the JSON Schema is derived correctly, and the tool reaches the model
|
|
7841
|
-
* -- so it surfaces on the first call rather than at boot.
|
|
7842
|
-
*
|
|
7843
|
-
* Resolution is the right place to fix it. A symlink into the store cannot be: a generation is
|
|
7844
|
-
* immutable and shared by every project on the machine, while the harness doing the loading is
|
|
7845
|
-
* whichever one is running now, and two applications embedding the harness need not agree on
|
|
7846
|
-
* where their `effect` lives.
|
|
7847
|
-
*/
|
|
7848
|
-
const sharedPackages = /* @__PURE__ */ new Set(["effect", "@codeworksh/plugin"]);
|
|
7849
|
-
/** The package a bare specifier names: `effect/Schema` -> `effect`, `@a/b/c` -> `@a/b`. */
|
|
7850
|
-
function packageOf(specifier) {
|
|
7851
|
-
if (specifier.startsWith(".") || specifier.startsWith("/") || specifier.includes(":")) return "";
|
|
7852
|
-
const segments = specifier.split("/");
|
|
7853
|
-
return specifier.startsWith("@") ? segments.slice(0, 2).join("/") : segments[0] ?? "";
|
|
7854
|
-
}
|
|
7855
|
-
/**
|
|
7856
|
-
* Resolve the shared packages as though this module had imported them, for as long as `run`
|
|
7857
|
-
* takes. Anything else resolves exactly as it would have.
|
|
7858
|
-
*/
|
|
7859
|
-
function withSharedModules(run) {
|
|
7860
|
-
const hook = registerHooks({ resolve(specifier, context, nextResolve) {
|
|
7861
|
-
return sharedPackages.has(packageOf(specifier)) ? nextResolve(specifier, {
|
|
7862
|
-
...context,
|
|
7863
|
-
parentURL: import.meta.url
|
|
7864
|
-
}) : nextResolve(specifier, context);
|
|
7865
|
-
} });
|
|
7866
|
-
return run().finally(() => hook.deregister());
|
|
7867
|
-
}
|
|
7868
|
-
/** Use Node's main loader even when the caller runs inside a bundler or test VM. */
|
|
7869
|
-
async function importModule(specifier) {
|
|
7870
|
-
const imported = await withSharedModules(() => new Script(`import(${JSON.stringify(specifier)})`, { importModuleDynamically: constants.USE_MAIN_CONTEXT_DEFAULT_LOADER }).runInThisContext());
|
|
7871
|
-
if (typeof imported !== "object" || imported === null) return imported;
|
|
7872
|
-
const module = imported;
|
|
7873
|
-
const exports = module["module.exports"];
|
|
7874
|
-
if (exports !== module.default || typeof exports !== "object" && typeof exports !== "function" || exports === null) return imported;
|
|
7875
|
-
return Object.assign({}, module, exports);
|
|
7876
|
-
}
|
|
7877
|
-
/** Node resolution scoped synchronously to the caller. */
|
|
7878
|
-
function resolveModule(specifier, directory, conditions) {
|
|
7879
|
-
const hook = registerHooks({ resolve(target, context, nextResolve) {
|
|
7880
|
-
return nextResolve(target, {
|
|
7881
|
-
...context,
|
|
7882
|
-
parentURL: pathToFileURL(path.join(directory, "package.json")).href,
|
|
7883
|
-
...conditions === void 0 ? {} : { conditions: [.../* @__PURE__ */ new Set([...context.conditions, ...conditions])] }
|
|
7884
|
-
});
|
|
7885
|
-
} });
|
|
7886
|
-
try {
|
|
7887
|
-
const resolve = (target) => {
|
|
7888
|
-
const resolved = import.meta.resolve(path.isAbsolute(target) ? pathToFileURL(target).href : target);
|
|
7889
|
-
if (resolved.startsWith("file:")) statSync(new URL(resolved));
|
|
7890
|
-
return resolved;
|
|
7891
|
-
};
|
|
7892
|
-
try {
|
|
7893
|
-
return resolve(specifier);
|
|
7894
|
-
} catch (error) {
|
|
7895
|
-
if (path.extname(specifier) || !missing(error)) throw error;
|
|
7896
|
-
for (const extension of [
|
|
7897
|
-
".ts",
|
|
7898
|
-
".tsx",
|
|
7899
|
-
".js",
|
|
7900
|
-
".jsx",
|
|
7901
|
-
".mts",
|
|
7902
|
-
".mjs",
|
|
7903
|
-
".cts",
|
|
7904
|
-
".cjs"
|
|
7905
|
-
]) try {
|
|
7906
|
-
return resolve(specifier + extension);
|
|
7907
|
-
} catch (cause) {
|
|
7908
|
-
if (!missing(cause)) throw cause;
|
|
7909
|
-
}
|
|
7910
|
-
throw error;
|
|
7911
|
-
}
|
|
7912
|
-
} finally {
|
|
7913
|
-
hook.deregister();
|
|
7914
|
-
}
|
|
7915
|
-
}
|
|
7916
|
-
function missing(error) {
|
|
7917
|
-
return error instanceof Error && "code" in error && [
|
|
7918
|
-
"ENOENT",
|
|
7919
|
-
"ENOTDIR",
|
|
7920
|
-
"ERR_MODULE_NOT_FOUND"
|
|
7921
|
-
].includes(String(error.code));
|
|
7922
|
-
}
|
|
7923
|
-
//#endregion
|
|
7924
7937
|
//#region src/plugin/error.ts
|
|
7925
7938
|
/**
|
|
7926
7939
|
* The reference as the person wrote it -- the string they will recognise in their settings file,
|
|
@@ -9800,31 +9813,116 @@ const openWith = (options = {}) => Effect.fn("LLM.open")(function* (input, signa
|
|
|
9800
9813
|
});
|
|
9801
9814
|
});
|
|
9802
9815
|
const open = openWith();
|
|
9816
|
+
const isProviderError = Schema.is(ProviderError);
|
|
9817
|
+
/** `error.type` for a request: the provider's failure reason, so a terminal and a thrown failure agree. */
|
|
9818
|
+
const requestErrorType = (input, exit) => {
|
|
9819
|
+
if (Exit.isFailure(exit)) {
|
|
9820
|
+
const error = Cause.squash(exit.cause);
|
|
9821
|
+
return isProviderError(error) ? error.reason._tag : errorType(exit.cause);
|
|
9822
|
+
}
|
|
9823
|
+
if (exit.value.outcome === "ended") return void 0;
|
|
9824
|
+
if (exit.value.reason === "aborted") return "aborted";
|
|
9825
|
+
return providerError(input, messageFailure(exit.value.message)).reason._tag;
|
|
9826
|
+
};
|
|
9827
|
+
const observe = Effect.fnUntraced(function* (input, timing, exit, drained) {
|
|
9828
|
+
const now = yield* Effect.clockWith((clock) => clock.currentTimeMillis);
|
|
9829
|
+
const labels = {
|
|
9830
|
+
provider: input.provider,
|
|
9831
|
+
model: input.model
|
|
9832
|
+
};
|
|
9833
|
+
const errorType = requestErrorType(input, exit);
|
|
9834
|
+
yield* record$1(llmDuration, (now - timing.start) / 1e3, errorType === void 0 ? labels : {
|
|
9835
|
+
...labels,
|
|
9836
|
+
error: errorType
|
|
9837
|
+
});
|
|
9838
|
+
if (timing.firstToken !== void 0) {
|
|
9839
|
+
const ttft = (timing.firstToken - timing.start) / 1e3;
|
|
9840
|
+
yield* record$1(llmTtft, ttft, labels);
|
|
9841
|
+
yield* Effect.annotateCurrentSpan("gen_ai.response.time_to_first_chunk", ttft);
|
|
9842
|
+
}
|
|
9843
|
+
if (errorType !== void 0) yield* Effect.annotateCurrentSpan("error.type", errorType);
|
|
9844
|
+
const terminal = Exit.isSuccess(exit) ? exit.value : drained;
|
|
9845
|
+
if (terminal === void 0) return;
|
|
9846
|
+
const { message } = terminal;
|
|
9847
|
+
const { usage } = message;
|
|
9848
|
+
const inputTokens = usage.input + usage.cacheRead + usage.cacheWrite;
|
|
9849
|
+
const tokens = {
|
|
9850
|
+
input: inputTokens,
|
|
9851
|
+
output: usage.output,
|
|
9852
|
+
cache_read: usage.cacheRead,
|
|
9853
|
+
cache_write: usage.cacheWrite,
|
|
9854
|
+
reasoning: usage.reasoning ?? 0
|
|
9855
|
+
};
|
|
9856
|
+
for (const [type, count] of Object.entries(tokens)) if (count > 0) yield* record$1(llmTokens, count, {
|
|
9857
|
+
...labels,
|
|
9858
|
+
type
|
|
9859
|
+
});
|
|
9860
|
+
if (usage.cost.total > 0) yield* record$1(llmCost, usage.cost.total, labels);
|
|
9861
|
+
yield* Effect.annotateCurrentSpan({
|
|
9862
|
+
"gen_ai.response.model": message.responseModel ?? message.model,
|
|
9863
|
+
...message.responseId === void 0 ? {} : { "gen_ai.response.id": message.responseId },
|
|
9864
|
+
"gen_ai.response.finish_reasons": [terminal.reason],
|
|
9865
|
+
"gen_ai.usage.input_tokens": inputTokens,
|
|
9866
|
+
"gen_ai.usage.output_tokens": usage.output,
|
|
9867
|
+
"gen_ai.usage.cache_read.input_tokens": usage.cacheRead,
|
|
9868
|
+
"gen_ai.usage.cache_write.input_tokens": usage.cacheWrite,
|
|
9869
|
+
...usage.reasoning === void 0 ? {} : { "gen_ai.usage.reasoning.output_tokens": usage.reasoning }
|
|
9870
|
+
});
|
|
9871
|
+
});
|
|
9872
|
+
const isToken = (event) => event.type === "text.delta" || event.type === "thinking.delta" || event.type === "toolcall.delta";
|
|
9873
|
+
/**
|
|
9874
|
+
* A failed terminal is the request's result, not an error. It leaves the
|
|
9875
|
+
* traced request as a failure so the span records an error status, and is
|
|
9876
|
+
* recovered just outside it.
|
|
9877
|
+
*/
|
|
9878
|
+
var FailedTerminal = class extends Data.TaggedError("LLM.FailedTerminal") {};
|
|
9803
9879
|
/**
|
|
9804
9880
|
* Build a provider request from an opener. Tests use this with deterministic
|
|
9805
9881
|
* aikit event streams; production uses `open` above.
|
|
9806
9882
|
*/
|
|
9807
9883
|
const make$5 = (openStream) => {
|
|
9808
|
-
const request = Effect.fn("LLM.run"
|
|
9884
|
+
const request = Effect.fn("LLM.run", {
|
|
9885
|
+
kind: "client",
|
|
9886
|
+
level: "Info"
|
|
9887
|
+
})(function* (input) {
|
|
9888
|
+
yield* Effect.annotateCurrentSpan({
|
|
9889
|
+
"gen_ai.operation.name": "chat",
|
|
9890
|
+
"gen_ai.provider.name": input.provider,
|
|
9891
|
+
"gen_ai.request.model": input.model,
|
|
9892
|
+
"gen_ai.conversation.id": input.sessionId,
|
|
9893
|
+
"gen_ai.request.stream": true
|
|
9894
|
+
});
|
|
9895
|
+
const start = yield* Effect.clockWith((clock) => clock.currentTimeMillis);
|
|
9896
|
+
let firstToken;
|
|
9897
|
+
let drained;
|
|
9898
|
+
const markToken = (event) => firstToken !== void 0 || !isToken(event) ? Effect.void : Effect.clockWith((clock) => Effect.sync(() => {
|
|
9899
|
+
firstToken = clock.currentTimeMillisUnsafe();
|
|
9900
|
+
}));
|
|
9809
9901
|
const signalScope = yield* Scope.make();
|
|
9810
9902
|
yield* Effect.addFinalizer((exit) => Scope.close(signalScope, exit));
|
|
9811
9903
|
const signal = yield* Effect.abortSignal.pipe(Scope.provide(signalScope));
|
|
9812
9904
|
const abort = Scope.close(signalScope, Exit.void);
|
|
9813
|
-
|
|
9905
|
+
const terminal = yield* Effect.uninterruptibleMask((restore) => Effect.gen(function* () {
|
|
9814
9906
|
const iterable = yield* restore(openStream(input, signal)).pipe(Effect.onInterrupt(() => abort));
|
|
9815
|
-
const consumer = yield* Stream.fromAsyncIterable(iterable, (cause) => providerErrorFromUnknown(input, cause)).pipe(Stream.runForEach(input.publisher.publish), Effect.andThen(input.publisher.terminal), Effect.interruptible).pipe(Effect.forkScoped({ startImmediately: true }));
|
|
9907
|
+
const consumer = yield* Stream.fromAsyncIterable(iterable, (cause) => providerErrorFromUnknown(input, cause)).pipe(Stream.runForEach((event) => Effect.andThen(markToken(event), input.publisher.publish(event))), Effect.andThen(input.publisher.terminal), Effect.interruptible).pipe(Effect.forkScoped({ startImmediately: true }));
|
|
9816
9908
|
const awaited = yield* restore(Fiber.await(consumer)).pipe(Effect.onInterrupt(() => abort), Effect.exit);
|
|
9817
9909
|
if (Exit.isFailure(awaited)) {
|
|
9818
|
-
const
|
|
9819
|
-
if (Exit.isFailure(
|
|
9910
|
+
const consumed = yield* Fiber.await(consumer);
|
|
9911
|
+
if (Exit.isFailure(consumed)) return yield* Effect.failCause(consumed.cause);
|
|
9912
|
+
drained = consumed.value;
|
|
9820
9913
|
return yield* Effect.failCause(awaited.cause);
|
|
9821
9914
|
}
|
|
9822
9915
|
const completed = awaited.value;
|
|
9823
9916
|
if (Exit.isFailure(completed)) return yield* Effect.failCause(completed.cause);
|
|
9824
9917
|
return completed.value;
|
|
9825
|
-
}))
|
|
9826
|
-
|
|
9827
|
-
|
|
9918
|
+
})).pipe(Effect.onExit((exit) => observe(input, {
|
|
9919
|
+
start,
|
|
9920
|
+
firstToken
|
|
9921
|
+
}, exit, drained)));
|
|
9922
|
+
if (terminal.outcome === "failed") return yield* new FailedTerminal({ terminal });
|
|
9923
|
+
return terminal;
|
|
9924
|
+
});
|
|
9925
|
+
return (input) => request(input).pipe(Effect.catchTag("LLM.FailedTerminal", (failed) => Effect.succeed(failed.terminal)), Effect.scoped);
|
|
9828
9926
|
};
|
|
9829
9927
|
const run$1 = make$5(open);
|
|
9830
9928
|
//#endregion
|
|
@@ -10735,6 +10833,17 @@ const errorPart = (call, cause, now) => ({
|
|
|
10735
10833
|
end: endTime(call, now)
|
|
10736
10834
|
}
|
|
10737
10835
|
});
|
|
10836
|
+
const observeTool = (snapshot, call, seconds, exit) => {
|
|
10837
|
+
const tool = snapshot.tools.defs.some((def) => def.name === call.name) ? call.name : "_OTHER";
|
|
10838
|
+
const labels = Exit.isFailure(exit) ? {
|
|
10839
|
+
tool,
|
|
10840
|
+
error: errorType(exit.cause)
|
|
10841
|
+
} : exit.value.status === "completed" ? { tool } : {
|
|
10842
|
+
tool,
|
|
10843
|
+
error: exit.value.status
|
|
10844
|
+
};
|
|
10845
|
+
return record$1(toolDuration, seconds, labels);
|
|
10846
|
+
};
|
|
10738
10847
|
const layer$3 = (options = {}) => Layer.effect(Service$7, Effect.gen(function* () {
|
|
10739
10848
|
const context = yield* Service$13;
|
|
10740
10849
|
const events = yield* Service$16;
|
|
@@ -10773,7 +10882,7 @@ const layer$3 = (options = {}) => Layer.effect(Service$7, Effect.gen(function* (
|
|
|
10773
10882
|
if (draft === void 0) return;
|
|
10774
10883
|
yield* publishFailure(draft, { _tag: "interrupted" });
|
|
10775
10884
|
});
|
|
10776
|
-
const settleTools = Effect.fn("Loop.settleTools")(function* (snapshot, message, reason, markCommitted) {
|
|
10885
|
+
const settleTools = Effect.fn("Loop.settleTools", { level: "Info" })(function* (snapshot, message, reason, markCommitted) {
|
|
10777
10886
|
const pending = message.parts.filter((part) => part.type === "toolCall" && part.status === "pending");
|
|
10778
10887
|
let interruptedCause;
|
|
10779
10888
|
const messageId = ID.from(message.messageId);
|
|
@@ -10812,7 +10921,12 @@ const layer$3 = (options = {}) => Layer.effect(Service$7, Effect.gen(function* (
|
|
|
10812
10921
|
return;
|
|
10813
10922
|
}
|
|
10814
10923
|
const settled = /* @__PURE__ */ new Set();
|
|
10815
|
-
const handle = Effect.fn("Loop.handleTool")(function* (call) {
|
|
10924
|
+
const handle = Effect.fn("Loop.handleTool", { level: "Info" })(function* (call) {
|
|
10925
|
+
yield* Effect.annotateCurrentSpan({
|
|
10926
|
+
"gen_ai.operation.name": "execute_tool",
|
|
10927
|
+
"gen_ai.tool.name": call.name,
|
|
10928
|
+
"gen_ai.tool.call.id": call.callID
|
|
10929
|
+
});
|
|
10816
10930
|
yield* events.publish(ToolStarted, {
|
|
10817
10931
|
timestamp: yield* DateTime.now,
|
|
10818
10932
|
sessionId: snapshot.sessionId,
|
|
@@ -10822,7 +10936,7 @@ const layer$3 = (options = {}) => Layer.effect(Service$7, Effect.gen(function* (
|
|
|
10822
10936
|
label: snapshot.tools.defs.find((def) => def.name === call.name)?.label,
|
|
10823
10937
|
arguments: call.arguments
|
|
10824
10938
|
});
|
|
10825
|
-
const
|
|
10939
|
+
const execute = snapshot.tools.handle(call, {
|
|
10826
10940
|
sessionId: snapshot.sessionId,
|
|
10827
10941
|
messageId,
|
|
10828
10942
|
onProgress: (progress) => events.publish(ToolProgress$2, {
|
|
@@ -10833,6 +10947,7 @@ const layer$3 = (options = {}) => Layer.effect(Service$7, Effect.gen(function* (
|
|
|
10833
10947
|
partial: progress.partial
|
|
10834
10948
|
}).pipe(Effect.asVoid)
|
|
10835
10949
|
}).pipe(Effect.catchCauseIf((cause) => !Cause.hasInterrupts(cause), (cause) => Effect.map(Effect.clockWith((clock) => clock.currentTimeMillis), (now) => errorPart(call, cause, now))));
|
|
10950
|
+
const handled = yield* timed(execute, (seconds, exit) => observeTool(snapshot, call, seconds, exit));
|
|
10836
10951
|
yield* Effect.uninterruptible(Effect.gen(function* () {
|
|
10837
10952
|
yield* settle(call, handled);
|
|
10838
10953
|
yield* Effect.sync(() => settled.add(call.callID));
|
|
@@ -10855,7 +10970,7 @@ const layer$3 = (options = {}) => Layer.effect(Service$7, Effect.gen(function* (
|
|
|
10855
10970
|
}));
|
|
10856
10971
|
return interruptedCause;
|
|
10857
10972
|
});
|
|
10858
|
-
const runTurnAttempt = Effect.fn("Loop.runTurnAttempt")(function* (promotion, snapshot) {
|
|
10973
|
+
const runTurnAttempt = Effect.fn("Loop.runTurnAttempt", { level: "Info" })(function* (promotion, snapshot) {
|
|
10859
10974
|
const sessionId = snapshot.sessionId;
|
|
10860
10975
|
if (promotion !== void 0) {
|
|
10861
10976
|
const cutoff = yield* events.latestSequence(sessionId);
|
|
@@ -10959,27 +11074,35 @@ const layer$3 = (options = {}) => Layer.effect(Service$7, Effect.gen(function* (
|
|
|
10959
11074
|
});
|
|
10960
11075
|
}));
|
|
10961
11076
|
});
|
|
10962
|
-
const runTurn = Effect.fn("Loop.runTurn")(function* (promotion, snapshot) {
|
|
11077
|
+
const runTurn = Effect.fn("Loop.runTurn", { level: "Info" })(function* (promotion, snapshot) {
|
|
10963
11078
|
return yield* runTurnAttempt(promotion, snapshot);
|
|
10964
11079
|
});
|
|
10965
|
-
const run = Effect.fn("Loop.run")(function* (input) {
|
|
11080
|
+
const run = Effect.fn("Loop.run", { level: "Info" })(function* (input) {
|
|
10966
11081
|
yield* healDanglingDraft(input.sessionId);
|
|
10967
11082
|
const hasSteer = yield* inputs.hasPending(input.sessionId, "steer");
|
|
10968
11083
|
const hasFollowUp = hasSteer ? false : yield* inputs.hasPending(input.sessionId, "followUp");
|
|
10969
11084
|
if (!input.force && !hasSteer && !hasFollowUp) return;
|
|
11085
|
+
yield* Effect.annotateCurrentSpan({
|
|
11086
|
+
"gen_ai.operation.name": "invoke_agent",
|
|
11087
|
+
"gen_ai.agent.name": "codework",
|
|
11088
|
+
"gen_ai.conversation.id": input.sessionId
|
|
11089
|
+
});
|
|
10970
11090
|
let promotion = hasSteer ? "steer" : hasFollowUp ? "followUp" : void 0;
|
|
10971
|
-
|
|
10972
|
-
|
|
10973
|
-
|
|
10974
|
-
|
|
10975
|
-
|
|
10976
|
-
|
|
10977
|
-
|
|
10978
|
-
|
|
11091
|
+
const drain = Effect.gen(function* () {
|
|
11092
|
+
let shouldRun = true;
|
|
11093
|
+
while (shouldRun) {
|
|
11094
|
+
const snapshot = yield* state.snapshot(input.sessionId);
|
|
11095
|
+
let needsContinuation = true;
|
|
11096
|
+
while (needsContinuation) {
|
|
11097
|
+
const result = yield* runTurn(promotion, snapshot);
|
|
11098
|
+
promotion = "steer";
|
|
11099
|
+
needsContinuation = result.needsContinuation || (yield* inputs.hasPending(input.sessionId, "steer"));
|
|
11100
|
+
}
|
|
11101
|
+
shouldRun = yield* inputs.hasPending(input.sessionId, "followUp");
|
|
11102
|
+
promotion = shouldRun ? "followUp" : void 0;
|
|
10979
11103
|
}
|
|
10980
|
-
|
|
10981
|
-
|
|
10982
|
-
}
|
|
11104
|
+
});
|
|
11105
|
+
yield* timed(drain, (seconds, exit) => record$1(agentDuration, seconds, withError({}, exit)));
|
|
10983
11106
|
});
|
|
10984
11107
|
return Service$7.of({ run });
|
|
10985
11108
|
}));
|
|
@@ -11300,7 +11423,7 @@ const runtimeOverrides = (driver, value) => {
|
|
|
11300
11423
|
}));
|
|
11301
11424
|
return Effect.succeed(value);
|
|
11302
11425
|
};
|
|
11303
|
-
const create$2 = Effect.fn("Sandbox.create")(function* (input) {
|
|
11426
|
+
const create$2 = Effect.fn("Sandbox.create", { level: "Info" })(function* (input) {
|
|
11304
11427
|
const controller = yield* Controller;
|
|
11305
11428
|
const registry = yield* Registry;
|
|
11306
11429
|
const driverName = name(input.driver);
|
|
@@ -11326,7 +11449,7 @@ const Selection = Schema.Union([Schema.Struct({ id: instance_exports.SandboxInst
|
|
|
11326
11449
|
driver: Schema.String,
|
|
11327
11450
|
providerResourceId: (0, schema_exports$9.optional)(Schema.String)
|
|
11328
11451
|
})]);
|
|
11329
|
-
const resolve = Effect.fn("Sandbox.resolve")(function* (input) {
|
|
11452
|
+
const resolve = Effect.fn("Sandbox.resolve", { level: "Info" })(function* (input) {
|
|
11330
11453
|
if ("id" in input) {
|
|
11331
11454
|
const found = yield* get$1(input.id);
|
|
11332
11455
|
if (Option.isNone(found)) return yield* new errors_exports.SandboxNotFoundError({ id: input.id });
|
|
@@ -11379,7 +11502,7 @@ const list = Effect.fn("Sandbox.list")(function* (input) {
|
|
|
11379
11502
|
const refresh = Effect.fn("Sandbox.refresh")(function* (id) {
|
|
11380
11503
|
return yield* (yield* Controller).refresh(id);
|
|
11381
11504
|
});
|
|
11382
|
-
const wake = Effect.fn("Sandbox.wake")(function* (id) {
|
|
11505
|
+
const wake = Effect.fn("Sandbox.wake", { level: "Info" })(function* (id) {
|
|
11383
11506
|
return yield* (yield* Controller).wake(id);
|
|
11384
11507
|
});
|
|
11385
11508
|
const stop = Effect.fn("Sandbox.stop")(function* (id) {
|
|
@@ -11602,12 +11725,14 @@ var plugin_exports = /* @__PURE__ */ __exportAll({
|
|
|
11602
11725
|
definition: () => definition$1,
|
|
11603
11726
|
identity: () => digest,
|
|
11604
11727
|
inspect: () => inspect,
|
|
11728
|
+
lendResolve: () => lendResolve,
|
|
11605
11729
|
localName: () => localName,
|
|
11606
11730
|
parse: () => parse$1,
|
|
11607
11731
|
probe: () => probe,
|
|
11608
11732
|
resolve: () => resolve$2,
|
|
11609
11733
|
resolveCached: () => required,
|
|
11610
11734
|
settingsLock: () => lock,
|
|
11735
|
+
share: () => share,
|
|
11611
11736
|
update: () => update
|
|
11612
11737
|
});
|
|
11613
11738
|
//#endregion
|