@odla-ai/harness 0.9.1 → 0.9.3

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.
Files changed (38) hide show
  1. package/dist/{chunk-HDIR4MM5.js → chunk-5LRYJKUI.js} +3 -3
  2. package/dist/{chunk-4EPJJMFG.js → chunk-AEAISFY3.js} +157 -217
  3. package/dist/chunk-AEAISFY3.js.map +1 -0
  4. package/dist/chunk-FAN2R3GW.js +166 -0
  5. package/dist/chunk-FAN2R3GW.js.map +1 -0
  6. package/dist/{chunk-CIKYMC67.js → chunk-OZBJNTML.js} +4 -4
  7. package/dist/{chunk-I43KTCJ2.js → chunk-U324RQ4N.js} +1 -1
  8. package/dist/{chunk-I43KTCJ2.js.map → chunk-U324RQ4N.js.map} +1 -1
  9. package/dist/{chunk-VGNIDRKM.js → chunk-VDY5V7ZG.js} +2 -2
  10. package/dist/cli.cjs.map +1 -1
  11. package/dist/cli.js +4 -4
  12. package/dist/code-runtime-cli.cjs +258 -163
  13. package/dist/code-runtime-cli.cjs.map +1 -1
  14. package/dist/code-runtime-cli.js +6 -5
  15. package/dist/code-runtime-cli.js.map +1 -1
  16. package/dist/index.cjs +172 -6
  17. package/dist/index.cjs.map +1 -1
  18. package/dist/index.d.cts +24 -3
  19. package/dist/index.d.ts +24 -3
  20. package/dist/index.js +11 -3
  21. package/dist/index.js.map +1 -1
  22. package/dist/node.cjs +261 -162
  23. package/dist/node.cjs.map +1 -1
  24. package/dist/node.d.cts +39 -6
  25. package/dist/node.d.ts +39 -6
  26. package/dist/node.js +10 -5
  27. package/dist/node.js.map +1 -1
  28. package/dist/testing.cjs.map +1 -1
  29. package/dist/testing.d.cts +1 -1
  30. package/dist/testing.d.ts +1 -1
  31. package/dist/testing.js +1 -1
  32. package/dist/{types-BazqxWK8.d.cts → types-_8y8vBDI.d.cts} +5 -1
  33. package/dist/{types-BazqxWK8.d.ts → types-_8y8vBDI.d.ts} +5 -1
  34. package/package.json +1 -1
  35. package/dist/chunk-4EPJJMFG.js.map +0 -1
  36. /package/dist/{chunk-HDIR4MM5.js.map → chunk-5LRYJKUI.js.map} +0 -0
  37. /package/dist/{chunk-CIKYMC67.js.map → chunk-OZBJNTML.js.map} +0 -0
  38. /package/dist/{chunk-VGNIDRKM.js.map → chunk-VDY5V7ZG.js.map} +0 -0
package/dist/cli.cjs.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/cli.ts","../src/client.ts","../src/container.ts","../src/types.ts","../src/protocol.ts","../src/runner.ts","../src/workspace.ts","../src/workspace-policy.ts"],"sourcesContent":["#!/usr/bin/env node\nimport { resolve } from \"node:path\";\nimport { createHarnessControlClient } from \"./client\";\nimport { selectContainerEngine, type ContainerEngine } from \"./container\";\nimport { runHarnessRunner } from \"./runner\";\n\ninterface CliOptions {\n endpoint: string;\n engine: ContainerEngine | \"auto\";\n image: string;\n workspaces: Record<string, string>;\n once: boolean;\n pollMs: number;\n preserveWorkspace: boolean;\n allowUnpinnedImage: boolean;\n}\n\nfunction usage(): string {\n return `Usage:\n ODLA_HARNESS_TOKEN=odla_hrn_... odla-harness runner \\\\\n --endpoint https://odla.ai \\\\\n --workspace my-repo=/absolute/path \\\\\n --image registry.example/agent@sha256:<digest> [--engine auto|container|podman|docker] [--once]\n\nThe token is read only from ODLA_HARNESS_TOKEN so it does not enter shell history.\nImages must be digest-pinned. Network is disabled inside the container.\nAuto prefers Apple container on macOS and rootless Podman on Linux.`;\n}\n\nfunction parse(argv: string[]): CliOptions {\n if (argv[0] !== \"runner\") throw new TypeError(usage());\n const values: Record<string, string[]> = {};\n const flags = new Set<string>();\n for (let index = 1; index < argv.length; index++) {\n const arg = argv[index]!;\n if ([\"--once\", \"--preserve-workspace\", \"--allow-unpinned-image\"].includes(arg)) {\n flags.add(arg);\n continue;\n }\n if (!arg.startsWith(\"--\") || !argv[index + 1]) throw new TypeError(`missing value for ${arg}`);\n (values[arg] ??= []).push(argv[++index]!);\n }\n const endpoint = values[\"--endpoint\"]?.at(-1);\n const image = values[\"--image\"]?.at(-1);\n const engine = values[\"--engine\"]?.at(-1) ?? \"auto\";\n if (!endpoint || !image || ![\"auto\", \"container\", \"podman\", \"docker\"].includes(engine)) throw new TypeError(usage());\n const workspaces: Record<string, string> = {};\n for (const mapping of values[\"--workspace\"] ?? []) {\n const equals = mapping.indexOf(\"=\");\n const key = mapping.slice(0, equals);\n const path = mapping.slice(equals + 1);\n if (equals < 1 || !/^[a-z0-9][a-z0-9_-]{0,79}$/.test(key) || !path) {\n throw new TypeError(`invalid workspace mapping: ${mapping}`);\n }\n workspaces[key] = resolve(path);\n }\n if (!Object.keys(workspaces).length) throw new TypeError(\"at least one --workspace key=/absolute/path is required\");\n const allowUnpinnedImage = flags.has(\"--allow-unpinned-image\");\n if (allowUnpinnedImage && process.env.ODLA_HARNESS_UNSAFE_TESTING !== \"1\") {\n throw new TypeError(\"--allow-unpinned-image requires ODLA_HARNESS_UNSAFE_TESTING=1\");\n }\n const pollMs = Number(values[\"--poll-ms\"]?.at(-1) ?? 2_000);\n if (!Number.isSafeInteger(pollMs) || pollMs < 250 || pollMs > 60_000) {\n throw new TypeError(\"--poll-ms must be an integer from 250 to 60000\");\n }\n return {\n endpoint,\n image,\n engine: engine as ContainerEngine | \"auto\",\n workspaces,\n once: flags.has(\"--once\"),\n pollMs,\n preserveWorkspace: flags.has(\"--preserve-workspace\"),\n allowUnpinnedImage,\n };\n}\n\nasync function main(): Promise<void> {\n const token = process.env.ODLA_HARNESS_TOKEN;\n if (!token) throw new TypeError(\"ODLA_HARNESS_TOKEN is required\");\n const options = parse(process.argv.slice(2));\n const controller = new AbortController();\n for (const signal of [\"SIGINT\", \"SIGTERM\"] as const) process.once(signal, () => controller.abort(signal));\n const engine = await selectContainerEngine(options.engine);\n if (process.platform === \"linux\" && engine === \"docker\") {\n process.stderr.write(\"[odla-harness] warning: explicit Docker on Linux may use a rootful daemon; rootless Podman is preferred\\n\");\n }\n await runHarnessRunner({\n ...options,\n engine,\n control: createHarnessControlClient({ endpoint: options.endpoint, token, signal: controller.signal }),\n signal: controller.signal,\n log: (message) => process.stderr.write(`[odla-harness] ${message}\\n`),\n });\n}\n\nmain().catch((error) => {\n process.stderr.write(`${error instanceof Error ? error.message : String(error)}\\n`);\n process.exitCode = 1;\n});\n","import type {\n HarnessCompletion,\n HarnessControlPlane,\n HarnessEventInput,\n HarnessInferenceRequest,\n HarnessInferenceResponse,\n HarnessLease,\n} from \"./types\";\n\n/** HTTP error returned by the harness control plane, including its stable error code. */\nexport class HarnessControlError extends Error {\n override readonly name = \"HarnessControlError\";\n constructor(message: string, readonly status: number, readonly code = \"control_error\") { super(message); }\n}\n\n/** Connection, credential, cancellation, and timeout settings for a runner client. */\nexport interface HarnessControlClientOptions {\n endpoint: string;\n token: string;\n fetch?: typeof fetch;\n requestTimeoutMs?: number;\n signal?: AbortSignal;\n}\n\n/** Create a validated HTTPS client implementing the runner control-plane operations. */\nexport function createHarnessControlClient(options: HarnessControlClientOptions): HarnessControlPlane {\n const endpoint = options.endpoint.replace(/\\/+$/, \"\");\n let endpointUrl: URL;\n try { endpointUrl = new URL(endpoint); } catch { throw new TypeError(\"endpoint must be an HTTPS URL\"); }\n const loopback = endpointUrl.hostname === \"localhost\" || endpointUrl.hostname === \"127.0.0.1\" || endpointUrl.hostname === \"[::1]\";\n if (endpointUrl.username || endpointUrl.password || (endpointUrl.protocol !== \"https:\" && !(loopback && endpointUrl.protocol === \"http:\"))) {\n throw new TypeError(\"endpoint must use HTTPS (HTTP is allowed only for loopback testing)\");\n }\n if (!/^odla_hrn_[0-9a-f]{64}$/.test(options.token)) throw new TypeError(\"invalid harness runner credential\");\n const requestTimeoutMs = options.requestTimeoutMs ?? 30_000;\n if (!Number.isSafeInteger(requestTimeoutMs) || requestTimeoutMs < 1_000 || requestTimeoutMs > 120_000) {\n throw new TypeError(\"requestTimeoutMs must be an integer from 1000 to 120000\");\n }\n const request = options.fetch ?? fetch;\n const call = async <T>(path: string, body: unknown, allowEmpty = false): Promise<T | null> => {\n const timeout = AbortSignal.timeout(requestTimeoutMs);\n const signal = options.signal ? AbortSignal.any([options.signal, timeout]) : timeout;\n const response = await request(`${endpoint}${path}`, {\n method: \"POST\",\n headers: { authorization: `Bearer ${options.token}`, \"content-type\": \"application/json\" },\n body: JSON.stringify(body),\n redirect: \"error\",\n signal,\n });\n if (allowEmpty && response.status === 204) return null;\n const value = await response.json().catch(() => null) as { error?: { code?: string; message?: string } } | null;\n if (!response.ok) throw new HarnessControlError(\n value?.error?.message ?? `harness control request failed (${response.status})`,\n response.status,\n value?.error?.code,\n );\n return value as T;\n };\n return {\n lease: async (workspaces) => {\n const body = await call<{ lease: HarnessLease }>(\"/registry/harness/lease\", { workspaces }, true);\n return body?.lease ?? null;\n },\n heartbeat: async (attemptId, leaseId) => {\n const body = await call<{ cancelRequested: boolean; expiresAt: number }>(\n `/registry/harness/attempts/${encodeURIComponent(attemptId)}/heartbeat`, { leaseId },\n );\n return body!;\n },\n appendEvents: async (attemptId, leaseId, events: HarnessEventInput[]) => {\n await call(`/registry/harness/attempts/${encodeURIComponent(attemptId)}/events`, { leaseId, events });\n },\n infer: async (attemptId, leaseId, inference: HarnessInferenceRequest) => {\n const body = await call<HarnessInferenceResponse>(\n `/registry/harness/attempts/${encodeURIComponent(attemptId)}/inference`, { leaseId, ...inference },\n );\n return body!;\n },\n complete: async (attemptId, leaseId, completion: HarnessCompletion) => {\n await call(`/registry/harness/attempts/${encodeURIComponent(attemptId)}/complete`, { leaseId, ...completion });\n },\n };\n}\n","import { execFile, spawn } from \"node:child_process\";\nimport { constants } from \"node:fs\";\nimport { access } from \"node:fs/promises\";\nimport { delimiter, join } from \"node:path\";\nimport { getgid, getuid } from \"node:process\";\nimport { encodeAgentInput, parseAgentOutput } from \"./protocol\";\nimport {\n HARNESS_PROTOCOL_VERSION,\n type HarnessAgentInput,\n type HarnessAgentOutput,\n type HarnessTaskSpec,\n} from \"./types\";\n\nconst DIGEST_IMAGE = /^[a-z0-9][a-z0-9._/-]*(?::[a-zA-Z0-9._-]+)?@sha256:[0-9a-f]{64}$/;\n\n/** Supported command-line container engines for isolated harness attempts. */\nexport type ContainerEngine = \"container\" | \"podman\" | \"docker\";\n\n/** Host facts and executable probe used while selecting a safe container engine. */\nexport interface ContainerEngineSelectionOptions {\n platform?: NodeJS.Platform;\n arch?: string;\n uid?: number;\n available?: (engine: ContainerEngine) => Promise<boolean>;\n}\n\n/** Host facts and rootless probe used to verify the selected engine boundary. */\nexport interface ContainerEngineVerificationOptions {\n platform?: NodeJS.Platform;\n arch?: string;\n uid?: number;\n podmanRootless?: () => Promise<boolean>;\n}\n\n/** Optional CPU, memory, process, and temporary-filesystem limits for an attempt. */\nexport interface ContainerLimits {\n cpus?: number;\n memory?: string;\n pids?: number;\n tmpfsBytes?: number;\n}\n\n/** Container, task, callback, and cancellation settings for one agent attempt. */\nexport interface ContainerRunOptions {\n engine: ContainerEngine;\n image: string;\n workspaceDir: string;\n workspaceAccess?: \"read-write\" | \"read-only\" | \"none\";\n task: HarnessTaskSpec;\n limits?: ContainerLimits;\n allowUnpinnedImage?: boolean;\n signal?: AbortSignal;\n onMessage(message: HarnessAgentOutput): Promise<HarnessAgentInput | void>;\n onStderr?(text: string): Promise<void> | void;\n}\n\n/** Terminal container outcome and bounded diagnostic output returned to the runner. */\nexport interface ContainerRunResult {\n exitCode: number;\n status: \"completed\" | \"failed\" | \"cancelled\";\n result?: unknown;\n stderr: string;\n}\n\n/** Require an immutable OCI image reference pinned to a SHA-256 digest. */\nexport function assertPinnedImage(image: string): void {\n if (!DIGEST_IMAGE.test(image)) throw new TypeError(\"container image must be pinned by sha256 digest\");\n}\n\nasync function commandAvailable(engine: ContainerEngine): Promise<boolean> {\n for (const directory of (process.env.PATH ?? \"\").split(delimiter).filter(Boolean)) {\n try { await access(join(directory, engine), constants.X_OK); return true; } catch { /* try the next PATH entry */ }\n }\n return false;\n}\n\n/** Choose the strongest installed local default without silently selecting a\n * rootful Linux daemon. Apple container is a per-container VM boundary;\n * rootless Podman is the Linux default; Docker remains explicit. */\nexport async function selectContainerEngine(\n requested: ContainerEngine | \"auto\" = \"auto\",\n options: ContainerEngineSelectionOptions = {},\n): Promise<ContainerEngine> {\n const platform = options.platform ?? process.platform;\n const arch = options.arch ?? process.arch;\n const uid = options.uid ?? (typeof getuid === \"function\" ? getuid() : 1000);\n const available = options.available ?? commandAvailable;\n const validate = async (engine: ContainerEngine): Promise<ContainerEngine> => {\n if (engine === \"container\" && (platform !== \"darwin\" || arch !== \"arm64\")) {\n throw new TypeError(\"Apple container requires Apple Silicon macOS\");\n }\n if (engine === \"podman\" && platform === \"linux\" && uid === 0) {\n throw new TypeError(\"the Linux harness requires rootless Podman; do not run the runner as root\");\n }\n if (!(await available(engine))) throw new TypeError(`${engine} is not installed or executable`);\n return engine;\n };\n if (requested !== \"auto\") return validate(requested);\n const candidates: ContainerEngine[] = platform === \"darwin\"\n ? arch === \"arm64\" ? [\"container\", \"podman\"] : [\"podman\"]\n : platform === \"linux\" ? [\"podman\"] : [];\n for (const engine of candidates) {\n if (await available(engine)) return validate(engine);\n }\n if (platform === \"linux\") {\n throw new TypeError(\"no rootless Podman found; install Podman or explicitly choose --engine docker after reviewing its daemon boundary\");\n }\n if (platform === \"darwin\") {\n throw new TypeError(\"Apple container is not installed; on Apple Silicon macOS 26 run `brew install container`, then retry (Podman Machine is the fallback)\");\n }\n throw new TypeError(\"no supported container engine found\");\n}\n\nfunction inspectRootlessPodman(): Promise<boolean> {\n return new Promise((resolve, reject) => {\n execFile(\n \"podman\",\n [\"info\", \"--format\", \"{{.Host.Security.Rootless}}\"],\n { encoding: \"utf8\", maxBuffer: 16 * 1024, timeout: 10_000 },\n (error, stdout) => {\n if (error) {\n reject(new TypeError(\"could not verify that the active Podman service is rootless\"));\n return;\n }\n resolve(stdout.trim() === \"true\");\n },\n );\n });\n}\n\n/** Fail closed if the selected engine cannot provide the promised host\n * boundary. This is checked for every attempt so a changed Podman connection\n * cannot silently turn a rootless Linux runner into a rootful one. */\nexport async function verifyContainerEngineBoundary(\n engine: ContainerEngine,\n options: ContainerEngineVerificationOptions = {},\n): Promise<void> {\n const platform = options.platform ?? process.platform;\n const arch = options.arch ?? process.arch;\n const uid = options.uid ?? (typeof getuid === \"function\" ? getuid() : 1000);\n if (engine === \"container\" && (platform !== \"darwin\" || arch !== \"arm64\")) {\n throw new TypeError(\"Apple container requires Apple Silicon macOS\");\n }\n if (engine !== \"podman\" || platform !== \"linux\") return;\n if (uid === 0) throw new TypeError(\"the Linux harness requires rootless Podman; do not run the runner as root\");\n const rootless = await (options.podmanRootless ?? inspectRootlessPodman)();\n if (!rootless) throw new TypeError(\"the active Podman service is not rootless; refusing to run the harness\");\n}\n\n/** Build hardened, networkless engine arguments without starting the container. */\nexport function buildContainerRunArgs(options: Omit<ContainerRunOptions, \"onMessage\" | \"onStderr\" | \"signal\">): string[] {\n if (!options.allowUnpinnedImage) assertPinnedImage(options.image);\n if (/[,\\r\\n]/.test(options.workspaceDir)) throw new TypeError(\"workspace path contains unsupported mount characters\");\n const uid = typeof getuid === \"function\" ? getuid() : 1000;\n const gid = typeof getgid === \"function\" ? getgid() : 1000;\n const safeAttempt = options.task.attemptId.toLowerCase().replace(/[^a-z0-9_.-]/g, \"-\").slice(0, 40);\n const name = `odla-harness-${safeAttempt}-${crypto.randomUUID().slice(0, 8)}`;\n const limits = options.limits ?? {};\n const access = options.workspaceAccess ?? \"read-write\";\n const appleMount = access === \"none\" ? [] : [`--mount=type=bind,source=${options.workspaceDir},target=/workspace${access === \"read-only\" ? \",readonly\" : \"\"}`];\n const ociMount = access === \"none\" ? [] : [`--mount=type=bind,src=${options.workspaceDir},dst=/workspace${access === \"read-only\" ? \",readonly\" : \"\"}`];\n if (options.engine === \"container\") {\n return [\n \"run\", \"--rm\", \"--interactive\", `--name=${name}`,\n \"--network=none\", \"--read-only\", \"--cap-drop=ALL\",\n `--memory=${limits.memory ?? \"1g\"}`, `--cpus=${limits.cpus ?? 1}`,\n `--user=${uid}:${gid}`, \"--tmpfs=/tmp\",\n ...appleMount,\n \"--workdir=/workspace\", `--env=ODLA_HARNESS_PROTOCOL=${HARNESS_PROTOCOL_VERSION}`,\n `--label=ai.odla.harness.attempt=${options.task.attemptId}`,\n options.image,\n ];\n }\n return [\n \"run\", \"--rm\", \"--interactive\", `--name=${name}`, \"--pull=never\",\n \"--network=none\", \"--read-only\", \"--cap-drop=ALL\",\n \"--security-opt=no-new-privileges\", `--pids-limit=${limits.pids ?? 256}`,\n `--memory=${limits.memory ?? \"1g\"}`, `--cpus=${limits.cpus ?? 1}`,\n `--user=${uid}:${gid}`,\n `--tmpfs=/tmp:rw,noexec,nosuid,nodev,size=${limits.tmpfsBytes ?? 64 * 1024 * 1024}`,\n ...ociMount,\n \"--workdir=/workspace\", `--env=ODLA_HARNESS_PROTOCOL=${HARNESS_PROTOCOL_VERSION}`,\n `--label=ai.odla.harness.attempt=${options.task.attemptId}`,\n options.image,\n ];\n}\n\nfunction containerName(args: string[]): string {\n return args.find((arg) => arg.startsWith(\"--name=\"))!.slice(\"--name=\".length);\n}\n\n/** Execute one JSONL agent inside a hardened Apple container, Podman, or Docker\n * boundary. The\n * container has no network and receives no credentials; inference requests are\n * bridged over stdin/stdout to the trusted runner process. */\nexport async function runContainerAttempt(options: ContainerRunOptions): Promise<ContainerRunResult> {\n if (options.signal?.aborted) return { exitCode: 1, status: \"cancelled\", stderr: \"\" };\n await verifyContainerEngineBoundary(options.engine);\n const args = buildContainerRunArgs(options);\n const name = containerName(args);\n const child = spawn(options.engine, args, { stdio: [\"pipe\", \"pipe\", \"pipe\"], shell: false });\n let stderr = \"\";\n let outputBytes = 0;\n let complete: Extract<HarnessAgentOutput, { type: \"attempt.complete\" }> | null = null;\n let stopped = false;\n let exited = false;\n\n child.stderr.setEncoding(\"utf8\");\n child.stderr.on(\"data\", (text: string) => {\n if (stderr.length < 64 * 1024) stderr += text.slice(0, 64 * 1024 - stderr.length);\n });\n\n const stop = (reason: string) => {\n if (stopped || exited) return;\n stopped = true;\n if (!child.stdin.destroyed) {\n const cancel: HarnessAgentInput = { protocolVersion: HARNESS_PROTOCOL_VERSION, type: \"attempt.cancel\", reason };\n child.stdin.write(encodeAgentInput(cancel));\n }\n const removeArgs = options.engine === \"container\" ? [\"delete\", \"--force\", name] : [\"rm\", \"-f\", name];\n const killer = spawn(options.engine, removeArgs, { stdio: \"ignore\", shell: false });\n killer.unref();\n };\n const abort = () => stop(\"runner_cancelled\");\n options.signal?.addEventListener(\"abort\", abort, { once: true });\n\n const timeout = setTimeout(() => stop(\"timeout\"), options.task.policy.timeoutMs);\n const start: HarnessAgentInput = { protocolVersion: HARNESS_PROTOCOL_VERSION, type: \"task.start\", task: options.task };\n if (!stopped && !options.signal?.aborted) child.stdin.write(encodeAgentInput(start));\n\n const consume = (async () => {\n let pending = Buffer.alloc(0);\n const handleLine = async (raw: Buffer) => {\n const bytes = raw.at(-1) === 13 ? raw.subarray(0, -1) : raw;\n if (bytes.byteLength > 1_000_000) throw new Error(\"agent message exceeds 1 MB\");\n const line = bytes.toString(\"utf8\");\n if (!line.trim()) return;\n const message = parseAgentOutput(line);\n if (message.type === \"attempt.complete\") complete = message;\n const response = await options.onMessage(message);\n if (response && !child.stdin.destroyed) child.stdin.write(encodeAgentInput(response));\n };\n try {\n for await (const raw of child.stdout) {\n const chunk = Buffer.isBuffer(raw) ? raw : Buffer.from(raw);\n outputBytes += chunk.byteLength;\n if (outputBytes > options.task.policy.maxOutputBytes) {\n throw new Error(`agent output exceeds ${options.task.policy.maxOutputBytes} bytes`);\n }\n pending = Buffer.concat([pending, chunk]);\n let newline = pending.indexOf(10);\n while (newline >= 0) {\n await handleLine(pending.subarray(0, newline));\n pending = pending.subarray(newline + 1);\n newline = pending.indexOf(10);\n }\n if (pending.byteLength > 1_000_000) throw new Error(\"agent message exceeds 1 MB\");\n }\n if (pending.byteLength) await handleLine(pending);\n } catch (error) {\n stop(\"protocol_error\");\n throw error;\n }\n })();\n\n const exit = new Promise<number>((accept, reject) => {\n child.once(\"error\", reject);\n child.once(\"exit\", (code) => { exited = true; accept(code ?? 1); });\n });\n try {\n const [exitCode] = await Promise.all([exit, consume]);\n if (stderr && options.onStderr) await options.onStderr(stderr);\n if (options.signal?.aborted) return { exitCode, status: \"cancelled\", stderr };\n const terminal = complete as Extract<HarnessAgentOutput, { type: \"attempt.complete\" }> | null;\n if (!terminal) return { exitCode, status: \"failed\", result: { error: \"agent exited without completion\" }, stderr };\n return { exitCode, status: exitCode === 0 ? terminal.status : \"failed\", result: terminal.result, stderr };\n } catch (error) {\n stop(\"runner_error\");\n await exit.catch(() => 1);\n throw error;\n } finally {\n clearTimeout(timeout);\n options.signal?.removeEventListener(\"abort\", abort);\n }\n}\n","import type { ChatInput, OracleResponse } from \"@odla-ai/ai\";\nimport type { CodeToolPresentation } from \"./code-session-event-types\";\nexport type { CodeToolLocationPreview, CodeToolPresentation } from \"./code-session-event-types\";\n\n/** Current JSONL protocol version exchanged between a runner and an agent container. */\nexport const HARNESS_PROTOCOL_VERSION = 1 as const;\n\n/** Default control-plane route used for model inference requested by coding agents. */\nexport const DEFAULT_AI_ROUTE = \"coding\" as const;\n\n/** Lifecycle state reported for a harness task and its active attempt. */\nexport type HarnessTaskStatus =\n | \"queued\"\n | \"running\"\n | \"cancel_requested\"\n | \"completed\"\n | \"failed\"\n | \"cancelled\";\n\n/** Lifecycle state of one execution attempt for a task. */\nexport type HarnessAttemptStatus = HarnessTaskStatus;\n\n/** Trusted or untrusted participant that emitted a harness event. */\nexport type HarnessActor = \"operator\" | \"runner\" | \"agent\" | \"model\" | \"system\";\n\n/** Resource and isolation limits enforced while an untrusted task executes. */\nexport interface HarnessPolicy {\n network: \"none\";\n timeoutMs: number;\n maxOutputBytes: number;\n maxPatchBytes: number;\n}\n\n/** Immutable task instructions and execution policy delivered with a lease. */\nexport interface HarnessTaskSpec {\n taskId: string;\n attemptId: string;\n title: string;\n prompt: string;\n workspace: string;\n aiRoute: string;\n policy: HarnessPolicy;\n parentAttemptId?: string | null;\n checkpointSeq?: number | null;\n}\n\n/** Time-bound assignment authorizing a runner to execute one task attempt. */\nexport interface HarnessLease {\n protocolVersion: typeof HARNESS_PROTOCOL_VERSION;\n leaseId: string;\n generation: number;\n expiresAt: number;\n task: HarnessTaskSpec;\n}\n\n/** Runner-supplied event before the control plane assigns sequence and task metadata. */\nexport interface HarnessEventInput {\n eventId: string;\n kind: string;\n actor: HarnessActor;\n payload: unknown;\n createdAt: number;\n}\n\n/** Persisted, ordered event associated with a specific task attempt. */\nexport interface HarnessEvent extends HarnessEventInput {\n seq: number;\n taskId: string;\n attemptId: string;\n}\n\n/** List-view metadata for a task and its current attempt. */\nexport interface HarnessTaskSummary {\n taskId: string;\n attemptId: string;\n appId: string;\n env: string;\n title: string;\n prompt: string;\n workspace: string;\n aiRoute: string;\n status: HarnessTaskStatus;\n parentAttemptId: string | null;\n checkpointSeq: number | null;\n runnerId: string | null;\n generation: number;\n createdAt: number;\n updatedAt: number;\n}\n\n/** List-view metadata for one attempt, including retry ancestry and runner ownership. */\nexport interface HarnessAttemptSummary {\n attemptId: string;\n taskId: string;\n parentAttemptId: string | null;\n checkpointSeq: number | null;\n status: HarnessAttemptStatus;\n runnerId: string | null;\n generation: number;\n createdAt: number;\n updatedAt: number;\n}\n\n/** Complete task view including attempts, events, result, and generated patch. */\nexport interface HarnessTaskDetail extends HarnessTaskSummary {\n attempts: HarnessAttemptSummary[];\n events: HarnessEvent[];\n patch: string | null;\n result: unknown;\n}\n\n/** Public control-plane view of a registered harness runner. */\nexport interface HarnessRunnerView {\n runnerId: string;\n appId: string;\n env: string;\n name: string;\n createdAt: number;\n lastSeenAt: number | null;\n revokedAt: number | null;\n}\n\n/** Credential-free normalized model request sent from an agent through the runner. */\nexport interface HarnessInferenceRequest {\n requestId: string;\n /** Exact initial, follow-up, or resume command whose budget this call consumes. */\n interactionId?: string;\n call: ChatInput;\n}\n\n/** Normalized model response plus auditable provider, policy, and token metadata. */\nexport interface HarnessInferenceResponse {\n requestId: string;\n response: OracleResponse;\n receipt: {\n provider: string;\n model: string;\n policyVersion: number;\n inputTokens: number;\n outputTokens: number;\n /**\n * USD charged for this call, priced against the model the control plane\n * actually resolved.\n *\n * ABSENT when the live catalog has no price for that model — never zero.\n * An unpriced call is unknown spend, and reporting it as free is what let\n * a goal's `maxUsd` look enforced while nothing enforced it. The runtime\n * cannot compute this itself: it asks for `brokered` and only the control\n * plane knows which model answered.\n */\n costUsd?: number;\n };\n}\n\n/** Bounded, content-minimized session activity emitted by a Code runtime.\n * Message bodies are projected separately into the app's owner-private\n * odla-db chat. `interactionId` is optional so stored v1 events remain valid. */\nexport type CodeSessionEventData = (\n | { type: \"message\"; actor: \"agent\" | \"system\"; body: string }\n | { type: \"diagnostic\"; level: \"error\"; message: string }\n | { type: \"thinking\"; available: true; durationMs: number }\n | {\n type: \"tool\";\n phase: \"started\";\n tool: HarnessToolName;\n operationId?: string;\n presentation?: CodeToolPresentation;\n }\n | {\n type: \"tool\";\n phase: \"completed\";\n tool: HarnessToolName;\n ok: boolean;\n durationMs: number;\n operationId?: string;\n presentation?: CodeToolPresentation;\n }\n | {\n type: \"collaboration\";\n phase: \"started\";\n skill: string;\n tool: string;\n operationId: string;\n }\n | {\n type: \"collaboration\";\n phase: \"completed\";\n skill: string;\n tool: string;\n ok: boolean;\n durationMs: number;\n operationId: string;\n }\n | {\n type: \"usage\"; provider: string; model: string;\n inputTokens: number; outputTokens: number; durationMs: number;\n interactionTokens?: number; interactionMaxTokens?: number;\n /** USD for this call; absent when the model is unpriced, never zero. */\n costUsd?: number;\n /** Cumulative USD for this owner interaction, when every call in it was\n * priced. Absent the moment one was not, so a partial total can never be\n * mistaken for the whole. */\n interactionCostUsd?: number;\n }\n | {\n type: \"status\"; status: \"running\" | \"idle\" | \"failed\" | \"checkpointed\";\n durationMs?: number;\n }\n) & { interactionId?: string };\n\n/** Registry-assigned cursor and timestamp for an owner-visible Code event. */\nexport type CodeSessionEvent = CodeSessionEventData & {\n eventId: string; sequence: number; createdAt: number;\n};\n\n/** Closed set of effects an agent container may request from its trusted broker. */\nexport type HarnessToolName =\n | \"sandbox.read\"\n | \"sandbox.list\"\n | \"sandbox.search\"\n | \"sandbox.overview\"\n | \"sandbox.where_is\"\n | \"sandbox.who_imports\"\n | \"sandbox.who_touches\"\n | \"sandbox.apply_patch\"\n | \"sandbox.run_recipe\";\n/** Correlated, structured tool request emitted by an untrusted agent container. */\nexport interface HarnessToolRequest {\n requestId: string;\n tool: HarnessToolName;\n input: Record<string, unknown>;\n}\n/** Bounded tool result returned to an agent after trusted policy evaluation. */\nexport interface HarnessToolResponse {\n requestId: string;\n ok: boolean;\n content: string;\n details?: Record<string, unknown>;\n}\n\n/** Validated JSONL message emitted by an untrusted agent container. */\nexport type HarnessAgentOutput =\n | {\n protocolVersion: typeof HARNESS_PROTOCOL_VERSION;\n type: \"event\";\n kind: string;\n payload?: unknown;\n }\n | {\n protocolVersion: typeof HARNESS_PROTOCOL_VERSION;\n type: \"inference.request\";\n requestId: string;\n call: ChatInput;\n }\n | ({ protocolVersion: typeof HARNESS_PROTOCOL_VERSION; type: \"tool.request\" } & HarnessToolRequest)\n | {\n protocolVersion: typeof HARNESS_PROTOCOL_VERSION;\n type: \"attempt.complete\";\n status: \"completed\" | \"failed\" | \"cancelled\";\n result?: unknown;\n };\n\n/** JSONL command or inference result written by the trusted runner to an agent. */\nexport type HarnessAgentInput =\n | {\n protocolVersion: typeof HARNESS_PROTOCOL_VERSION;\n type: \"task.start\";\n task: HarnessTaskSpec;\n }\n | {\n protocolVersion: typeof HARNESS_PROTOCOL_VERSION;\n type: \"inference.response\";\n requestId: string;\n response: OracleResponse;\n }\n | ({ protocolVersion: typeof HARNESS_PROTOCOL_VERSION; type: \"tool.response\" } & HarnessToolResponse)\n | {\n protocolVersion: typeof HARNESS_PROTOCOL_VERSION;\n type: \"attempt.cancel\";\n reason: string;\n };\n\n/** Terminal attempt report submitted by a runner to the control plane. */\nexport interface HarnessCompletion {\n status: \"completed\" | \"failed\" | \"cancelled\";\n result?: unknown;\n patch?: string;\n error?: string;\n}\n\n/** Operations a credentialed runner may perform against the harness control plane. */\nexport interface HarnessControlPlane {\n lease(workspaces: string[]): Promise<HarnessLease | null>;\n heartbeat(attemptId: string, leaseId: string): Promise<{ cancelRequested: boolean; expiresAt: number }>;\n appendEvents(attemptId: string, leaseId: string, events: HarnessEventInput[]): Promise<void>;\n infer(attemptId: string, leaseId: string, request: HarnessInferenceRequest): Promise<HarnessInferenceResponse>;\n complete(attemptId: string, leaseId: string, completion: HarnessCompletion): Promise<void>;\n}\n\n/** Trusted inference bridge used to keep model credentials outside agent containers. */\nexport interface HarnessAiConnection {\n infer(request: HarnessInferenceRequest): Promise<HarnessInferenceResponse>;\n}\n\n/** Trusted tool boundary. Implementations must evaluate CaMeL policy before effects. */\nexport interface HarnessToolBroker {\n execute(\n context: { lease: HarnessLease; workspaceDir: string; signal?: AbortSignal },\n request: HarnessToolRequest,\n ): Promise<HarnessToolResponse>;\n}\n","import type { ChatInput } from \"@odla-ai/ai\";\nimport {\n HARNESS_PROTOCOL_VERSION,\n type HarnessAgentInput,\n type HarnessAgentOutput,\n type HarnessEventInput,\n} from \"./types\";\n\nconst CONTROL = /[\\u0000-\\u0008\\u000b\\u000c\\u000e-\\u001f\\u007f]/;\n\n/** Error raised when an agent emits malformed, oversized, or unsupported protocol data. */\nexport class HarnessProtocolError extends Error {\n override readonly name = \"HarnessProtocolError\";\n}\n\nfunction record(value: unknown): Record<string, unknown> | null {\n return value !== null && typeof value === \"object\" && !Array.isArray(value)\n ? value as Record<string, unknown>\n : null;\n}\n\nfunction boundedText(value: unknown, label: string, max: number): string {\n if (typeof value !== \"string\" || !value || value.length > max || CONTROL.test(value)) {\n throw new HarnessProtocolError(`${label} must be a non-empty string of at most ${max} characters`);\n }\n return value;\n}\n\n/** Parse and validate one newline-delimited message emitted by an agent container. */\nexport function parseAgentOutput(line: string): HarnessAgentOutput {\n if (Buffer.byteLength(line, \"utf8\") > 1_000_000) throw new HarnessProtocolError(\"agent message exceeds 1 MB\");\n let value: unknown;\n try { value = JSON.parse(line); } catch { throw new HarnessProtocolError(\"agent emitted invalid JSON\"); }\n const message = record(value);\n if (!message || message.protocolVersion !== HARNESS_PROTOCOL_VERSION) {\n throw new HarnessProtocolError(`agent protocolVersion must be ${HARNESS_PROTOCOL_VERSION}`);\n }\n if (message.type === \"event\") {\n return {\n protocolVersion: HARNESS_PROTOCOL_VERSION,\n type: \"event\",\n kind: boundedText(message.kind, \"event.kind\", 120),\n ...(message.payload === undefined ? {} : { payload: message.payload }),\n };\n }\n if (message.type === \"inference.request\") {\n const call = record(message.call);\n if (!call || !Array.isArray(call.messages) || !Number.isSafeInteger(call.maxTokens)) {\n throw new HarnessProtocolError(\"inference.request.call requires messages and maxTokens\");\n }\n return {\n protocolVersion: HARNESS_PROTOCOL_VERSION,\n type: \"inference.request\",\n requestId: boundedText(message.requestId, \"requestId\", 180),\n call: call as unknown as ChatInput,\n };\n }\n if (message.type === \"tool.request\") {\n const input = record(message.input);\n const tool = String(message.tool);\n if (!input || ![\"sandbox.read\", \"sandbox.apply_patch\", \"sandbox.run_recipe\"].includes(tool)) {\n throw new HarnessProtocolError(\"tool.request requires a registered tool and object input\");\n }\n return {\n protocolVersion: HARNESS_PROTOCOL_VERSION,\n type: \"tool.request\",\n requestId: boundedText(message.requestId, \"requestId\", 180),\n tool: tool as \"sandbox.read\" | \"sandbox.apply_patch\" | \"sandbox.run_recipe\",\n input,\n };\n }\n if (message.type === \"attempt.complete\") {\n if (!new Set([\"completed\", \"failed\", \"cancelled\"]).has(String(message.status))) {\n throw new HarnessProtocolError(\"attempt.complete.status is invalid\");\n }\n return {\n protocolVersion: HARNESS_PROTOCOL_VERSION,\n type: \"attempt.complete\",\n status: message.status as \"completed\" | \"failed\" | \"cancelled\",\n ...(message.result === undefined ? {} : { result: message.result }),\n };\n }\n throw new HarnessProtocolError(\"agent message type is unsupported\");\n}\n\n/** Serialize one trusted runner message as a newline-terminated JSONL record. */\nexport function encodeAgentInput(message: HarnessAgentInput): string {\n return `${JSON.stringify(message)}\\n`;\n}\n\n/** Create a timestamped, uniquely identified event for control-plane submission. */\nexport function makeHarnessEvent(\n kind: string,\n actor: HarnessEventInput[\"actor\"],\n payload: unknown,\n now = Date.now(),\n id = crypto.randomUUID(),\n): HarnessEventInput {\n boundedText(kind, \"event.kind\", 120);\n return { eventId: id, kind, actor, payload, createdAt: now };\n}\n","import { setTimeout as delay } from \"node:timers/promises\";\nimport { runContainerAttempt, type ContainerEngine, type ContainerLimits } from \"./container\";\nimport { makeHarnessEvent } from \"./protocol\";\nimport { stageWorkspace, type StagedWorkspace } from \"./workspace\";\nimport {\n HARNESS_PROTOCOL_VERSION,\n type HarnessAgentInput,\n type HarnessAgentOutput,\n type HarnessControlPlane,\n type HarnessLease,\n type HarnessToolBroker,\n} from \"./types\";\n\n/** Control-plane, workspace, isolation, polling, and lifecycle settings for a runner. */\nexport interface HarnessRunnerOptions {\n control: HarnessControlPlane;\n workspaces: Readonly<Record<string, string>>;\n engine: ContainerEngine;\n image: string;\n limits?: ContainerLimits;\n heartbeatMs?: number;\n pollMs?: number;\n once?: boolean;\n preserveWorkspace?: boolean;\n allowUnpinnedImage?: boolean;\n workspaceAccess?: \"read-write\" | \"read-only\" | \"none\";\n signal?: AbortSignal;\n log?: (message: string) => void;\n toolBroker?: HarnessToolBroker;\n}\n\nasync function append(\n control: HarnessControlPlane,\n lease: HarnessLease,\n kind: string,\n actor: \"runner\" | \"agent\" | \"model\" | \"system\",\n payload: unknown,\n): Promise<void> {\n await control.appendEvents(lease.task.attemptId, lease.leaseId, [makeHarnessEvent(kind, actor, payload)]);\n}\n\n/** Execute one leased task. The registered workspace is copied before the\n * container starts; neither the checkout nor the runner credential is mounted. */\nexport async function runLeasedAttempt(lease: HarnessLease, options: HarnessRunnerOptions): Promise<void> {\n const source = options.workspaces[lease.task.workspace];\n if (!source) {\n await options.control.complete(lease.task.attemptId, lease.leaseId, {\n status: \"failed\",\n error: `runner does not expose workspace \"${lease.task.workspace}\"`,\n });\n return;\n }\n\n let staged: StagedWorkspace | null = null;\n const controller = new AbortController();\n const cancelFromParent = () => controller.abort(options.signal?.reason);\n options.signal?.addEventListener(\"abort\", cancelFromParent, { once: true });\n if (options.signal?.aborted) controller.abort(options.signal.reason);\n let heartbeat: ReturnType<typeof setInterval> | undefined;\n let heartbeatInFlight = false;\n const pulse = async () => {\n if (heartbeatInFlight || controller.signal.aborted) return;\n heartbeatInFlight = true;\n try {\n const value = await options.control.heartbeat(lease.task.attemptId, lease.leaseId);\n if (value.cancelRequested) controller.abort(\"cancel_requested\");\n } catch {\n controller.abort(\"heartbeat_failed\");\n } finally {\n heartbeatInFlight = false;\n }\n };\n try {\n await pulse();\n heartbeat = setInterval(() => { void pulse(); }, options.heartbeatMs ?? 15_000);\n if (controller.signal.aborted) throw new Error(\"lease was cancelled before workspace staging\");\n staged = await stageWorkspace(source);\n if (controller.signal.aborted) throw new Error(\"lease was cancelled during workspace staging\");\n const stagedWorkspace = staged;\n await append(options.control, lease, \"runner.workspace_staged\", \"runner\", {\n workspace: lease.task.workspace,\n files: stagedWorkspace.fileCount,\n bytes: stagedWorkspace.byteCount,\n });\n\n const result = await runContainerAttempt({\n engine: options.engine,\n image: options.image,\n workspaceDir: stagedWorkspace.workspaceDir,\n task: lease.task,\n limits: options.limits,\n allowUnpinnedImage: options.allowUnpinnedImage,\n workspaceAccess: options.workspaceAccess ?? (options.toolBroker ? \"none\" : \"read-write\"),\n signal: controller.signal,\n onStderr: async (text) => {\n await append(options.control, lease, \"agent.stderr\", \"agent\", { text: text.slice(0, 64 * 1024) });\n },\n onMessage: async (message: HarnessAgentOutput): Promise<HarnessAgentInput | void> => {\n if (message.type === \"event\") {\n await append(options.control, lease, message.kind, \"agent\", message.payload ?? null);\n return;\n }\n if (message.type === \"attempt.complete\") {\n await append(options.control, lease, \"agent.completed\", \"agent\", {\n status: message.status,\n result: message.result ?? null,\n });\n return;\n }\n if (message.type === \"tool.request\") {\n await append(options.control, lease, \"tool.requested\", \"agent\", {\n requestId: message.requestId, tool: message.tool,\n });\n const response = options.toolBroker\n ? await options.toolBroker.execute({\n lease, workspaceDir: stagedWorkspace.workspaceDir, signal: controller.signal,\n }, message)\n : { requestId: message.requestId, ok: false, content: \"tool denied: no trusted broker configured\" };\n await append(options.control, lease, \"tool.responded\", \"system\", {\n requestId: message.requestId, tool: message.tool, ok: response.ok,\n contentBytes: Buffer.byteLength(response.content),\n });\n return { protocolVersion: HARNESS_PROTOCOL_VERSION, type: \"tool.response\", ...response };\n }\n await append(options.control, lease, \"model.requested\", \"agent\", {\n requestId: message.requestId,\n messages: message.call.messages.length,\n maxTokens: message.call.maxTokens,\n });\n const response = await options.control.infer(lease.task.attemptId, lease.leaseId, {\n requestId: message.requestId,\n call: message.call,\n });\n await append(options.control, lease, \"model.responded\", \"model\", {\n requestId: message.requestId,\n response: response.response,\n receipt: response.receipt,\n });\n return {\n protocolVersion: HARNESS_PROTOCOL_VERSION,\n type: \"inference.response\",\n requestId: message.requestId,\n response: response.response,\n };\n },\n });\n\n const patch = await stagedWorkspace.patch(lease.task.policy.maxPatchBytes);\n await options.control.complete(lease.task.attemptId, lease.leaseId, {\n status: result.status,\n result: result.result,\n patch,\n ...(result.status === \"failed\" ? { error: result.stderr.slice(0, 4_000) || \"container attempt failed\" } : {}),\n });\n } catch (reason) {\n const message = reason instanceof Error ? reason.message : \"runner failed\";\n try {\n await append(options.control, lease, \"runner.failed\", \"runner\", { message });\n await options.control.complete(lease.task.attemptId, lease.leaseId, {\n status: controller.signal.aborted ? \"cancelled\" : \"failed\",\n error: message,\n });\n } catch {\n // A lost or revoked lease can also make the terminal report unavailable.\n }\n } finally {\n if (heartbeat) clearInterval(heartbeat);\n options.signal?.removeEventListener(\"abort\", cancelFromParent);\n if (staged && !options.preserveWorkspace) await staged.cleanup();\n }\n}\n\n/** One runner executes one attempt at a time. Concurrency comes from multiple\n * independently credentialed runner processes. */\nexport async function runHarnessRunner(options: HarnessRunnerOptions): Promise<void> {\n const workspaceNames = Object.keys(options.workspaces).sort();\n if (!workspaceNames.length) throw new TypeError(\"at least one workspace mapping is required\");\n do {\n if (options.signal?.aborted) return;\n const lease = await options.control.lease(workspaceNames);\n if (lease) {\n options.log?.(`leased ${lease.task.taskId}/${lease.task.attemptId}`);\n await runLeasedAttempt(lease, options);\n if (options.once) return;\n continue;\n }\n if (options.once) return;\n await delay(options.pollMs ?? 2_000, undefined, { signal: options.signal }).catch(() => {});\n } while (!options.signal?.aborted);\n}\n","import { chmod, copyFile, lstat, mkdir, mkdtemp, readdir, realpath, rm, stat } from \"node:fs/promises\";\nimport { tmpdir } from \"node:os\";\nimport { basename, join, relative, resolve, sep } from \"node:path\";\nimport { spawn } from \"node:child_process\";\nimport { allowedWorkspacePath, SECRET_WORKSPACE_FILE, SKIP_WORKSPACE_DIRS } from \"./workspace-policy\";\nexport { materializeGitTree, type MaterializedGitTree } from \"./workspace-git-tree\";\n\n/** File, byte, and temporary-directory limits applied while staging a workspace. */\nexport interface StageWorkspaceOptions {\n maxFiles?: number;\n maxBytes?: number;\n tempRoot?: string;\n /** Stage tracked files plus non-ignored untracked files from a Git checkout. */\n gitTrackedAndUnignored?: boolean;\n}\n\n/** Disposable baseline and mutable workspace copy used to generate a bounded patch. */\nexport interface StagedWorkspace {\n root: string;\n baselineDir: string;\n workspaceDir: string;\n fileCount: number;\n byteCount: number;\n patch(maxBytes: number): Promise<string>;\n cleanup(): Promise<void>;\n}\n\ninterface SourceFile {\n source: string;\n relativePath: string;\n mode: number;\n bytes: number;\n}\n\nasync function sourceFiles(sourceDir: string, maxFiles: number, maxBytes: number): Promise<SourceFile[]> {\n const files: SourceFile[] = [];\n let bytes = 0;\n const walk = async (dir: string): Promise<void> => {\n for (const entry of await readdir(dir, { withFileTypes: true })) {\n if (entry.isDirectory() && SKIP_WORKSPACE_DIRS.has(entry.name)) continue;\n if (!entry.isDirectory() && SECRET_WORKSPACE_FILE.test(entry.name)) continue;\n const path = join(dir, entry.name);\n if (entry.isSymbolicLink()) continue;\n if (entry.isDirectory()) {\n await walk(path);\n continue;\n }\n if (!entry.isFile()) continue;\n const metadata = await stat(path);\n bytes += metadata.size;\n if (files.length + 1 > maxFiles) throw new Error(`workspace exceeds ${maxFiles} files`);\n if (bytes > maxBytes) throw new Error(`workspace exceeds ${maxBytes} bytes`);\n files.push({\n source: path,\n relativePath: relative(sourceDir, path),\n mode: metadata.mode & 0o777,\n bytes: metadata.size,\n });\n }\n };\n await walk(sourceDir);\n return files.sort((left, right) => left.relativePath.localeCompare(right.relativePath));\n}\n\nasync function gitSourceFiles(sourceDir: string, maxFiles: number, maxBytes: number): Promise<SourceFile[]> {\n const child = spawn(\"git\", [\"ls-files\", \"-z\", \"--cached\", \"--others\", \"--exclude-standard\"], {\n cwd: sourceDir, stdio: [\"ignore\", \"pipe\", \"pipe\"], shell: false,\n });\n const stdout: Buffer[] = [];\n const stderr: Buffer[] = [];\n let outputBytes = 0;\n child.stdout.on(\"data\", (chunk: Buffer) => {\n outputBytes += chunk.byteLength;\n if (outputBytes > 8 * 1024 * 1024) child.kill(\"SIGKILL\");\n else stdout.push(chunk);\n });\n child.stderr.on(\"data\", (chunk: Buffer) => {\n if (stderr.reduce((sum, value) => sum + value.byteLength, 0) < 16_384) stderr.push(chunk);\n });\n const code = await new Promise<number | null>((accept, reject) => {\n child.once(\"error\", reject);\n child.once(\"exit\", accept);\n });\n if (outputBytes > 8 * 1024 * 1024) throw new Error(\"git file inventory exceeds 8 MiB\");\n if (code !== 0) throw new Error(`git file inventory failed: ${Buffer.concat(stderr).toString(\"utf8\").slice(0, 1_000)}`);\n const paths = Buffer.concat(stdout).toString(\"utf8\").split(\"\\0\").filter(Boolean).sort();\n if (paths.length > maxFiles) throw new Error(`workspace exceeds ${maxFiles} files`);\n const root = resolve(sourceDir);\n const files: SourceFile[] = [];\n let bytes = 0;\n for (const relativePath of paths) {\n if (!allowedWorkspacePath(relativePath)) continue;\n const source = resolve(root, relativePath);\n if (!source.startsWith(`${root}${sep}`)) throw new TypeError(\"git file path escapes workspace\");\n let metadata;\n try { metadata = await lstat(source); }\n catch (error) {\n if ((error as NodeJS.ErrnoException).code === \"ENOENT\") continue;\n throw error;\n }\n if (metadata.isSymbolicLink() || !metadata.isFile()) continue;\n bytes += metadata.size;\n if (bytes > maxBytes) throw new Error(`workspace exceeds ${maxBytes} bytes`);\n files.push({ source, relativePath, mode: metadata.mode & 0o777, bytes: metadata.size });\n }\n return files;\n}\n\nasync function copyTree(files: SourceFile[], destination: string): Promise<void> {\n for (const file of files) {\n const target = join(destination, file.relativePath);\n await mkdir(resolve(target, \"..\"), { recursive: true });\n await copyFile(file.source, target);\n await chmod(target, file.mode);\n }\n}\n\nasync function captureGitDiff(root: string, maxBytes: number): Promise<string> {\n const child = spawn(\"git\", [\n \"diff\", \"--no-index\", \"--binary\", \"--no-ext-diff\",\n \"--src-prefix=a/\", \"--dst-prefix=b/\", \"--\", \"baseline\", \"workspace\",\n ], { cwd: root, stdio: [\"ignore\", \"pipe\", \"pipe\"], shell: false });\n const stdout: Buffer[] = [];\n const stderr: Buffer[] = [];\n let bytes = 0;\n child.stdout.on(\"data\", (chunk: Buffer) => {\n bytes += chunk.byteLength;\n if (bytes > maxBytes) child.kill(\"SIGKILL\");\n else stdout.push(chunk);\n });\n child.stderr.on(\"data\", (chunk: Buffer) => {\n if (stderr.reduce((sum, value) => sum + value.byteLength, 0) < 16_384) stderr.push(chunk);\n });\n const code = await new Promise<number | null>((accept, reject) => {\n child.once(\"error\", reject);\n child.once(\"exit\", accept);\n });\n if (bytes > maxBytes) throw new Error(`patch exceeds ${maxBytes} bytes`);\n if (code !== 0 && code !== 1) {\n throw new Error(`git diff failed: ${Buffer.concat(stderr).toString(\"utf8\").slice(0, 1_000)}`);\n }\n return Buffer.concat(stdout).toString(\"utf8\")\n .replaceAll(\"a/baseline/\", \"a/\")\n .replaceAll(\"a/workspace/\", \"a/\")\n .replaceAll(\"b/baseline/\", \"b/\")\n .replaceAll(\"b/workspace/\", \"b/\")\n .replaceAll(\"--- a/baseline\", \"--- a\")\n .replaceAll(\"+++ b/workspace\", \"+++ b\");\n}\n\n/** Copy a bounded, secret-filtered workspace twice: one immutable baseline and\n * one disposable directory mounted into the container. The developer checkout\n * itself is never mounted. */\nexport async function stageWorkspace(source: string, options: StageWorkspaceOptions = {}): Promise<StagedWorkspace> {\n const sourceDir = await realpath(resolve(source));\n const sourceStat = await stat(sourceDir);\n if (!sourceStat.isDirectory()) throw new TypeError(\"workspace source must be a directory\");\n const root = await mkdtemp(join(options.tempRoot ?? tmpdir(), \"odla-harness-\"));\n const baselineDir = join(root, \"baseline\");\n const workspaceDir = join(root, \"workspace\");\n await Promise.all([mkdir(baselineDir), mkdir(workspaceDir)]);\n try {\n const maxFiles = options.maxFiles ?? 20_000;\n const maxBytes = options.maxBytes ?? 512 * 1024 * 1024;\n const files = options.gitTrackedAndUnignored\n ? await gitSourceFiles(sourceDir, maxFiles, maxBytes)\n : await sourceFiles(sourceDir, maxFiles, maxBytes);\n await Promise.all([copyTree(files, baselineDir), copyTree(files, workspaceDir)]);\n return {\n root,\n baselineDir,\n workspaceDir,\n fileCount: files.length,\n byteCount: files.reduce((sum, file) => sum + file.bytes, 0),\n patch: (maxBytes) => captureGitDiff(root, maxBytes),\n cleanup: () => rm(root, { recursive: true, force: true }),\n };\n } catch (error) {\n await rm(root, { recursive: true, force: true });\n throw error;\n }\n}\n\n/** Create a disposable workspace whose diff base and initial editable tree\n * intentionally come from different already-filtered sources. */\nexport async function stageWorkspacePair(\n baselineSource: string, workspaceSource: string, options: StageWorkspaceOptions = {},\n): Promise<StagedWorkspace> {\n const baselineDirSource = await realpath(resolve(baselineSource));\n const workspaceDirSource = await realpath(resolve(workspaceSource));\n const maxFiles = options.maxFiles ?? 20_000;\n const maxBytes = options.maxBytes ?? 512 * 1024 * 1024;\n const [baselineFiles, workspaceFiles] = await Promise.all([\n sourceFiles(baselineDirSource, maxFiles, maxBytes),\n sourceFiles(workspaceDirSource, maxFiles, maxBytes),\n ]);\n const root = await mkdtemp(join(options.tempRoot ?? tmpdir(), \"odla-harness-\"));\n const baselineDir = join(root, \"baseline\");\n const workspaceDir = join(root, \"workspace\");\n await Promise.all([mkdir(baselineDir), mkdir(workspaceDir)]);\n try {\n await Promise.all([copyTree(baselineFiles, baselineDir), copyTree(workspaceFiles, workspaceDir)]);\n return {\n root, baselineDir, workspaceDir,\n fileCount: workspaceFiles.length,\n byteCount: workspaceFiles.reduce((sum, file) => sum + file.bytes, 0),\n patch: (maxPatchBytes) => captureGitDiff(root, maxPatchBytes),\n cleanup: () => rm(root, { recursive: true, force: true }),\n };\n } catch (error) {\n await rm(root, { recursive: true, force: true });\n throw error;\n }\n}\n\n/** Convert a path-like value into a bounded lowercase label safe for runner metadata. */\nexport function safeWorkspaceLabel(value: string): string {\n const label = basename(value).toLowerCase().replace(/[^a-z0-9_-]+/g, \"-\").replace(/^-+|-+$/g, \"\");\n if (!label) throw new TypeError(\"workspace label is empty\");\n return label.slice(0, 80);\n}\n","import { isAbsolute } from \"node:path\";\n\nexport const SKIP_WORKSPACE_DIRS = new Set([\n \".git\", \".odla\", \".wrangler\", \"node_modules\", \"dist\", \"coverage\",\n]);\nexport const SECRET_WORKSPACE_FILE = /^(?:\\.env(?:\\..+)?|\\.dev\\.vars|\\.dev-token(?:\\..+)?|credentials(?:\\..+)?\\.json|dev-token(?:\\..+)?(?:\\.json)?)$/i;\n\n/** Reject paths that are unsafe or reserved at either the local or Git-tree boundary. */\nexport function allowedWorkspacePath(relativePath: string): boolean {\n const parts = relativePath.split(\"/\");\n return !isAbsolute(relativePath) && !relativePath.includes(\"\\\\\") && !relativePath.includes(\"\\0\")\n && !parts.some((part) => !part || part === \".\" || part === \"..\" || SKIP_WORKSPACE_DIRS.has(part))\n && !SECRET_WORKSPACE_FILE.test(parts.at(-1) ?? \"\");\n}\n"],"mappings":"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","names":["import_node_path","resolve","access","import_promises","import_promises","import_node_path","import_node_child_process","import_node_path","maxBytes","response","delay"]}
1
+ {"version":3,"sources":["../src/cli.ts","../src/client.ts","../src/container.ts","../src/types.ts","../src/protocol.ts","../src/runner.ts","../src/workspace.ts","../src/workspace-policy.ts"],"sourcesContent":["#!/usr/bin/env node\nimport { resolve } from \"node:path\";\nimport { createHarnessControlClient } from \"./client\";\nimport { selectContainerEngine, type ContainerEngine } from \"./container\";\nimport { runHarnessRunner } from \"./runner\";\n\ninterface CliOptions {\n endpoint: string;\n engine: ContainerEngine | \"auto\";\n image: string;\n workspaces: Record<string, string>;\n once: boolean;\n pollMs: number;\n preserveWorkspace: boolean;\n allowUnpinnedImage: boolean;\n}\n\nfunction usage(): string {\n return `Usage:\n ODLA_HARNESS_TOKEN=odla_hrn_... odla-harness runner \\\\\n --endpoint https://odla.ai \\\\\n --workspace my-repo=/absolute/path \\\\\n --image registry.example/agent@sha256:<digest> [--engine auto|container|podman|docker] [--once]\n\nThe token is read only from ODLA_HARNESS_TOKEN so it does not enter shell history.\nImages must be digest-pinned. Network is disabled inside the container.\nAuto prefers Apple container on macOS and rootless Podman on Linux.`;\n}\n\nfunction parse(argv: string[]): CliOptions {\n if (argv[0] !== \"runner\") throw new TypeError(usage());\n const values: Record<string, string[]> = {};\n const flags = new Set<string>();\n for (let index = 1; index < argv.length; index++) {\n const arg = argv[index]!;\n if ([\"--once\", \"--preserve-workspace\", \"--allow-unpinned-image\"].includes(arg)) {\n flags.add(arg);\n continue;\n }\n if (!arg.startsWith(\"--\") || !argv[index + 1]) throw new TypeError(`missing value for ${arg}`);\n (values[arg] ??= []).push(argv[++index]!);\n }\n const endpoint = values[\"--endpoint\"]?.at(-1);\n const image = values[\"--image\"]?.at(-1);\n const engine = values[\"--engine\"]?.at(-1) ?? \"auto\";\n if (!endpoint || !image || ![\"auto\", \"container\", \"podman\", \"docker\"].includes(engine)) throw new TypeError(usage());\n const workspaces: Record<string, string> = {};\n for (const mapping of values[\"--workspace\"] ?? []) {\n const equals = mapping.indexOf(\"=\");\n const key = mapping.slice(0, equals);\n const path = mapping.slice(equals + 1);\n if (equals < 1 || !/^[a-z0-9][a-z0-9_-]{0,79}$/.test(key) || !path) {\n throw new TypeError(`invalid workspace mapping: ${mapping}`);\n }\n workspaces[key] = resolve(path);\n }\n if (!Object.keys(workspaces).length) throw new TypeError(\"at least one --workspace key=/absolute/path is required\");\n const allowUnpinnedImage = flags.has(\"--allow-unpinned-image\");\n if (allowUnpinnedImage && process.env.ODLA_HARNESS_UNSAFE_TESTING !== \"1\") {\n throw new TypeError(\"--allow-unpinned-image requires ODLA_HARNESS_UNSAFE_TESTING=1\");\n }\n const pollMs = Number(values[\"--poll-ms\"]?.at(-1) ?? 2_000);\n if (!Number.isSafeInteger(pollMs) || pollMs < 250 || pollMs > 60_000) {\n throw new TypeError(\"--poll-ms must be an integer from 250 to 60000\");\n }\n return {\n endpoint,\n image,\n engine: engine as ContainerEngine | \"auto\",\n workspaces,\n once: flags.has(\"--once\"),\n pollMs,\n preserveWorkspace: flags.has(\"--preserve-workspace\"),\n allowUnpinnedImage,\n };\n}\n\nasync function main(): Promise<void> {\n const token = process.env.ODLA_HARNESS_TOKEN;\n if (!token) throw new TypeError(\"ODLA_HARNESS_TOKEN is required\");\n const options = parse(process.argv.slice(2));\n const controller = new AbortController();\n for (const signal of [\"SIGINT\", \"SIGTERM\"] as const) process.once(signal, () => controller.abort(signal));\n const engine = await selectContainerEngine(options.engine);\n if (process.platform === \"linux\" && engine === \"docker\") {\n process.stderr.write(\"[odla-harness] warning: explicit Docker on Linux may use a rootful daemon; rootless Podman is preferred\\n\");\n }\n await runHarnessRunner({\n ...options,\n engine,\n control: createHarnessControlClient({ endpoint: options.endpoint, token, signal: controller.signal }),\n signal: controller.signal,\n log: (message) => process.stderr.write(`[odla-harness] ${message}\\n`),\n });\n}\n\nmain().catch((error) => {\n process.stderr.write(`${error instanceof Error ? error.message : String(error)}\\n`);\n process.exitCode = 1;\n});\n","import type {\n HarnessCompletion,\n HarnessControlPlane,\n HarnessEventInput,\n HarnessInferenceRequest,\n HarnessInferenceResponse,\n HarnessLease,\n} from \"./types\";\n\n/** HTTP error returned by the harness control plane, including its stable error code. */\nexport class HarnessControlError extends Error {\n override readonly name = \"HarnessControlError\";\n constructor(message: string, readonly status: number, readonly code = \"control_error\") { super(message); }\n}\n\n/** Connection, credential, cancellation, and timeout settings for a runner client. */\nexport interface HarnessControlClientOptions {\n endpoint: string;\n token: string;\n fetch?: typeof fetch;\n requestTimeoutMs?: number;\n signal?: AbortSignal;\n}\n\n/** Create a validated HTTPS client implementing the runner control-plane operations. */\nexport function createHarnessControlClient(options: HarnessControlClientOptions): HarnessControlPlane {\n const endpoint = options.endpoint.replace(/\\/+$/, \"\");\n let endpointUrl: URL;\n try { endpointUrl = new URL(endpoint); } catch { throw new TypeError(\"endpoint must be an HTTPS URL\"); }\n const loopback = endpointUrl.hostname === \"localhost\" || endpointUrl.hostname === \"127.0.0.1\" || endpointUrl.hostname === \"[::1]\";\n if (endpointUrl.username || endpointUrl.password || (endpointUrl.protocol !== \"https:\" && !(loopback && endpointUrl.protocol === \"http:\"))) {\n throw new TypeError(\"endpoint must use HTTPS (HTTP is allowed only for loopback testing)\");\n }\n if (!/^odla_hrn_[0-9a-f]{64}$/.test(options.token)) throw new TypeError(\"invalid harness runner credential\");\n const requestTimeoutMs = options.requestTimeoutMs ?? 30_000;\n if (!Number.isSafeInteger(requestTimeoutMs) || requestTimeoutMs < 1_000 || requestTimeoutMs > 120_000) {\n throw new TypeError(\"requestTimeoutMs must be an integer from 1000 to 120000\");\n }\n const request = options.fetch ?? fetch;\n const call = async <T>(path: string, body: unknown, allowEmpty = false): Promise<T | null> => {\n const timeout = AbortSignal.timeout(requestTimeoutMs);\n const signal = options.signal ? AbortSignal.any([options.signal, timeout]) : timeout;\n const response = await request(`${endpoint}${path}`, {\n method: \"POST\",\n headers: { authorization: `Bearer ${options.token}`, \"content-type\": \"application/json\" },\n body: JSON.stringify(body),\n redirect: \"error\",\n signal,\n });\n if (allowEmpty && response.status === 204) return null;\n const value = await response.json().catch(() => null) as { error?: { code?: string; message?: string } } | null;\n if (!response.ok) throw new HarnessControlError(\n value?.error?.message ?? `harness control request failed (${response.status})`,\n response.status,\n value?.error?.code,\n );\n return value as T;\n };\n return {\n lease: async (workspaces) => {\n const body = await call<{ lease: HarnessLease }>(\"/registry/harness/lease\", { workspaces }, true);\n return body?.lease ?? null;\n },\n heartbeat: async (attemptId, leaseId) => {\n const body = await call<{ cancelRequested: boolean; expiresAt: number }>(\n `/registry/harness/attempts/${encodeURIComponent(attemptId)}/heartbeat`, { leaseId },\n );\n return body!;\n },\n appendEvents: async (attemptId, leaseId, events: HarnessEventInput[]) => {\n await call(`/registry/harness/attempts/${encodeURIComponent(attemptId)}/events`, { leaseId, events });\n },\n infer: async (attemptId, leaseId, inference: HarnessInferenceRequest) => {\n const body = await call<HarnessInferenceResponse>(\n `/registry/harness/attempts/${encodeURIComponent(attemptId)}/inference`, { leaseId, ...inference },\n );\n return body!;\n },\n complete: async (attemptId, leaseId, completion: HarnessCompletion) => {\n await call(`/registry/harness/attempts/${encodeURIComponent(attemptId)}/complete`, { leaseId, ...completion });\n },\n };\n}\n","import { execFile, spawn } from \"node:child_process\";\nimport { constants } from \"node:fs\";\nimport { access } from \"node:fs/promises\";\nimport { delimiter, join } from \"node:path\";\nimport { getgid, getuid } from \"node:process\";\nimport { encodeAgentInput, parseAgentOutput } from \"./protocol\";\nimport {\n HARNESS_PROTOCOL_VERSION,\n type HarnessAgentInput,\n type HarnessAgentOutput,\n type HarnessTaskSpec,\n} from \"./types\";\n\nconst DIGEST_IMAGE = /^[a-z0-9][a-z0-9._/-]*(?::[a-zA-Z0-9._-]+)?@sha256:[0-9a-f]{64}$/;\n\n/** Supported command-line container engines for isolated harness attempts. */\nexport type ContainerEngine = \"container\" | \"podman\" | \"docker\";\n\n/** Host facts and executable probe used while selecting a safe container engine. */\nexport interface ContainerEngineSelectionOptions {\n platform?: NodeJS.Platform;\n arch?: string;\n uid?: number;\n available?: (engine: ContainerEngine) => Promise<boolean>;\n}\n\n/** Host facts and rootless probe used to verify the selected engine boundary. */\nexport interface ContainerEngineVerificationOptions {\n platform?: NodeJS.Platform;\n arch?: string;\n uid?: number;\n podmanRootless?: () => Promise<boolean>;\n}\n\n/** Optional CPU, memory, process, and temporary-filesystem limits for an attempt. */\nexport interface ContainerLimits {\n cpus?: number;\n memory?: string;\n pids?: number;\n tmpfsBytes?: number;\n}\n\n/** Container, task, callback, and cancellation settings for one agent attempt. */\nexport interface ContainerRunOptions {\n engine: ContainerEngine;\n image: string;\n workspaceDir: string;\n workspaceAccess?: \"read-write\" | \"read-only\" | \"none\";\n task: HarnessTaskSpec;\n limits?: ContainerLimits;\n allowUnpinnedImage?: boolean;\n signal?: AbortSignal;\n onMessage(message: HarnessAgentOutput): Promise<HarnessAgentInput | void>;\n onStderr?(text: string): Promise<void> | void;\n}\n\n/** Terminal container outcome and bounded diagnostic output returned to the runner. */\nexport interface ContainerRunResult {\n exitCode: number;\n status: \"completed\" | \"failed\" | \"cancelled\";\n result?: unknown;\n stderr: string;\n}\n\n/** Require an immutable OCI image reference pinned to a SHA-256 digest. */\nexport function assertPinnedImage(image: string): void {\n if (!DIGEST_IMAGE.test(image)) throw new TypeError(\"container image must be pinned by sha256 digest\");\n}\n\nasync function commandAvailable(engine: ContainerEngine): Promise<boolean> {\n for (const directory of (process.env.PATH ?? \"\").split(delimiter).filter(Boolean)) {\n try { await access(join(directory, engine), constants.X_OK); return true; } catch { /* try the next PATH entry */ }\n }\n return false;\n}\n\n/** Choose the strongest installed local default without silently selecting a\n * rootful Linux daemon. Apple container is a per-container VM boundary;\n * rootless Podman is the Linux default; Docker remains explicit. */\nexport async function selectContainerEngine(\n requested: ContainerEngine | \"auto\" = \"auto\",\n options: ContainerEngineSelectionOptions = {},\n): Promise<ContainerEngine> {\n const platform = options.platform ?? process.platform;\n const arch = options.arch ?? process.arch;\n const uid = options.uid ?? (typeof getuid === \"function\" ? getuid() : 1000);\n const available = options.available ?? commandAvailable;\n const validate = async (engine: ContainerEngine): Promise<ContainerEngine> => {\n if (engine === \"container\" && (platform !== \"darwin\" || arch !== \"arm64\")) {\n throw new TypeError(\"Apple container requires Apple Silicon macOS\");\n }\n if (engine === \"podman\" && platform === \"linux\" && uid === 0) {\n throw new TypeError(\"the Linux harness requires rootless Podman; do not run the runner as root\");\n }\n if (!(await available(engine))) throw new TypeError(`${engine} is not installed or executable`);\n return engine;\n };\n if (requested !== \"auto\") return validate(requested);\n const candidates: ContainerEngine[] = platform === \"darwin\"\n ? arch === \"arm64\" ? [\"container\", \"podman\"] : [\"podman\"]\n : platform === \"linux\" ? [\"podman\"] : [];\n for (const engine of candidates) {\n if (await available(engine)) return validate(engine);\n }\n if (platform === \"linux\") {\n throw new TypeError(\"no rootless Podman found; install Podman or explicitly choose --engine docker after reviewing its daemon boundary\");\n }\n if (platform === \"darwin\") {\n throw new TypeError(\"Apple container is not installed; on Apple Silicon macOS 26 run `brew install container`, then retry (Podman Machine is the fallback)\");\n }\n throw new TypeError(\"no supported container engine found\");\n}\n\nfunction inspectRootlessPodman(): Promise<boolean> {\n return new Promise((resolve, reject) => {\n execFile(\n \"podman\",\n [\"info\", \"--format\", \"{{.Host.Security.Rootless}}\"],\n { encoding: \"utf8\", maxBuffer: 16 * 1024, timeout: 10_000 },\n (error, stdout) => {\n if (error) {\n reject(new TypeError(\"could not verify that the active Podman service is rootless\"));\n return;\n }\n resolve(stdout.trim() === \"true\");\n },\n );\n });\n}\n\n/** Fail closed if the selected engine cannot provide the promised host\n * boundary. This is checked for every attempt so a changed Podman connection\n * cannot silently turn a rootless Linux runner into a rootful one. */\nexport async function verifyContainerEngineBoundary(\n engine: ContainerEngine,\n options: ContainerEngineVerificationOptions = {},\n): Promise<void> {\n const platform = options.platform ?? process.platform;\n const arch = options.arch ?? process.arch;\n const uid = options.uid ?? (typeof getuid === \"function\" ? getuid() : 1000);\n if (engine === \"container\" && (platform !== \"darwin\" || arch !== \"arm64\")) {\n throw new TypeError(\"Apple container requires Apple Silicon macOS\");\n }\n if (engine !== \"podman\" || platform !== \"linux\") return;\n if (uid === 0) throw new TypeError(\"the Linux harness requires rootless Podman; do not run the runner as root\");\n const rootless = await (options.podmanRootless ?? inspectRootlessPodman)();\n if (!rootless) throw new TypeError(\"the active Podman service is not rootless; refusing to run the harness\");\n}\n\n/** Build hardened, networkless engine arguments without starting the container. */\nexport function buildContainerRunArgs(options: Omit<ContainerRunOptions, \"onMessage\" | \"onStderr\" | \"signal\">): string[] {\n if (!options.allowUnpinnedImage) assertPinnedImage(options.image);\n if (/[,\\r\\n]/.test(options.workspaceDir)) throw new TypeError(\"workspace path contains unsupported mount characters\");\n const uid = typeof getuid === \"function\" ? getuid() : 1000;\n const gid = typeof getgid === \"function\" ? getgid() : 1000;\n const safeAttempt = options.task.attemptId.toLowerCase().replace(/[^a-z0-9_.-]/g, \"-\").slice(0, 40);\n const name = `odla-harness-${safeAttempt}-${crypto.randomUUID().slice(0, 8)}`;\n const limits = options.limits ?? {};\n const access = options.workspaceAccess ?? \"read-write\";\n const appleMount = access === \"none\" ? [] : [`--mount=type=bind,source=${options.workspaceDir},target=/workspace${access === \"read-only\" ? \",readonly\" : \"\"}`];\n const ociMount = access === \"none\" ? [] : [`--mount=type=bind,src=${options.workspaceDir},dst=/workspace${access === \"read-only\" ? \",readonly\" : \"\"}`];\n if (options.engine === \"container\") {\n return [\n \"run\", \"--rm\", \"--interactive\", `--name=${name}`,\n \"--network=none\", \"--read-only\", \"--cap-drop=ALL\",\n `--memory=${limits.memory ?? \"1g\"}`, `--cpus=${limits.cpus ?? 1}`,\n `--user=${uid}:${gid}`, \"--tmpfs=/tmp\",\n ...appleMount,\n \"--workdir=/workspace\", `--env=ODLA_HARNESS_PROTOCOL=${HARNESS_PROTOCOL_VERSION}`,\n `--label=ai.odla.harness.attempt=${options.task.attemptId}`,\n options.image,\n ];\n }\n return [\n \"run\", \"--rm\", \"--interactive\", `--name=${name}`, \"--pull=never\",\n \"--network=none\", \"--read-only\", \"--cap-drop=ALL\",\n \"--security-opt=no-new-privileges\", `--pids-limit=${limits.pids ?? 256}`,\n `--memory=${limits.memory ?? \"1g\"}`, `--cpus=${limits.cpus ?? 1}`,\n `--user=${uid}:${gid}`,\n `--tmpfs=/tmp:rw,noexec,nosuid,nodev,size=${limits.tmpfsBytes ?? 64 * 1024 * 1024}`,\n ...ociMount,\n \"--workdir=/workspace\", `--env=ODLA_HARNESS_PROTOCOL=${HARNESS_PROTOCOL_VERSION}`,\n `--label=ai.odla.harness.attempt=${options.task.attemptId}`,\n options.image,\n ];\n}\n\nfunction containerName(args: string[]): string {\n return args.find((arg) => arg.startsWith(\"--name=\"))!.slice(\"--name=\".length);\n}\n\n/** Execute one JSONL agent inside a hardened Apple container, Podman, or Docker\n * boundary. The\n * container has no network and receives no credentials; inference requests are\n * bridged over stdin/stdout to the trusted runner process. */\nexport async function runContainerAttempt(options: ContainerRunOptions): Promise<ContainerRunResult> {\n if (options.signal?.aborted) return { exitCode: 1, status: \"cancelled\", stderr: \"\" };\n await verifyContainerEngineBoundary(options.engine);\n const args = buildContainerRunArgs(options);\n const name = containerName(args);\n const child = spawn(options.engine, args, { stdio: [\"pipe\", \"pipe\", \"pipe\"], shell: false });\n let stderr = \"\";\n let outputBytes = 0;\n let complete: Extract<HarnessAgentOutput, { type: \"attempt.complete\" }> | null = null;\n let stopped = false;\n let exited = false;\n\n child.stderr.setEncoding(\"utf8\");\n child.stderr.on(\"data\", (text: string) => {\n if (stderr.length < 64 * 1024) stderr += text.slice(0, 64 * 1024 - stderr.length);\n });\n\n const stop = (reason: string) => {\n if (stopped || exited) return;\n stopped = true;\n if (!child.stdin.destroyed) {\n const cancel: HarnessAgentInput = { protocolVersion: HARNESS_PROTOCOL_VERSION, type: \"attempt.cancel\", reason };\n child.stdin.write(encodeAgentInput(cancel));\n }\n const removeArgs = options.engine === \"container\" ? [\"delete\", \"--force\", name] : [\"rm\", \"-f\", name];\n const killer = spawn(options.engine, removeArgs, { stdio: \"ignore\", shell: false });\n killer.unref();\n };\n const abort = () => stop(\"runner_cancelled\");\n options.signal?.addEventListener(\"abort\", abort, { once: true });\n\n const timeout = setTimeout(() => stop(\"timeout\"), options.task.policy.timeoutMs);\n const start: HarnessAgentInput = { protocolVersion: HARNESS_PROTOCOL_VERSION, type: \"task.start\", task: options.task };\n if (!stopped && !options.signal?.aborted) child.stdin.write(encodeAgentInput(start));\n\n const consume = (async () => {\n let pending = Buffer.alloc(0);\n const handleLine = async (raw: Buffer) => {\n const bytes = raw.at(-1) === 13 ? raw.subarray(0, -1) : raw;\n if (bytes.byteLength > 1_000_000) throw new Error(\"agent message exceeds 1 MB\");\n const line = bytes.toString(\"utf8\");\n if (!line.trim()) return;\n const message = parseAgentOutput(line);\n if (message.type === \"attempt.complete\") complete = message;\n const response = await options.onMessage(message);\n if (response && !child.stdin.destroyed) child.stdin.write(encodeAgentInput(response));\n };\n try {\n for await (const raw of child.stdout) {\n const chunk = Buffer.isBuffer(raw) ? raw : Buffer.from(raw);\n outputBytes += chunk.byteLength;\n if (outputBytes > options.task.policy.maxOutputBytes) {\n throw new Error(`agent output exceeds ${options.task.policy.maxOutputBytes} bytes`);\n }\n pending = Buffer.concat([pending, chunk]);\n let newline = pending.indexOf(10);\n while (newline >= 0) {\n await handleLine(pending.subarray(0, newline));\n pending = pending.subarray(newline + 1);\n newline = pending.indexOf(10);\n }\n if (pending.byteLength > 1_000_000) throw new Error(\"agent message exceeds 1 MB\");\n }\n if (pending.byteLength) await handleLine(pending);\n } catch (error) {\n stop(\"protocol_error\");\n throw error;\n }\n })();\n\n const exit = new Promise<number>((accept, reject) => {\n child.once(\"error\", reject);\n child.once(\"exit\", (code) => { exited = true; accept(code ?? 1); });\n });\n try {\n const [exitCode] = await Promise.all([exit, consume]);\n if (stderr && options.onStderr) await options.onStderr(stderr);\n if (options.signal?.aborted) return { exitCode, status: \"cancelled\", stderr };\n const terminal = complete as Extract<HarnessAgentOutput, { type: \"attempt.complete\" }> | null;\n if (!terminal) return { exitCode, status: \"failed\", result: { error: \"agent exited without completion\" }, stderr };\n return { exitCode, status: exitCode === 0 ? terminal.status : \"failed\", result: terminal.result, stderr };\n } catch (error) {\n stop(\"runner_error\");\n await exit.catch(() => 1);\n throw error;\n } finally {\n clearTimeout(timeout);\n options.signal?.removeEventListener(\"abort\", abort);\n }\n}\n","import type { ChatInput, OracleResponse } from \"@odla-ai/ai\";\nimport type { CodeToolPresentation } from \"./code-session-event-types\";\nexport type { CodeToolLocationPreview, CodeToolPresentation } from \"./code-session-event-types\";\n\n/** Current JSONL protocol version exchanged between a runner and an agent container. */\nexport const HARNESS_PROTOCOL_VERSION = 1 as const;\n\n/** Default control-plane route used for model inference requested by coding agents. */\nexport const DEFAULT_AI_ROUTE = \"coding\" as const;\n\n/** Lifecycle state reported for a harness task and its active attempt. */\nexport type HarnessTaskStatus =\n | \"queued\"\n | \"running\"\n | \"cancel_requested\"\n | \"completed\"\n | \"failed\"\n | \"cancelled\";\n\n/** Lifecycle state of one execution attempt for a task. */\nexport type HarnessAttemptStatus = HarnessTaskStatus;\n\n/** Trusted or untrusted participant that emitted a harness event. */\nexport type HarnessActor = \"operator\" | \"runner\" | \"agent\" | \"model\" | \"system\";\n\n/** Resource and isolation limits enforced while an untrusted task executes. */\nexport interface HarnessPolicy {\n network: \"none\";\n timeoutMs: number;\n maxOutputBytes: number;\n maxPatchBytes: number;\n}\n\n/** Immutable task instructions and execution policy delivered with a lease. */\nexport interface HarnessTaskSpec {\n taskId: string;\n attemptId: string;\n title: string;\n prompt: string;\n workspace: string;\n aiRoute: string;\n policy: HarnessPolicy;\n parentAttemptId?: string | null;\n checkpointSeq?: number | null;\n}\n\n/** Time-bound assignment authorizing a runner to execute one task attempt. */\nexport interface HarnessLease {\n protocolVersion: typeof HARNESS_PROTOCOL_VERSION;\n leaseId: string;\n generation: number;\n expiresAt: number;\n task: HarnessTaskSpec;\n}\n\n/** Runner-supplied event before the control plane assigns sequence and task metadata. */\nexport interface HarnessEventInput {\n eventId: string;\n kind: string;\n actor: HarnessActor;\n payload: unknown;\n createdAt: number;\n}\n\n/** Persisted, ordered event associated with a specific task attempt. */\nexport interface HarnessEvent extends HarnessEventInput {\n seq: number;\n taskId: string;\n attemptId: string;\n}\n\n/** List-view metadata for a task and its current attempt. */\nexport interface HarnessTaskSummary {\n taskId: string;\n attemptId: string;\n appId: string;\n env: string;\n title: string;\n prompt: string;\n workspace: string;\n aiRoute: string;\n status: HarnessTaskStatus;\n parentAttemptId: string | null;\n checkpointSeq: number | null;\n runnerId: string | null;\n generation: number;\n createdAt: number;\n updatedAt: number;\n}\n\n/** List-view metadata for one attempt, including retry ancestry and runner ownership. */\nexport interface HarnessAttemptSummary {\n attemptId: string;\n taskId: string;\n parentAttemptId: string | null;\n checkpointSeq: number | null;\n status: HarnessAttemptStatus;\n runnerId: string | null;\n generation: number;\n createdAt: number;\n updatedAt: number;\n}\n\n/** Complete task view including attempts, events, result, and generated patch. */\nexport interface HarnessTaskDetail extends HarnessTaskSummary {\n attempts: HarnessAttemptSummary[];\n events: HarnessEvent[];\n patch: string | null;\n result: unknown;\n}\n\n/** Public control-plane view of a registered harness runner. */\nexport interface HarnessRunnerView {\n runnerId: string;\n appId: string;\n env: string;\n name: string;\n createdAt: number;\n lastSeenAt: number | null;\n revokedAt: number | null;\n}\n\n/** Credential-free normalized model request sent from an agent through the runner. */\nexport interface HarnessInferenceRequest {\n requestId: string;\n /** Exact initial, follow-up, or resume command whose budget this call consumes. */\n interactionId?: string;\n call: ChatInput;\n}\n\n/** Normalized model response plus auditable provider, policy, and token metadata. */\nexport interface HarnessInferenceResponse {\n requestId: string;\n response: OracleResponse;\n receipt: {\n provider: string;\n model: string;\n policyVersion: number;\n inputTokens: number;\n outputTokens: number;\n /**\n * USD charged for this call, priced against the model the control plane\n * actually resolved.\n *\n * ABSENT when the live catalog has no price for that model — never zero.\n * An unpriced call is unknown spend, and reporting it as free is what let\n * a goal's `maxUsd` look enforced while nothing enforced it. The runtime\n * cannot compute this itself: it asks for `brokered` and only the control\n * plane knows which model answered.\n */\n costUsd?: number;\n };\n}\n\n/** Bounded, content-minimized session activity emitted by a Code runtime.\n * Message bodies are projected separately into the app's owner-private\n * odla-db chat. `interactionId` is optional so stored v1 events remain valid. */\nexport type CodeSessionEventData = (\n | { type: \"message\"; actor: \"agent\" | \"system\"; body: string }\n | { type: \"diagnostic\"; level: \"error\"; message: string }\n | { type: \"thinking\"; available: true; durationMs: number }\n | {\n type: \"tool\";\n phase: \"started\";\n tool: HarnessToolName;\n operationId?: string;\n presentation?: CodeToolPresentation;\n }\n | {\n type: \"tool\";\n phase: \"completed\";\n tool: HarnessToolName;\n ok: boolean;\n durationMs: number;\n operationId?: string;\n /** Why the call failed, bounded. Absent when `ok`. Without this a watcher\n * saw that a tool failed and never why, which is what made an 84%\n * apply_patch failure rate impossible to diagnose (PM bug 515655ec). */\n failureReason?: string;\n presentation?: CodeToolPresentation;\n }\n | {\n type: \"collaboration\";\n phase: \"started\";\n skill: string;\n tool: string;\n operationId: string;\n }\n | {\n type: \"collaboration\";\n phase: \"completed\";\n skill: string;\n tool: string;\n ok: boolean;\n durationMs: number;\n operationId: string;\n }\n | {\n type: \"usage\"; provider: string; model: string;\n inputTokens: number; outputTokens: number; durationMs: number;\n interactionTokens?: number; interactionMaxTokens?: number;\n /** USD for this call; absent when the model is unpriced, never zero. */\n costUsd?: number;\n /** Cumulative USD for this owner interaction, when every call in it was\n * priced. Absent the moment one was not, so a partial total can never be\n * mistaken for the whole. */\n interactionCostUsd?: number;\n }\n | {\n type: \"status\"; status: \"running\" | \"idle\" | \"failed\" | \"checkpointed\";\n durationMs?: number;\n }\n) & { interactionId?: string };\n\n/** Registry-assigned cursor and timestamp for an owner-visible Code event. */\nexport type CodeSessionEvent = CodeSessionEventData & {\n eventId: string; sequence: number; createdAt: number;\n};\n\n/** Closed set of effects an agent container may request from its trusted broker. */\nexport type HarnessToolName =\n | \"sandbox.read\"\n | \"sandbox.list\"\n | \"sandbox.search\"\n | \"sandbox.overview\"\n | \"sandbox.where_is\"\n | \"sandbox.who_imports\"\n | \"sandbox.who_touches\"\n | \"sandbox.apply_patch\"\n | \"sandbox.run_recipe\";\n/** Correlated, structured tool request emitted by an untrusted agent container. */\nexport interface HarnessToolRequest {\n requestId: string;\n tool: HarnessToolName;\n input: Record<string, unknown>;\n}\n/** Bounded tool result returned to an agent after trusted policy evaluation. */\nexport interface HarnessToolResponse {\n requestId: string;\n ok: boolean;\n content: string;\n details?: Record<string, unknown>;\n}\n\n/** Validated JSONL message emitted by an untrusted agent container. */\nexport type HarnessAgentOutput =\n | {\n protocolVersion: typeof HARNESS_PROTOCOL_VERSION;\n type: \"event\";\n kind: string;\n payload?: unknown;\n }\n | {\n protocolVersion: typeof HARNESS_PROTOCOL_VERSION;\n type: \"inference.request\";\n requestId: string;\n call: ChatInput;\n }\n | ({ protocolVersion: typeof HARNESS_PROTOCOL_VERSION; type: \"tool.request\" } & HarnessToolRequest)\n | {\n protocolVersion: typeof HARNESS_PROTOCOL_VERSION;\n type: \"attempt.complete\";\n status: \"completed\" | \"failed\" | \"cancelled\";\n result?: unknown;\n };\n\n/** JSONL command or inference result written by the trusted runner to an agent. */\nexport type HarnessAgentInput =\n | {\n protocolVersion: typeof HARNESS_PROTOCOL_VERSION;\n type: \"task.start\";\n task: HarnessTaskSpec;\n }\n | {\n protocolVersion: typeof HARNESS_PROTOCOL_VERSION;\n type: \"inference.response\";\n requestId: string;\n response: OracleResponse;\n }\n | ({ protocolVersion: typeof HARNESS_PROTOCOL_VERSION; type: \"tool.response\" } & HarnessToolResponse)\n | {\n protocolVersion: typeof HARNESS_PROTOCOL_VERSION;\n type: \"attempt.cancel\";\n reason: string;\n };\n\n/** Terminal attempt report submitted by a runner to the control plane. */\nexport interface HarnessCompletion {\n status: \"completed\" | \"failed\" | \"cancelled\";\n result?: unknown;\n patch?: string;\n error?: string;\n}\n\n/** Operations a credentialed runner may perform against the harness control plane. */\nexport interface HarnessControlPlane {\n lease(workspaces: string[]): Promise<HarnessLease | null>;\n heartbeat(attemptId: string, leaseId: string): Promise<{ cancelRequested: boolean; expiresAt: number }>;\n appendEvents(attemptId: string, leaseId: string, events: HarnessEventInput[]): Promise<void>;\n infer(attemptId: string, leaseId: string, request: HarnessInferenceRequest): Promise<HarnessInferenceResponse>;\n complete(attemptId: string, leaseId: string, completion: HarnessCompletion): Promise<void>;\n}\n\n/** Trusted inference bridge used to keep model credentials outside agent containers. */\nexport interface HarnessAiConnection {\n infer(request: HarnessInferenceRequest): Promise<HarnessInferenceResponse>;\n}\n\n/** Trusted tool boundary. Implementations must evaluate CaMeL policy before effects. */\nexport interface HarnessToolBroker {\n execute(\n context: { lease: HarnessLease; workspaceDir: string; signal?: AbortSignal },\n request: HarnessToolRequest,\n ): Promise<HarnessToolResponse>;\n}\n","import type { ChatInput } from \"@odla-ai/ai\";\nimport {\n HARNESS_PROTOCOL_VERSION,\n type HarnessAgentInput,\n type HarnessAgentOutput,\n type HarnessEventInput,\n} from \"./types\";\n\nconst CONTROL = /[\\u0000-\\u0008\\u000b\\u000c\\u000e-\\u001f\\u007f]/;\n\n/** Error raised when an agent emits malformed, oversized, or unsupported protocol data. */\nexport class HarnessProtocolError extends Error {\n override readonly name = \"HarnessProtocolError\";\n}\n\nfunction record(value: unknown): Record<string, unknown> | null {\n return value !== null && typeof value === \"object\" && !Array.isArray(value)\n ? value as Record<string, unknown>\n : null;\n}\n\nfunction boundedText(value: unknown, label: string, max: number): string {\n if (typeof value !== \"string\" || !value || value.length > max || CONTROL.test(value)) {\n throw new HarnessProtocolError(`${label} must be a non-empty string of at most ${max} characters`);\n }\n return value;\n}\n\n/** Parse and validate one newline-delimited message emitted by an agent container. */\nexport function parseAgentOutput(line: string): HarnessAgentOutput {\n if (Buffer.byteLength(line, \"utf8\") > 1_000_000) throw new HarnessProtocolError(\"agent message exceeds 1 MB\");\n let value: unknown;\n try { value = JSON.parse(line); } catch { throw new HarnessProtocolError(\"agent emitted invalid JSON\"); }\n const message = record(value);\n if (!message || message.protocolVersion !== HARNESS_PROTOCOL_VERSION) {\n throw new HarnessProtocolError(`agent protocolVersion must be ${HARNESS_PROTOCOL_VERSION}`);\n }\n if (message.type === \"event\") {\n return {\n protocolVersion: HARNESS_PROTOCOL_VERSION,\n type: \"event\",\n kind: boundedText(message.kind, \"event.kind\", 120),\n ...(message.payload === undefined ? {} : { payload: message.payload }),\n };\n }\n if (message.type === \"inference.request\") {\n const call = record(message.call);\n if (!call || !Array.isArray(call.messages) || !Number.isSafeInteger(call.maxTokens)) {\n throw new HarnessProtocolError(\"inference.request.call requires messages and maxTokens\");\n }\n return {\n protocolVersion: HARNESS_PROTOCOL_VERSION,\n type: \"inference.request\",\n requestId: boundedText(message.requestId, \"requestId\", 180),\n call: call as unknown as ChatInput,\n };\n }\n if (message.type === \"tool.request\") {\n const input = record(message.input);\n const tool = String(message.tool);\n if (!input || ![\"sandbox.read\", \"sandbox.apply_patch\", \"sandbox.run_recipe\"].includes(tool)) {\n throw new HarnessProtocolError(\"tool.request requires a registered tool and object input\");\n }\n return {\n protocolVersion: HARNESS_PROTOCOL_VERSION,\n type: \"tool.request\",\n requestId: boundedText(message.requestId, \"requestId\", 180),\n tool: tool as \"sandbox.read\" | \"sandbox.apply_patch\" | \"sandbox.run_recipe\",\n input,\n };\n }\n if (message.type === \"attempt.complete\") {\n if (!new Set([\"completed\", \"failed\", \"cancelled\"]).has(String(message.status))) {\n throw new HarnessProtocolError(\"attempt.complete.status is invalid\");\n }\n return {\n protocolVersion: HARNESS_PROTOCOL_VERSION,\n type: \"attempt.complete\",\n status: message.status as \"completed\" | \"failed\" | \"cancelled\",\n ...(message.result === undefined ? {} : { result: message.result }),\n };\n }\n throw new HarnessProtocolError(\"agent message type is unsupported\");\n}\n\n/** Serialize one trusted runner message as a newline-terminated JSONL record. */\nexport function encodeAgentInput(message: HarnessAgentInput): string {\n return `${JSON.stringify(message)}\\n`;\n}\n\n/** Create a timestamped, uniquely identified event for control-plane submission. */\nexport function makeHarnessEvent(\n kind: string,\n actor: HarnessEventInput[\"actor\"],\n payload: unknown,\n now = Date.now(),\n id = crypto.randomUUID(),\n): HarnessEventInput {\n boundedText(kind, \"event.kind\", 120);\n return { eventId: id, kind, actor, payload, createdAt: now };\n}\n","import { setTimeout as delay } from \"node:timers/promises\";\nimport { runContainerAttempt, type ContainerEngine, type ContainerLimits } from \"./container\";\nimport { makeHarnessEvent } from \"./protocol\";\nimport { stageWorkspace, type StagedWorkspace } from \"./workspace\";\nimport {\n HARNESS_PROTOCOL_VERSION,\n type HarnessAgentInput,\n type HarnessAgentOutput,\n type HarnessControlPlane,\n type HarnessLease,\n type HarnessToolBroker,\n} from \"./types\";\n\n/** Control-plane, workspace, isolation, polling, and lifecycle settings for a runner. */\nexport interface HarnessRunnerOptions {\n control: HarnessControlPlane;\n workspaces: Readonly<Record<string, string>>;\n engine: ContainerEngine;\n image: string;\n limits?: ContainerLimits;\n heartbeatMs?: number;\n pollMs?: number;\n once?: boolean;\n preserveWorkspace?: boolean;\n allowUnpinnedImage?: boolean;\n workspaceAccess?: \"read-write\" | \"read-only\" | \"none\";\n signal?: AbortSignal;\n log?: (message: string) => void;\n toolBroker?: HarnessToolBroker;\n}\n\nasync function append(\n control: HarnessControlPlane,\n lease: HarnessLease,\n kind: string,\n actor: \"runner\" | \"agent\" | \"model\" | \"system\",\n payload: unknown,\n): Promise<void> {\n await control.appendEvents(lease.task.attemptId, lease.leaseId, [makeHarnessEvent(kind, actor, payload)]);\n}\n\n/** Execute one leased task. The registered workspace is copied before the\n * container starts; neither the checkout nor the runner credential is mounted. */\nexport async function runLeasedAttempt(lease: HarnessLease, options: HarnessRunnerOptions): Promise<void> {\n const source = options.workspaces[lease.task.workspace];\n if (!source) {\n await options.control.complete(lease.task.attemptId, lease.leaseId, {\n status: \"failed\",\n error: `runner does not expose workspace \"${lease.task.workspace}\"`,\n });\n return;\n }\n\n let staged: StagedWorkspace | null = null;\n const controller = new AbortController();\n const cancelFromParent = () => controller.abort(options.signal?.reason);\n options.signal?.addEventListener(\"abort\", cancelFromParent, { once: true });\n if (options.signal?.aborted) controller.abort(options.signal.reason);\n let heartbeat: ReturnType<typeof setInterval> | undefined;\n let heartbeatInFlight = false;\n const pulse = async () => {\n if (heartbeatInFlight || controller.signal.aborted) return;\n heartbeatInFlight = true;\n try {\n const value = await options.control.heartbeat(lease.task.attemptId, lease.leaseId);\n if (value.cancelRequested) controller.abort(\"cancel_requested\");\n } catch {\n controller.abort(\"heartbeat_failed\");\n } finally {\n heartbeatInFlight = false;\n }\n };\n try {\n await pulse();\n heartbeat = setInterval(() => { void pulse(); }, options.heartbeatMs ?? 15_000);\n if (controller.signal.aborted) throw new Error(\"lease was cancelled before workspace staging\");\n staged = await stageWorkspace(source);\n if (controller.signal.aborted) throw new Error(\"lease was cancelled during workspace staging\");\n const stagedWorkspace = staged;\n await append(options.control, lease, \"runner.workspace_staged\", \"runner\", {\n workspace: lease.task.workspace,\n files: stagedWorkspace.fileCount,\n bytes: stagedWorkspace.byteCount,\n });\n\n const result = await runContainerAttempt({\n engine: options.engine,\n image: options.image,\n workspaceDir: stagedWorkspace.workspaceDir,\n task: lease.task,\n limits: options.limits,\n allowUnpinnedImage: options.allowUnpinnedImage,\n workspaceAccess: options.workspaceAccess ?? (options.toolBroker ? \"none\" : \"read-write\"),\n signal: controller.signal,\n onStderr: async (text) => {\n await append(options.control, lease, \"agent.stderr\", \"agent\", { text: text.slice(0, 64 * 1024) });\n },\n onMessage: async (message: HarnessAgentOutput): Promise<HarnessAgentInput | void> => {\n if (message.type === \"event\") {\n await append(options.control, lease, message.kind, \"agent\", message.payload ?? null);\n return;\n }\n if (message.type === \"attempt.complete\") {\n await append(options.control, lease, \"agent.completed\", \"agent\", {\n status: message.status,\n result: message.result ?? null,\n });\n return;\n }\n if (message.type === \"tool.request\") {\n await append(options.control, lease, \"tool.requested\", \"agent\", {\n requestId: message.requestId, tool: message.tool,\n });\n const response = options.toolBroker\n ? await options.toolBroker.execute({\n lease, workspaceDir: stagedWorkspace.workspaceDir, signal: controller.signal,\n }, message)\n : { requestId: message.requestId, ok: false, content: \"tool denied: no trusted broker configured\" };\n await append(options.control, lease, \"tool.responded\", \"system\", {\n requestId: message.requestId, tool: message.tool, ok: response.ok,\n contentBytes: Buffer.byteLength(response.content),\n });\n return { protocolVersion: HARNESS_PROTOCOL_VERSION, type: \"tool.response\", ...response };\n }\n await append(options.control, lease, \"model.requested\", \"agent\", {\n requestId: message.requestId,\n messages: message.call.messages.length,\n maxTokens: message.call.maxTokens,\n });\n const response = await options.control.infer(lease.task.attemptId, lease.leaseId, {\n requestId: message.requestId,\n call: message.call,\n });\n await append(options.control, lease, \"model.responded\", \"model\", {\n requestId: message.requestId,\n response: response.response,\n receipt: response.receipt,\n });\n return {\n protocolVersion: HARNESS_PROTOCOL_VERSION,\n type: \"inference.response\",\n requestId: message.requestId,\n response: response.response,\n };\n },\n });\n\n const patch = await stagedWorkspace.patch(lease.task.policy.maxPatchBytes);\n await options.control.complete(lease.task.attemptId, lease.leaseId, {\n status: result.status,\n result: result.result,\n patch,\n ...(result.status === \"failed\" ? { error: result.stderr.slice(0, 4_000) || \"container attempt failed\" } : {}),\n });\n } catch (reason) {\n const message = reason instanceof Error ? reason.message : \"runner failed\";\n try {\n await append(options.control, lease, \"runner.failed\", \"runner\", { message });\n await options.control.complete(lease.task.attemptId, lease.leaseId, {\n status: controller.signal.aborted ? \"cancelled\" : \"failed\",\n error: message,\n });\n } catch {\n // A lost or revoked lease can also make the terminal report unavailable.\n }\n } finally {\n if (heartbeat) clearInterval(heartbeat);\n options.signal?.removeEventListener(\"abort\", cancelFromParent);\n if (staged && !options.preserveWorkspace) await staged.cleanup();\n }\n}\n\n/** One runner executes one attempt at a time. Concurrency comes from multiple\n * independently credentialed runner processes. */\nexport async function runHarnessRunner(options: HarnessRunnerOptions): Promise<void> {\n const workspaceNames = Object.keys(options.workspaces).sort();\n if (!workspaceNames.length) throw new TypeError(\"at least one workspace mapping is required\");\n do {\n if (options.signal?.aborted) return;\n const lease = await options.control.lease(workspaceNames);\n if (lease) {\n options.log?.(`leased ${lease.task.taskId}/${lease.task.attemptId}`);\n await runLeasedAttempt(lease, options);\n if (options.once) return;\n continue;\n }\n if (options.once) return;\n await delay(options.pollMs ?? 2_000, undefined, { signal: options.signal }).catch(() => {});\n } while (!options.signal?.aborted);\n}\n","import { chmod, copyFile, lstat, mkdir, mkdtemp, readdir, realpath, rm, stat } from \"node:fs/promises\";\nimport { tmpdir } from \"node:os\";\nimport { basename, join, relative, resolve, sep } from \"node:path\";\nimport { spawn } from \"node:child_process\";\nimport { allowedWorkspacePath, SECRET_WORKSPACE_FILE, SKIP_WORKSPACE_DIRS } from \"./workspace-policy\";\nexport { materializeGitTree, type MaterializedGitTree } from \"./workspace-git-tree\";\n\n/** File, byte, and temporary-directory limits applied while staging a workspace. */\nexport interface StageWorkspaceOptions {\n maxFiles?: number;\n maxBytes?: number;\n tempRoot?: string;\n /** Stage tracked files plus non-ignored untracked files from a Git checkout. */\n gitTrackedAndUnignored?: boolean;\n}\n\n/** Disposable baseline and mutable workspace copy used to generate a bounded patch. */\nexport interface StagedWorkspace {\n root: string;\n baselineDir: string;\n workspaceDir: string;\n fileCount: number;\n byteCount: number;\n patch(maxBytes: number): Promise<string>;\n cleanup(): Promise<void>;\n}\n\ninterface SourceFile {\n source: string;\n relativePath: string;\n mode: number;\n bytes: number;\n}\n\nasync function sourceFiles(sourceDir: string, maxFiles: number, maxBytes: number): Promise<SourceFile[]> {\n const files: SourceFile[] = [];\n let bytes = 0;\n const walk = async (dir: string): Promise<void> => {\n for (const entry of await readdir(dir, { withFileTypes: true })) {\n if (entry.isDirectory() && SKIP_WORKSPACE_DIRS.has(entry.name)) continue;\n if (!entry.isDirectory() && SECRET_WORKSPACE_FILE.test(entry.name)) continue;\n const path = join(dir, entry.name);\n if (entry.isSymbolicLink()) continue;\n if (entry.isDirectory()) {\n await walk(path);\n continue;\n }\n if (!entry.isFile()) continue;\n const metadata = await stat(path);\n bytes += metadata.size;\n if (files.length + 1 > maxFiles) throw new Error(`workspace exceeds ${maxFiles} files`);\n if (bytes > maxBytes) throw new Error(`workspace exceeds ${maxBytes} bytes`);\n files.push({\n source: path,\n relativePath: relative(sourceDir, path),\n mode: metadata.mode & 0o777,\n bytes: metadata.size,\n });\n }\n };\n await walk(sourceDir);\n return files.sort((left, right) => left.relativePath.localeCompare(right.relativePath));\n}\n\nasync function gitSourceFiles(sourceDir: string, maxFiles: number, maxBytes: number): Promise<SourceFile[]> {\n const child = spawn(\"git\", [\"ls-files\", \"-z\", \"--cached\", \"--others\", \"--exclude-standard\"], {\n cwd: sourceDir, stdio: [\"ignore\", \"pipe\", \"pipe\"], shell: false,\n });\n const stdout: Buffer[] = [];\n const stderr: Buffer[] = [];\n let outputBytes = 0;\n child.stdout.on(\"data\", (chunk: Buffer) => {\n outputBytes += chunk.byteLength;\n if (outputBytes > 8 * 1024 * 1024) child.kill(\"SIGKILL\");\n else stdout.push(chunk);\n });\n child.stderr.on(\"data\", (chunk: Buffer) => {\n if (stderr.reduce((sum, value) => sum + value.byteLength, 0) < 16_384) stderr.push(chunk);\n });\n const code = await new Promise<number | null>((accept, reject) => {\n child.once(\"error\", reject);\n child.once(\"exit\", accept);\n });\n if (outputBytes > 8 * 1024 * 1024) throw new Error(\"git file inventory exceeds 8 MiB\");\n if (code !== 0) throw new Error(`git file inventory failed: ${Buffer.concat(stderr).toString(\"utf8\").slice(0, 1_000)}`);\n const paths = Buffer.concat(stdout).toString(\"utf8\").split(\"\\0\").filter(Boolean).sort();\n if (paths.length > maxFiles) throw new Error(`workspace exceeds ${maxFiles} files`);\n const root = resolve(sourceDir);\n const files: SourceFile[] = [];\n let bytes = 0;\n for (const relativePath of paths) {\n if (!allowedWorkspacePath(relativePath)) continue;\n const source = resolve(root, relativePath);\n if (!source.startsWith(`${root}${sep}`)) throw new TypeError(\"git file path escapes workspace\");\n let metadata;\n try { metadata = await lstat(source); }\n catch (error) {\n if ((error as NodeJS.ErrnoException).code === \"ENOENT\") continue;\n throw error;\n }\n if (metadata.isSymbolicLink() || !metadata.isFile()) continue;\n bytes += metadata.size;\n if (bytes > maxBytes) throw new Error(`workspace exceeds ${maxBytes} bytes`);\n files.push({ source, relativePath, mode: metadata.mode & 0o777, bytes: metadata.size });\n }\n return files;\n}\n\nasync function copyTree(files: SourceFile[], destination: string): Promise<void> {\n for (const file of files) {\n const target = join(destination, file.relativePath);\n await mkdir(resolve(target, \"..\"), { recursive: true });\n await copyFile(file.source, target);\n await chmod(target, file.mode);\n }\n}\n\nasync function captureGitDiff(root: string, maxBytes: number): Promise<string> {\n const child = spawn(\"git\", [\n \"diff\", \"--no-index\", \"--binary\", \"--no-ext-diff\",\n \"--src-prefix=a/\", \"--dst-prefix=b/\", \"--\", \"baseline\", \"workspace\",\n ], { cwd: root, stdio: [\"ignore\", \"pipe\", \"pipe\"], shell: false });\n const stdout: Buffer[] = [];\n const stderr: Buffer[] = [];\n let bytes = 0;\n child.stdout.on(\"data\", (chunk: Buffer) => {\n bytes += chunk.byteLength;\n if (bytes > maxBytes) child.kill(\"SIGKILL\");\n else stdout.push(chunk);\n });\n child.stderr.on(\"data\", (chunk: Buffer) => {\n if (stderr.reduce((sum, value) => sum + value.byteLength, 0) < 16_384) stderr.push(chunk);\n });\n const code = await new Promise<number | null>((accept, reject) => {\n child.once(\"error\", reject);\n child.once(\"exit\", accept);\n });\n if (bytes > maxBytes) throw new Error(`patch exceeds ${maxBytes} bytes`);\n if (code !== 0 && code !== 1) {\n throw new Error(`git diff failed: ${Buffer.concat(stderr).toString(\"utf8\").slice(0, 1_000)}`);\n }\n return Buffer.concat(stdout).toString(\"utf8\")\n .replaceAll(\"a/baseline/\", \"a/\")\n .replaceAll(\"a/workspace/\", \"a/\")\n .replaceAll(\"b/baseline/\", \"b/\")\n .replaceAll(\"b/workspace/\", \"b/\")\n .replaceAll(\"--- a/baseline\", \"--- a\")\n .replaceAll(\"+++ b/workspace\", \"+++ b\");\n}\n\n/** Copy a bounded, secret-filtered workspace twice: one immutable baseline and\n * one disposable directory mounted into the container. The developer checkout\n * itself is never mounted. */\nexport async function stageWorkspace(source: string, options: StageWorkspaceOptions = {}): Promise<StagedWorkspace> {\n const sourceDir = await realpath(resolve(source));\n const sourceStat = await stat(sourceDir);\n if (!sourceStat.isDirectory()) throw new TypeError(\"workspace source must be a directory\");\n const root = await mkdtemp(join(options.tempRoot ?? tmpdir(), \"odla-harness-\"));\n const baselineDir = join(root, \"baseline\");\n const workspaceDir = join(root, \"workspace\");\n await Promise.all([mkdir(baselineDir), mkdir(workspaceDir)]);\n try {\n const maxFiles = options.maxFiles ?? 20_000;\n const maxBytes = options.maxBytes ?? 512 * 1024 * 1024;\n const files = options.gitTrackedAndUnignored\n ? await gitSourceFiles(sourceDir, maxFiles, maxBytes)\n : await sourceFiles(sourceDir, maxFiles, maxBytes);\n await Promise.all([copyTree(files, baselineDir), copyTree(files, workspaceDir)]);\n return {\n root,\n baselineDir,\n workspaceDir,\n fileCount: files.length,\n byteCount: files.reduce((sum, file) => sum + file.bytes, 0),\n patch: (maxBytes) => captureGitDiff(root, maxBytes),\n cleanup: () => rm(root, { recursive: true, force: true }),\n };\n } catch (error) {\n await rm(root, { recursive: true, force: true });\n throw error;\n }\n}\n\n/** Create a disposable workspace whose diff base and initial editable tree\n * intentionally come from different already-filtered sources. */\nexport async function stageWorkspacePair(\n baselineSource: string, workspaceSource: string, options: StageWorkspaceOptions = {},\n): Promise<StagedWorkspace> {\n const baselineDirSource = await realpath(resolve(baselineSource));\n const workspaceDirSource = await realpath(resolve(workspaceSource));\n const maxFiles = options.maxFiles ?? 20_000;\n const maxBytes = options.maxBytes ?? 512 * 1024 * 1024;\n const [baselineFiles, workspaceFiles] = await Promise.all([\n sourceFiles(baselineDirSource, maxFiles, maxBytes),\n sourceFiles(workspaceDirSource, maxFiles, maxBytes),\n ]);\n const root = await mkdtemp(join(options.tempRoot ?? tmpdir(), \"odla-harness-\"));\n const baselineDir = join(root, \"baseline\");\n const workspaceDir = join(root, \"workspace\");\n await Promise.all([mkdir(baselineDir), mkdir(workspaceDir)]);\n try {\n await Promise.all([copyTree(baselineFiles, baselineDir), copyTree(workspaceFiles, workspaceDir)]);\n return {\n root, baselineDir, workspaceDir,\n fileCount: workspaceFiles.length,\n byteCount: workspaceFiles.reduce((sum, file) => sum + file.bytes, 0),\n patch: (maxPatchBytes) => captureGitDiff(root, maxPatchBytes),\n cleanup: () => rm(root, { recursive: true, force: true }),\n };\n } catch (error) {\n await rm(root, { recursive: true, force: true });\n throw error;\n }\n}\n\n/** Convert a path-like value into a bounded lowercase label safe for runner metadata. */\nexport function safeWorkspaceLabel(value: string): string {\n const label = basename(value).toLowerCase().replace(/[^a-z0-9_-]+/g, \"-\").replace(/^-+|-+$/g, \"\");\n if (!label) throw new TypeError(\"workspace label is empty\");\n return label.slice(0, 80);\n}\n","import { isAbsolute } from \"node:path\";\n\nexport const SKIP_WORKSPACE_DIRS = new Set([\n \".git\", \".odla\", \".wrangler\", \"node_modules\", \"dist\", \"coverage\",\n]);\nexport const SECRET_WORKSPACE_FILE = /^(?:\\.env(?:\\..+)?|\\.dev\\.vars|\\.dev-token(?:\\..+)?|credentials(?:\\..+)?\\.json|dev-token(?:\\..+)?(?:\\.json)?)$/i;\n\n/** Reject paths that are unsafe or reserved at either the local or Git-tree boundary. */\nexport function allowedWorkspacePath(relativePath: string): boolean {\n const parts = relativePath.split(\"/\");\n return !isAbsolute(relativePath) && !relativePath.includes(\"\\\\\") && !relativePath.includes(\"\\0\")\n && !parts.some((part) => !part || part === \".\" || part === \"..\" || SKIP_WORKSPACE_DIRS.has(part))\n && !SECRET_WORKSPACE_FILE.test(parts.at(-1) ?? \"\");\n}\n"],"mappings":";;;;AACA,IAAAA,oBAAwB;;;ACSjB,IAAM,sBAAN,cAAkC,MAAM;AAAA,EAE7C,YAAY,SAA0B,QAAyB,OAAO,iBAAiB;AAAE,UAAM,OAAO;AAAhE;AAAyB;AAAA,EAA0C;AAAA,EAAnE;AAAA,EAAyB;AAAA,EAD7C,OAAO;AAE3B;AAYO,SAAS,2BAA2B,SAA2D;AACpG,QAAM,WAAW,QAAQ,SAAS,QAAQ,QAAQ,EAAE;AACpD,MAAI;AACJ,MAAI;AAAE,kBAAc,IAAI,IAAI,QAAQ;AAAA,EAAG,QAAQ;AAAE,UAAM,IAAI,UAAU,+BAA+B;AAAA,EAAG;AACvG,QAAM,WAAW,YAAY,aAAa,eAAe,YAAY,aAAa,eAAe,YAAY,aAAa;AAC1H,MAAI,YAAY,YAAY,YAAY,YAAa,YAAY,aAAa,YAAY,EAAE,YAAY,YAAY,aAAa,UAAW;AAC1I,UAAM,IAAI,UAAU,qEAAqE;AAAA,EAC3F;AACA,MAAI,CAAC,0BAA0B,KAAK,QAAQ,KAAK,EAAG,OAAM,IAAI,UAAU,mCAAmC;AAC3G,QAAM,mBAAmB,QAAQ,oBAAoB;AACrD,MAAI,CAAC,OAAO,cAAc,gBAAgB,KAAK,mBAAmB,OAAS,mBAAmB,MAAS;AACrG,UAAM,IAAI,UAAU,yDAAyD;AAAA,EAC/E;AACA,QAAM,UAAU,QAAQ,SAAS;AACjC,QAAM,OAAO,OAAU,MAAc,MAAe,aAAa,UAA6B;AAC5F,UAAM,UAAU,YAAY,QAAQ,gBAAgB;AACpD,UAAM,SAAS,QAAQ,SAAS,YAAY,IAAI,CAAC,QAAQ,QAAQ,OAAO,CAAC,IAAI;AAC7E,UAAM,WAAW,MAAM,QAAQ,GAAG,QAAQ,GAAG,IAAI,IAAI;AAAA,MACnD,QAAQ;AAAA,MACR,SAAS,EAAE,eAAe,UAAU,QAAQ,KAAK,IAAI,gBAAgB,mBAAmB;AAAA,MACxF,MAAM,KAAK,UAAU,IAAI;AAAA,MACzB,UAAU;AAAA,MACV;AAAA,IACF,CAAC;AACD,QAAI,cAAc,SAAS,WAAW,IAAK,QAAO;AAClD,UAAM,QAAQ,MAAM,SAAS,KAAK,EAAE,MAAM,MAAM,IAAI;AACpD,QAAI,CAAC,SAAS,GAAI,OAAM,IAAI;AAAA,MAC1B,OAAO,OAAO,WAAW,mCAAmC,SAAS,MAAM;AAAA,MAC3E,SAAS;AAAA,MACT,OAAO,OAAO;AAAA,IAChB;AACA,WAAO;AAAA,EACT;AACA,SAAO;AAAA,IACL,OAAO,OAAO,eAAe;AAC3B,YAAM,OAAO,MAAM,KAA8B,2BAA2B,EAAE,WAAW,GAAG,IAAI;AAChG,aAAO,MAAM,SAAS;AAAA,IACxB;AAAA,IACA,WAAW,OAAO,WAAW,YAAY;AACvC,YAAM,OAAO,MAAM;AAAA,QACjB,8BAA8B,mBAAmB,SAAS,CAAC;AAAA,QAAc,EAAE,QAAQ;AAAA,MACrF;AACA,aAAO;AAAA,IACT;AAAA,IACA,cAAc,OAAO,WAAW,SAAS,WAAgC;AACvE,YAAM,KAAK,8BAA8B,mBAAmB,SAAS,CAAC,WAAW,EAAE,SAAS,OAAO,CAAC;AAAA,IACtG;AAAA,IACA,OAAO,OAAO,WAAW,SAAS,cAAuC;AACvE,YAAM,OAAO,MAAM;AAAA,QACjB,8BAA8B,mBAAmB,SAAS,CAAC;AAAA,QAAc,EAAE,SAAS,GAAG,UAAU;AAAA,MACnG;AACA,aAAO;AAAA,IACT;AAAA,IACA,UAAU,OAAO,WAAW,SAAS,eAAkC;AACrE,YAAM,KAAK,8BAA8B,mBAAmB,SAAS,CAAC,aAAa,EAAE,SAAS,GAAG,WAAW,CAAC;AAAA,IAC/G;AAAA,EACF;AACF;;;AClFA,gCAAgC;AAChC,qBAA0B;AAC1B,sBAAuB;AACvB,uBAAgC;AAChC,0BAA+B;;;ACCxB,IAAM,2BAA2B;;;ACGxC,IAAM,UAAU;AAGT,IAAM,uBAAN,cAAmC,MAAM;AAAA,EAC5B,OAAO;AAC3B;AAEA,SAAS,OAAO,OAAgD;AAC9D,SAAO,UAAU,QAAQ,OAAO,UAAU,YAAY,CAAC,MAAM,QAAQ,KAAK,IACtE,QACA;AACN;AAEA,SAAS,YAAY,OAAgB,OAAe,KAAqB;AACvE,MAAI,OAAO,UAAU,YAAY,CAAC,SAAS,MAAM,SAAS,OAAO,QAAQ,KAAK,KAAK,GAAG;AACpF,UAAM,IAAI,qBAAqB,GAAG,KAAK,0CAA0C,GAAG,aAAa;AAAA,EACnG;AACA,SAAO;AACT;AAGO,SAAS,iBAAiB,MAAkC;AACjE,MAAI,OAAO,WAAW,MAAM,MAAM,IAAI,IAAW,OAAM,IAAI,qBAAqB,4BAA4B;AAC5G,MAAI;AACJ,MAAI;AAAE,YAAQ,KAAK,MAAM,IAAI;AAAA,EAAG,QAAQ;AAAE,UAAM,IAAI,qBAAqB,4BAA4B;AAAA,EAAG;AACxG,QAAM,UAAU,OAAO,KAAK;AAC5B,MAAI,CAAC,WAAW,QAAQ,oBAAoB,0BAA0B;AACpE,UAAM,IAAI,qBAAqB,iCAAiC,wBAAwB,EAAE;AAAA,EAC5F;AACA,MAAI,QAAQ,SAAS,SAAS;AAC5B,WAAO;AAAA,MACL,iBAAiB;AAAA,MACjB,MAAM;AAAA,MACN,MAAM,YAAY,QAAQ,MAAM,cAAc,GAAG;AAAA,MACjD,GAAI,QAAQ,YAAY,SAAY,CAAC,IAAI,EAAE,SAAS,QAAQ,QAAQ;AAAA,IACtE;AAAA,EACF;AACA,MAAI,QAAQ,SAAS,qBAAqB;AACxC,UAAM,OAAO,OAAO,QAAQ,IAAI;AAChC,QAAI,CAAC,QAAQ,CAAC,MAAM,QAAQ,KAAK,QAAQ,KAAK,CAAC,OAAO,cAAc,KAAK,SAAS,GAAG;AACnF,YAAM,IAAI,qBAAqB,wDAAwD;AAAA,IACzF;AACA,WAAO;AAAA,MACL,iBAAiB;AAAA,MACjB,MAAM;AAAA,MACN,WAAW,YAAY,QAAQ,WAAW,aAAa,GAAG;AAAA,MAC1D;AAAA,IACF;AAAA,EACF;AACA,MAAI,QAAQ,SAAS,gBAAgB;AACnC,UAAM,QAAQ,OAAO,QAAQ,KAAK;AAClC,UAAM,OAAO,OAAO,QAAQ,IAAI;AAChC,QAAI,CAAC,SAAS,CAAC,CAAC,gBAAgB,uBAAuB,oBAAoB,EAAE,SAAS,IAAI,GAAG;AAC3F,YAAM,IAAI,qBAAqB,0DAA0D;AAAA,IAC3F;AACA,WAAO;AAAA,MACL,iBAAiB;AAAA,MACjB,MAAM;AAAA,MACN,WAAW,YAAY,QAAQ,WAAW,aAAa,GAAG;AAAA,MAC1D;AAAA,MACA;AAAA,IACF;AAAA,EACF;AACA,MAAI,QAAQ,SAAS,oBAAoB;AACvC,QAAI,EAAC,oBAAI,IAAI,CAAC,aAAa,UAAU,WAAW,CAAC,GAAE,IAAI,OAAO,QAAQ,MAAM,CAAC,GAAG;AAC9E,YAAM,IAAI,qBAAqB,oCAAoC;AAAA,IACrE;AACA,WAAO;AAAA,MACL,iBAAiB;AAAA,MACjB,MAAM;AAAA,MACN,QAAQ,QAAQ;AAAA,MAChB,GAAI,QAAQ,WAAW,SAAY,CAAC,IAAI,EAAE,QAAQ,QAAQ,OAAO;AAAA,IACnE;AAAA,EACF;AACA,QAAM,IAAI,qBAAqB,mCAAmC;AACpE;AAGO,SAAS,iBAAiB,SAAoC;AACnE,SAAO,GAAG,KAAK,UAAU,OAAO,CAAC;AAAA;AACnC;AAGO,SAAS,iBACd,MACA,OACA,SACA,MAAM,KAAK,IAAI,GACf,KAAK,OAAO,WAAW,GACJ;AACnB,cAAY,MAAM,cAAc,GAAG;AACnC,SAAO,EAAE,SAAS,IAAI,MAAM,OAAO,SAAS,WAAW,IAAI;AAC7D;;;AFvFA,IAAM,eAAe;AAoDd,SAAS,kBAAkB,OAAqB;AACrD,MAAI,CAAC,aAAa,KAAK,KAAK,EAAG,OAAM,IAAI,UAAU,iDAAiD;AACtG;AAEA,eAAe,iBAAiB,QAA2C;AACzE,aAAW,cAAc,QAAQ,IAAI,QAAQ,IAAI,MAAM,0BAAS,EAAE,OAAO,OAAO,GAAG;AACjF,QAAI;AAAE,gBAAM,4BAAO,uBAAK,WAAW,MAAM,GAAG,yBAAU,IAAI;AAAG,aAAO;AAAA,IAAM,QAAQ;AAAA,IAAgC;AAAA,EACpH;AACA,SAAO;AACT;AAKA,eAAsB,sBACpB,YAAsC,QACtC,UAA2C,CAAC,GAClB;AAC1B,QAAM,WAAW,QAAQ,YAAY,QAAQ;AAC7C,QAAM,OAAO,QAAQ,QAAQ,QAAQ;AACrC,QAAM,MAAM,QAAQ,QAAQ,OAAO,+BAAW,iBAAa,4BAAO,IAAI;AACtE,QAAM,YAAY,QAAQ,aAAa;AACvC,QAAM,WAAW,OAAO,WAAsD;AAC5E,QAAI,WAAW,gBAAgB,aAAa,YAAY,SAAS,UAAU;AACzE,YAAM,IAAI,UAAU,8CAA8C;AAAA,IACpE;AACA,QAAI,WAAW,YAAY,aAAa,WAAW,QAAQ,GAAG;AAC5D,YAAM,IAAI,UAAU,2EAA2E;AAAA,IACjG;AACA,QAAI,CAAE,MAAM,UAAU,MAAM,EAAI,OAAM,IAAI,UAAU,GAAG,MAAM,iCAAiC;AAC9F,WAAO;AAAA,EACT;AACA,MAAI,cAAc,OAAQ,QAAO,SAAS,SAAS;AACnD,QAAM,aAAgC,aAAa,WAC/C,SAAS,UAAU,CAAC,aAAa,QAAQ,IAAI,CAAC,QAAQ,IACtD,aAAa,UAAU,CAAC,QAAQ,IAAI,CAAC;AACzC,aAAW,UAAU,YAAY;AAC/B,QAAI,MAAM,UAAU,MAAM,EAAG,QAAO,SAAS,MAAM;AAAA,EACrD;AACA,MAAI,aAAa,SAAS;AACxB,UAAM,IAAI,UAAU,mHAAmH;AAAA,EACzI;AACA,MAAI,aAAa,UAAU;AACzB,UAAM,IAAI,UAAU,uIAAuI;AAAA,EAC7J;AACA,QAAM,IAAI,UAAU,qCAAqC;AAC3D;AAEA,SAAS,wBAA0C;AACjD,SAAO,IAAI,QAAQ,CAACC,UAAS,WAAW;AACtC;AAAA,MACE;AAAA,MACA,CAAC,QAAQ,YAAY,6BAA6B;AAAA,MAClD,EAAE,UAAU,QAAQ,WAAW,KAAK,MAAM,SAAS,IAAO;AAAA,MAC1D,CAAC,OAAO,WAAW;AACjB,YAAI,OAAO;AACT,iBAAO,IAAI,UAAU,6DAA6D,CAAC;AACnF;AAAA,QACF;AACA,QAAAA,SAAQ,OAAO,KAAK,MAAM,MAAM;AAAA,MAClC;AAAA,IACF;AAAA,EACF,CAAC;AACH;AAKA,eAAsB,8BACpB,QACA,UAA8C,CAAC,GAChC;AACf,QAAM,WAAW,QAAQ,YAAY,QAAQ;AAC7C,QAAM,OAAO,QAAQ,QAAQ,QAAQ;AACrC,QAAM,MAAM,QAAQ,QAAQ,OAAO,+BAAW,iBAAa,4BAAO,IAAI;AACtE,MAAI,WAAW,gBAAgB,aAAa,YAAY,SAAS,UAAU;AACzE,UAAM,IAAI,UAAU,8CAA8C;AAAA,EACpE;AACA,MAAI,WAAW,YAAY,aAAa,QAAS;AACjD,MAAI,QAAQ,EAAG,OAAM,IAAI,UAAU,2EAA2E;AAC9G,QAAM,WAAW,OAAO,QAAQ,kBAAkB,uBAAuB;AACzE,MAAI,CAAC,SAAU,OAAM,IAAI,UAAU,wEAAwE;AAC7G;AAGO,SAAS,sBAAsB,SAAmF;AACvH,MAAI,CAAC,QAAQ,mBAAoB,mBAAkB,QAAQ,KAAK;AAChE,MAAI,UAAU,KAAK,QAAQ,YAAY,EAAG,OAAM,IAAI,UAAU,sDAAsD;AACpH,QAAM,MAAM,OAAO,+BAAW,iBAAa,4BAAO,IAAI;AACtD,QAAM,MAAM,OAAO,+BAAW,iBAAa,4BAAO,IAAI;AACtD,QAAM,cAAc,QAAQ,KAAK,UAAU,YAAY,EAAE,QAAQ,iBAAiB,GAAG,EAAE,MAAM,GAAG,EAAE;AAClG,QAAM,OAAO,gBAAgB,WAAW,IAAI,OAAO,WAAW,EAAE,MAAM,GAAG,CAAC,CAAC;AAC3E,QAAM,SAAS,QAAQ,UAAU,CAAC;AAClC,QAAMC,UAAS,QAAQ,mBAAmB;AAC1C,QAAM,aAAaA,YAAW,SAAS,CAAC,IAAI,CAAC,4BAA4B,QAAQ,YAAY,qBAAqBA,YAAW,cAAc,cAAc,EAAE,EAAE;AAC7J,QAAM,WAAWA,YAAW,SAAS,CAAC,IAAI,CAAC,yBAAyB,QAAQ,YAAY,kBAAkBA,YAAW,cAAc,cAAc,EAAE,EAAE;AACrJ,MAAI,QAAQ,WAAW,aAAa;AAClC,WAAO;AAAA,MACL;AAAA,MAAO;AAAA,MAAQ;AAAA,MAAiB,UAAU,IAAI;AAAA,MAC9C;AAAA,MAAkB;AAAA,MAAe;AAAA,MACjC,YAAY,OAAO,UAAU,IAAI;AAAA,MAAI,UAAU,OAAO,QAAQ,CAAC;AAAA,MAC/D,UAAU,GAAG,IAAI,GAAG;AAAA,MAAI;AAAA,MACxB,GAAG;AAAA,MACH;AAAA,MAAwB,+BAA+B,wBAAwB;AAAA,MAC/E,mCAAmC,QAAQ,KAAK,SAAS;AAAA,MACzD,QAAQ;AAAA,IACV;AAAA,EACF;AACA,SAAO;AAAA,IACL;AAAA,IAAO;AAAA,IAAQ;AAAA,IAAiB,UAAU,IAAI;AAAA,IAAI;AAAA,IAClD;AAAA,IAAkB;AAAA,IAAe;AAAA,IACjC;AAAA,IAAoC,gBAAgB,OAAO,QAAQ,GAAG;AAAA,IACtE,YAAY,OAAO,UAAU,IAAI;AAAA,IAAI,UAAU,OAAO,QAAQ,CAAC;AAAA,IAC/D,UAAU,GAAG,IAAI,GAAG;AAAA,IACpB,4CAA4C,OAAO,cAAc,KAAK,OAAO,IAAI;AAAA,IACjF,GAAG;AAAA,IACH;AAAA,IAAwB,+BAA+B,wBAAwB;AAAA,IAC/E,mCAAmC,QAAQ,KAAK,SAAS;AAAA,IACzD,QAAQ;AAAA,EACV;AACF;AAEA,SAAS,cAAc,MAAwB;AAC7C,SAAO,KAAK,KAAK,CAAC,QAAQ,IAAI,WAAW,SAAS,CAAC,EAAG,MAAM,UAAU,MAAM;AAC9E;AAMA,eAAsB,oBAAoB,SAA2D;AACnG,MAAI,QAAQ,QAAQ,QAAS,QAAO,EAAE,UAAU,GAAG,QAAQ,aAAa,QAAQ,GAAG;AACnF,QAAM,8BAA8B,QAAQ,MAAM;AAClD,QAAM,OAAO,sBAAsB,OAAO;AAC1C,QAAM,OAAO,cAAc,IAAI;AAC/B,QAAM,YAAQ,iCAAM,QAAQ,QAAQ,MAAM,EAAE,OAAO,CAAC,QAAQ,QAAQ,MAAM,GAAG,OAAO,MAAM,CAAC;AAC3F,MAAI,SAAS;AACb,MAAI,cAAc;AAClB,MAAI,WAA6E;AACjF,MAAI,UAAU;AACd,MAAI,SAAS;AAEb,QAAM,OAAO,YAAY,MAAM;AAC/B,QAAM,OAAO,GAAG,QAAQ,CAAC,SAAiB;AACxC,QAAI,OAAO,SAAS,KAAK,KAAM,WAAU,KAAK,MAAM,GAAG,KAAK,OAAO,OAAO,MAAM;AAAA,EAClF,CAAC;AAED,QAAM,OAAO,CAAC,WAAmB;AAC/B,QAAI,WAAW,OAAQ;AACvB,cAAU;AACV,QAAI,CAAC,MAAM,MAAM,WAAW;AAC1B,YAAM,SAA4B,EAAE,iBAAiB,0BAA0B,MAAM,kBAAkB,OAAO;AAC9G,YAAM,MAAM,MAAM,iBAAiB,MAAM,CAAC;AAAA,IAC5C;AACA,UAAM,aAAa,QAAQ,WAAW,cAAc,CAAC,UAAU,WAAW,IAAI,IAAI,CAAC,MAAM,MAAM,IAAI;AACnG,UAAM,aAAS,iCAAM,QAAQ,QAAQ,YAAY,EAAE,OAAO,UAAU,OAAO,MAAM,CAAC;AAClF,WAAO,MAAM;AAAA,EACf;AACA,QAAM,QAAQ,MAAM,KAAK,kBAAkB;AAC3C,UAAQ,QAAQ,iBAAiB,SAAS,OAAO,EAAE,MAAM,KAAK,CAAC;AAE/D,QAAM,UAAU,WAAW,MAAM,KAAK,SAAS,GAAG,QAAQ,KAAK,OAAO,SAAS;AAC/E,QAAM,QAA2B,EAAE,iBAAiB,0BAA0B,MAAM,cAAc,MAAM,QAAQ,KAAK;AACrH,MAAI,CAAC,WAAW,CAAC,QAAQ,QAAQ,QAAS,OAAM,MAAM,MAAM,iBAAiB,KAAK,CAAC;AAEnF,QAAM,WAAW,YAAY;AAC3B,QAAI,UAAU,OAAO,MAAM,CAAC;AAC5B,UAAM,aAAa,OAAO,QAAgB;AACxC,YAAM,QAAQ,IAAI,GAAG,EAAE,MAAM,KAAK,IAAI,SAAS,GAAG,EAAE,IAAI;AACxD,UAAI,MAAM,aAAa,IAAW,OAAM,IAAI,MAAM,4BAA4B;AAC9E,YAAM,OAAO,MAAM,SAAS,MAAM;AAClC,UAAI,CAAC,KAAK,KAAK,EAAG;AAClB,YAAM,UAAU,iBAAiB,IAAI;AACrC,UAAI,QAAQ,SAAS,mBAAoB,YAAW;AACpD,YAAM,WAAW,MAAM,QAAQ,UAAU,OAAO;AAChD,UAAI,YAAY,CAAC,MAAM,MAAM,UAAW,OAAM,MAAM,MAAM,iBAAiB,QAAQ,CAAC;AAAA,IACtF;AACA,QAAI;AACF,uBAAiB,OAAO,MAAM,QAAQ;AACpC,cAAM,QAAQ,OAAO,SAAS,GAAG,IAAI,MAAM,OAAO,KAAK,GAAG;AAC1D,uBAAe,MAAM;AACrB,YAAI,cAAc,QAAQ,KAAK,OAAO,gBAAgB;AACpD,gBAAM,IAAI,MAAM,wBAAwB,QAAQ,KAAK,OAAO,cAAc,QAAQ;AAAA,QACpF;AACA,kBAAU,OAAO,OAAO,CAAC,SAAS,KAAK,CAAC;AACxC,YAAI,UAAU,QAAQ,QAAQ,EAAE;AAChC,eAAO,WAAW,GAAG;AACnB,gBAAM,WAAW,QAAQ,SAAS,GAAG,OAAO,CAAC;AAC7C,oBAAU,QAAQ,SAAS,UAAU,CAAC;AACtC,oBAAU,QAAQ,QAAQ,EAAE;AAAA,QAC9B;AACA,YAAI,QAAQ,aAAa,IAAW,OAAM,IAAI,MAAM,4BAA4B;AAAA,MAClF;AACA,UAAI,QAAQ,WAAY,OAAM,WAAW,OAAO;AAAA,IAClD,SAAS,OAAO;AACd,WAAK,gBAAgB;AACrB,YAAM;AAAA,IACR;AAAA,EACF,GAAG;AAEH,QAAM,OAAO,IAAI,QAAgB,CAAC,QAAQ,WAAW;AACnD,UAAM,KAAK,SAAS,MAAM;AAC1B,UAAM,KAAK,QAAQ,CAAC,SAAS;AAAE,eAAS;AAAM,aAAO,QAAQ,CAAC;AAAA,IAAG,CAAC;AAAA,EACpE,CAAC;AACD,MAAI;AACF,UAAM,CAAC,QAAQ,IAAI,MAAM,QAAQ,IAAI,CAAC,MAAM,OAAO,CAAC;AACpD,QAAI,UAAU,QAAQ,SAAU,OAAM,QAAQ,SAAS,MAAM;AAC7D,QAAI,QAAQ,QAAQ,QAAS,QAAO,EAAE,UAAU,QAAQ,aAAa,OAAO;AAC5E,UAAM,WAAW;AACjB,QAAI,CAAC,SAAU,QAAO,EAAE,UAAU,QAAQ,UAAU,QAAQ,EAAE,OAAO,kCAAkC,GAAG,OAAO;AACjH,WAAO,EAAE,UAAU,QAAQ,aAAa,IAAI,SAAS,SAAS,UAAU,QAAQ,SAAS,QAAQ,OAAO;AAAA,EAC1G,SAAS,OAAO;AACd,SAAK,cAAc;AACnB,UAAM,KAAK,MAAM,MAAM,CAAC;AACxB,UAAM;AAAA,EACR,UAAE;AACA,iBAAa,OAAO;AACpB,YAAQ,QAAQ,oBAAoB,SAAS,KAAK;AAAA,EACpD;AACF;;;AG5RA,IAAAC,mBAAoC;;;ACApC,IAAAC,mBAAoF;AACpF,qBAAuB;AACvB,IAAAC,oBAAuD;AACvD,IAAAC,6BAAsB;;;ACHtB,IAAAC,oBAA2B;AAEpB,IAAM,sBAAsB,oBAAI,IAAI;AAAA,EACzC;AAAA,EAAQ;AAAA,EAAS;AAAA,EAAa;AAAA,EAAgB;AAAA,EAAQ;AACxD,CAAC;AACM,IAAM,wBAAwB;AAG9B,SAAS,qBAAqB,cAA+B;AAClE,QAAM,QAAQ,aAAa,MAAM,GAAG;AACpC,SAAO,KAAC,8BAAW,YAAY,KAAK,CAAC,aAAa,SAAS,IAAI,KAAK,CAAC,aAAa,SAAS,IAAI,KAC1F,CAAC,MAAM,KAAK,CAAC,SAAS,CAAC,QAAQ,SAAS,OAAO,SAAS,QAAQ,oBAAoB,IAAI,IAAI,CAAC,KAC7F,CAAC,sBAAsB,KAAK,MAAM,GAAG,EAAE,KAAK,EAAE;AACrD;;;ADqBA,eAAe,YAAY,WAAmB,UAAkB,UAAyC;AACvG,QAAM,QAAsB,CAAC;AAC7B,MAAI,QAAQ;AACZ,QAAM,OAAO,OAAO,QAA+B;AACjD,eAAW,SAAS,UAAM,0BAAQ,KAAK,EAAE,eAAe,KAAK,CAAC,GAAG;AAC/D,UAAI,MAAM,YAAY,KAAK,oBAAoB,IAAI,MAAM,IAAI,EAAG;AAChE,UAAI,CAAC,MAAM,YAAY,KAAK,sBAAsB,KAAK,MAAM,IAAI,EAAG;AACpE,YAAM,WAAO,wBAAK,KAAK,MAAM,IAAI;AACjC,UAAI,MAAM,eAAe,EAAG;AAC5B,UAAI,MAAM,YAAY,GAAG;AACvB,cAAM,KAAK,IAAI;AACf;AAAA,MACF;AACA,UAAI,CAAC,MAAM,OAAO,EAAG;AACrB,YAAM,WAAW,UAAM,uBAAK,IAAI;AAChC,eAAS,SAAS;AAClB,UAAI,MAAM,SAAS,IAAI,SAAU,OAAM,IAAI,MAAM,qBAAqB,QAAQ,QAAQ;AACtF,UAAI,QAAQ,SAAU,OAAM,IAAI,MAAM,qBAAqB,QAAQ,QAAQ;AAC3E,YAAM,KAAK;AAAA,QACT,QAAQ;AAAA,QACR,kBAAc,4BAAS,WAAW,IAAI;AAAA,QACtC,MAAM,SAAS,OAAO;AAAA,QACtB,OAAO,SAAS;AAAA,MAClB,CAAC;AAAA,IACH;AAAA,EACF;AACA,QAAM,KAAK,SAAS;AACpB,SAAO,MAAM,KAAK,CAAC,MAAM,UAAU,KAAK,aAAa,cAAc,MAAM,YAAY,CAAC;AACxF;AAEA,eAAe,eAAe,WAAmB,UAAkB,UAAyC;AAC1G,QAAM,YAAQ,kCAAM,OAAO,CAAC,YAAY,MAAM,YAAY,YAAY,oBAAoB,GAAG;AAAA,IAC3F,KAAK;AAAA,IAAW,OAAO,CAAC,UAAU,QAAQ,MAAM;AAAA,IAAG,OAAO;AAAA,EAC5D,CAAC;AACD,QAAM,SAAmB,CAAC;AAC1B,QAAM,SAAmB,CAAC;AAC1B,MAAI,cAAc;AAClB,QAAM,OAAO,GAAG,QAAQ,CAAC,UAAkB;AACzC,mBAAe,MAAM;AACrB,QAAI,cAAc,IAAI,OAAO,KAAM,OAAM,KAAK,SAAS;AAAA,QAClD,QAAO,KAAK,KAAK;AAAA,EACxB,CAAC;AACD,QAAM,OAAO,GAAG,QAAQ,CAAC,UAAkB;AACzC,QAAI,OAAO,OAAO,CAAC,KAAK,UAAU,MAAM,MAAM,YAAY,CAAC,IAAI,MAAQ,QAAO,KAAK,KAAK;AAAA,EAC1F,CAAC;AACD,QAAM,OAAO,MAAM,IAAI,QAAuB,CAAC,QAAQ,WAAW;AAChE,UAAM,KAAK,SAAS,MAAM;AAC1B,UAAM,KAAK,QAAQ,MAAM;AAAA,EAC3B,CAAC;AACD,MAAI,cAAc,IAAI,OAAO,KAAM,OAAM,IAAI,MAAM,kCAAkC;AACrF,MAAI,SAAS,EAAG,OAAM,IAAI,MAAM,8BAA8B,OAAO,OAAO,MAAM,EAAE,SAAS,MAAM,EAAE,MAAM,GAAG,GAAK,CAAC,EAAE;AACtH,QAAM,QAAQ,OAAO,OAAO,MAAM,EAAE,SAAS,MAAM,EAAE,MAAM,IAAI,EAAE,OAAO,OAAO,EAAE,KAAK;AACtF,MAAI,MAAM,SAAS,SAAU,OAAM,IAAI,MAAM,qBAAqB,QAAQ,QAAQ;AAClF,QAAM,WAAO,2BAAQ,SAAS;AAC9B,QAAM,QAAsB,CAAC;AAC7B,MAAI,QAAQ;AACZ,aAAW,gBAAgB,OAAO;AAChC,QAAI,CAAC,qBAAqB,YAAY,EAAG;AACzC,UAAM,aAAS,2BAAQ,MAAM,YAAY;AACzC,QAAI,CAAC,OAAO,WAAW,GAAG,IAAI,GAAG,qBAAG,EAAE,EAAG,OAAM,IAAI,UAAU,iCAAiC;AAC9F,QAAI;AACJ,QAAI;AAAE,iBAAW,UAAM,wBAAM,MAAM;AAAA,IAAG,SAC/B,OAAO;AACZ,UAAK,MAAgC,SAAS,SAAU;AACxD,YAAM;AAAA,IACR;AACA,QAAI,SAAS,eAAe,KAAK,CAAC,SAAS,OAAO,EAAG;AACrD,aAAS,SAAS;AAClB,QAAI,QAAQ,SAAU,OAAM,IAAI,MAAM,qBAAqB,QAAQ,QAAQ;AAC3E,UAAM,KAAK,EAAE,QAAQ,cAAc,MAAM,SAAS,OAAO,KAAO,OAAO,SAAS,KAAK,CAAC;AAAA,EACxF;AACA,SAAO;AACT;AAEA,eAAe,SAAS,OAAqB,aAAoC;AAC/E,aAAW,QAAQ,OAAO;AACxB,UAAM,aAAS,wBAAK,aAAa,KAAK,YAAY;AAClD,cAAM,4BAAM,2BAAQ,QAAQ,IAAI,GAAG,EAAE,WAAW,KAAK,CAAC;AACtD,cAAM,2BAAS,KAAK,QAAQ,MAAM;AAClC,cAAM,wBAAM,QAAQ,KAAK,IAAI;AAAA,EAC/B;AACF;AAEA,eAAe,eAAe,MAAc,UAAmC;AAC7E,QAAM,YAAQ,kCAAM,OAAO;AAAA,IACzB;AAAA,IAAQ;AAAA,IAAc;AAAA,IAAY;AAAA,IAClC;AAAA,IAAmB;AAAA,IAAmB;AAAA,IAAM;AAAA,IAAY;AAAA,EAC1D,GAAG,EAAE,KAAK,MAAM,OAAO,CAAC,UAAU,QAAQ,MAAM,GAAG,OAAO,MAAM,CAAC;AACjE,QAAM,SAAmB,CAAC;AAC1B,QAAM,SAAmB,CAAC;AAC1B,MAAI,QAAQ;AACZ,QAAM,OAAO,GAAG,QAAQ,CAAC,UAAkB;AACzC,aAAS,MAAM;AACf,QAAI,QAAQ,SAAU,OAAM,KAAK,SAAS;AAAA,QACrC,QAAO,KAAK,KAAK;AAAA,EACxB,CAAC;AACD,QAAM,OAAO,GAAG,QAAQ,CAAC,UAAkB;AACzC,QAAI,OAAO,OAAO,CAAC,KAAK,UAAU,MAAM,MAAM,YAAY,CAAC,IAAI,MAAQ,QAAO,KAAK,KAAK;AAAA,EAC1F,CAAC;AACD,QAAM,OAAO,MAAM,IAAI,QAAuB,CAAC,QAAQ,WAAW;AAChE,UAAM,KAAK,SAAS,MAAM;AAC1B,UAAM,KAAK,QAAQ,MAAM;AAAA,EAC3B,CAAC;AACD,MAAI,QAAQ,SAAU,OAAM,IAAI,MAAM,iBAAiB,QAAQ,QAAQ;AACvE,MAAI,SAAS,KAAK,SAAS,GAAG;AAC5B,UAAM,IAAI,MAAM,oBAAoB,OAAO,OAAO,MAAM,EAAE,SAAS,MAAM,EAAE,MAAM,GAAG,GAAK,CAAC,EAAE;AAAA,EAC9F;AACA,SAAO,OAAO,OAAO,MAAM,EAAE,SAAS,MAAM,EACzC,WAAW,eAAe,IAAI,EAC9B,WAAW,gBAAgB,IAAI,EAC/B,WAAW,eAAe,IAAI,EAC9B,WAAW,gBAAgB,IAAI,EAC/B,WAAW,kBAAkB,OAAO,EACpC,WAAW,mBAAmB,OAAO;AAC1C;AAKA,eAAsB,eAAe,QAAgB,UAAiC,CAAC,GAA6B;AAClH,QAAM,YAAY,UAAM,+BAAS,2BAAQ,MAAM,CAAC;AAChD,QAAM,aAAa,UAAM,uBAAK,SAAS;AACvC,MAAI,CAAC,WAAW,YAAY,EAAG,OAAM,IAAI,UAAU,sCAAsC;AACzF,QAAM,OAAO,UAAM,8BAAQ,wBAAK,QAAQ,gBAAY,uBAAO,GAAG,eAAe,CAAC;AAC9E,QAAM,kBAAc,wBAAK,MAAM,UAAU;AACzC,QAAM,mBAAe,wBAAK,MAAM,WAAW;AAC3C,QAAM,QAAQ,IAAI,KAAC,wBAAM,WAAW,OAAG,wBAAM,YAAY,CAAC,CAAC;AAC3D,MAAI;AACF,UAAM,WAAW,QAAQ,YAAY;AACrC,UAAM,WAAW,QAAQ,YAAY,MAAM,OAAO;AAClD,UAAM,QAAQ,QAAQ,yBAClB,MAAM,eAAe,WAAW,UAAU,QAAQ,IAClD,MAAM,YAAY,WAAW,UAAU,QAAQ;AACnD,UAAM,QAAQ,IAAI,CAAC,SAAS,OAAO,WAAW,GAAG,SAAS,OAAO,YAAY,CAAC,CAAC;AAC/E,WAAO;AAAA,MACL;AAAA,MACA;AAAA,MACA;AAAA,MACA,WAAW,MAAM;AAAA,MACjB,WAAW,MAAM,OAAO,CAAC,KAAK,SAAS,MAAM,KAAK,OAAO,CAAC;AAAA,MAC1D,OAAO,CAACC,cAAa,eAAe,MAAMA,SAAQ;AAAA,MAClD,SAAS,UAAM,qBAAG,MAAM,EAAE,WAAW,MAAM,OAAO,KAAK,CAAC;AAAA,IAC1D;AAAA,EACF,SAAS,OAAO;AACd,cAAM,qBAAG,MAAM,EAAE,WAAW,MAAM,OAAO,KAAK,CAAC;AAC/C,UAAM;AAAA,EACR;AACF;;;ADtJA,eAAe,OACb,SACA,OACA,MACA,OACA,SACe;AACf,QAAM,QAAQ,aAAa,MAAM,KAAK,WAAW,MAAM,SAAS,CAAC,iBAAiB,MAAM,OAAO,OAAO,CAAC,CAAC;AAC1G;AAIA,eAAsB,iBAAiB,OAAqB,SAA8C;AACxG,QAAM,SAAS,QAAQ,WAAW,MAAM,KAAK,SAAS;AACtD,MAAI,CAAC,QAAQ;AACX,UAAM,QAAQ,QAAQ,SAAS,MAAM,KAAK,WAAW,MAAM,SAAS;AAAA,MAClE,QAAQ;AAAA,MACR,OAAO,qCAAqC,MAAM,KAAK,SAAS;AAAA,IAClE,CAAC;AACD;AAAA,EACF;AAEA,MAAI,SAAiC;AACrC,QAAM,aAAa,IAAI,gBAAgB;AACvC,QAAM,mBAAmB,MAAM,WAAW,MAAM,QAAQ,QAAQ,MAAM;AACtE,UAAQ,QAAQ,iBAAiB,SAAS,kBAAkB,EAAE,MAAM,KAAK,CAAC;AAC1E,MAAI,QAAQ,QAAQ,QAAS,YAAW,MAAM,QAAQ,OAAO,MAAM;AACnE,MAAI;AACJ,MAAI,oBAAoB;AACxB,QAAM,QAAQ,YAAY;AACxB,QAAI,qBAAqB,WAAW,OAAO,QAAS;AACpD,wBAAoB;AACpB,QAAI;AACF,YAAM,QAAQ,MAAM,QAAQ,QAAQ,UAAU,MAAM,KAAK,WAAW,MAAM,OAAO;AACjF,UAAI,MAAM,gBAAiB,YAAW,MAAM,kBAAkB;AAAA,IAChE,QAAQ;AACN,iBAAW,MAAM,kBAAkB;AAAA,IACrC,UAAE;AACA,0BAAoB;AAAA,IACtB;AAAA,EACF;AACA,MAAI;AACF,UAAM,MAAM;AACZ,gBAAY,YAAY,MAAM;AAAE,WAAK,MAAM;AAAA,IAAG,GAAG,QAAQ,eAAe,IAAM;AAC9E,QAAI,WAAW,OAAO,QAAS,OAAM,IAAI,MAAM,8CAA8C;AAC7F,aAAS,MAAM,eAAe,MAAM;AACpC,QAAI,WAAW,OAAO,QAAS,OAAM,IAAI,MAAM,8CAA8C;AAC7F,UAAM,kBAAkB;AACxB,UAAM,OAAO,QAAQ,SAAS,OAAO,2BAA2B,UAAU;AAAA,MACxE,WAAW,MAAM,KAAK;AAAA,MACtB,OAAO,gBAAgB;AAAA,MACvB,OAAO,gBAAgB;AAAA,IACzB,CAAC;AAED,UAAM,SAAS,MAAM,oBAAoB;AAAA,MACvC,QAAQ,QAAQ;AAAA,MAChB,OAAO,QAAQ;AAAA,MACf,cAAc,gBAAgB;AAAA,MAC9B,MAAM,MAAM;AAAA,MACZ,QAAQ,QAAQ;AAAA,MAChB,oBAAoB,QAAQ;AAAA,MAC5B,iBAAiB,QAAQ,oBAAoB,QAAQ,aAAa,SAAS;AAAA,MAC3E,QAAQ,WAAW;AAAA,MACnB,UAAU,OAAO,SAAS;AACxB,cAAM,OAAO,QAAQ,SAAS,OAAO,gBAAgB,SAAS,EAAE,MAAM,KAAK,MAAM,GAAG,KAAK,IAAI,EAAE,CAAC;AAAA,MAClG;AAAA,MACA,WAAW,OAAO,YAAmE;AACnF,YAAI,QAAQ,SAAS,SAAS;AAC5B,gBAAM,OAAO,QAAQ,SAAS,OAAO,QAAQ,MAAM,SAAS,QAAQ,WAAW,IAAI;AACnF;AAAA,QACF;AACA,YAAI,QAAQ,SAAS,oBAAoB;AACvC,gBAAM,OAAO,QAAQ,SAAS,OAAO,mBAAmB,SAAS;AAAA,YAC/D,QAAQ,QAAQ;AAAA,YAChB,QAAQ,QAAQ,UAAU;AAAA,UAC5B,CAAC;AACD;AAAA,QACF;AACA,YAAI,QAAQ,SAAS,gBAAgB;AACnC,gBAAM,OAAO,QAAQ,SAAS,OAAO,kBAAkB,SAAS;AAAA,YAC9D,WAAW,QAAQ;AAAA,YAAW,MAAM,QAAQ;AAAA,UAC9C,CAAC;AACD,gBAAMC,YAAW,QAAQ,aACrB,MAAM,QAAQ,WAAW,QAAQ;AAAA,YACjC;AAAA,YAAO,cAAc,gBAAgB;AAAA,YAAc,QAAQ,WAAW;AAAA,UACxE,GAAG,OAAO,IACR,EAAE,WAAW,QAAQ,WAAW,IAAI,OAAO,SAAS,4CAA4C;AACpG,gBAAM,OAAO,QAAQ,SAAS,OAAO,kBAAkB,UAAU;AAAA,YAC/D,WAAW,QAAQ;AAAA,YAAW,MAAM,QAAQ;AAAA,YAAM,IAAIA,UAAS;AAAA,YAC/D,cAAc,OAAO,WAAWA,UAAS,OAAO;AAAA,UAClD,CAAC;AACD,iBAAO,EAAE,iBAAiB,0BAA0B,MAAM,iBAAiB,GAAGA,UAAS;AAAA,QACzF;AACA,cAAM,OAAO,QAAQ,SAAS,OAAO,mBAAmB,SAAS;AAAA,UAC/D,WAAW,QAAQ;AAAA,UACnB,UAAU,QAAQ,KAAK,SAAS;AAAA,UAChC,WAAW,QAAQ,KAAK;AAAA,QAC1B,CAAC;AACD,cAAM,WAAW,MAAM,QAAQ,QAAQ,MAAM,MAAM,KAAK,WAAW,MAAM,SAAS;AAAA,UAChF,WAAW,QAAQ;AAAA,UACnB,MAAM,QAAQ;AAAA,QAChB,CAAC;AACD,cAAM,OAAO,QAAQ,SAAS,OAAO,mBAAmB,SAAS;AAAA,UAC/D,WAAW,QAAQ;AAAA,UACnB,UAAU,SAAS;AAAA,UACnB,SAAS,SAAS;AAAA,QACpB,CAAC;AACD,eAAO;AAAA,UACL,iBAAiB;AAAA,UACjB,MAAM;AAAA,UACN,WAAW,QAAQ;AAAA,UACnB,UAAU,SAAS;AAAA,QACrB;AAAA,MACF;AAAA,IACF,CAAC;AAED,UAAM,QAAQ,MAAM,gBAAgB,MAAM,MAAM,KAAK,OAAO,aAAa;AACzE,UAAM,QAAQ,QAAQ,SAAS,MAAM,KAAK,WAAW,MAAM,SAAS;AAAA,MAClE,QAAQ,OAAO;AAAA,MACf,QAAQ,OAAO;AAAA,MACf;AAAA,MACA,GAAI,OAAO,WAAW,WAAW,EAAE,OAAO,OAAO,OAAO,MAAM,GAAG,GAAK,KAAK,2BAA2B,IAAI,CAAC;AAAA,IAC7G,CAAC;AAAA,EACH,SAAS,QAAQ;AACf,UAAM,UAAU,kBAAkB,QAAQ,OAAO,UAAU;AAC3D,QAAI;AACF,YAAM,OAAO,QAAQ,SAAS,OAAO,iBAAiB,UAAU,EAAE,QAAQ,CAAC;AAC3E,YAAM,QAAQ,QAAQ,SAAS,MAAM,KAAK,WAAW,MAAM,SAAS;AAAA,QAClE,QAAQ,WAAW,OAAO,UAAU,cAAc;AAAA,QAClD,OAAO;AAAA,MACT,CAAC;AAAA,IACH,QAAQ;AAAA,IAER;AAAA,EACF,UAAE;AACA,QAAI,UAAW,eAAc,SAAS;AACtC,YAAQ,QAAQ,oBAAoB,SAAS,gBAAgB;AAC7D,QAAI,UAAU,CAAC,QAAQ,kBAAmB,OAAM,OAAO,QAAQ;AAAA,EACjE;AACF;AAIA,eAAsB,iBAAiB,SAA8C;AACnF,QAAM,iBAAiB,OAAO,KAAK,QAAQ,UAAU,EAAE,KAAK;AAC5D,MAAI,CAAC,eAAe,OAAQ,OAAM,IAAI,UAAU,4CAA4C;AAC5F,KAAG;AACD,QAAI,QAAQ,QAAQ,QAAS;AAC7B,UAAM,QAAQ,MAAM,QAAQ,QAAQ,MAAM,cAAc;AACxD,QAAI,OAAO;AACT,cAAQ,MAAM,UAAU,MAAM,KAAK,MAAM,IAAI,MAAM,KAAK,SAAS,EAAE;AACnE,YAAM,iBAAiB,OAAO,OAAO;AACrC,UAAI,QAAQ,KAAM;AAClB;AAAA,IACF;AACA,QAAI,QAAQ,KAAM;AAClB,cAAM,iBAAAC,YAAM,QAAQ,UAAU,KAAO,QAAW,EAAE,QAAQ,QAAQ,OAAO,CAAC,EAAE,MAAM,MAAM;AAAA,IAAC,CAAC;AAAA,EAC5F,SAAS,CAAC,QAAQ,QAAQ;AAC5B;;;AL5KA,SAAS,QAAgB;AACvB,SAAO;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAST;AAEA,SAAS,MAAM,MAA4B;AACzC,MAAI,KAAK,CAAC,MAAM,SAAU,OAAM,IAAI,UAAU,MAAM,CAAC;AACrD,QAAM,SAAmC,CAAC;AAC1C,QAAM,QAAQ,oBAAI,IAAY;AAC9B,WAAS,QAAQ,GAAG,QAAQ,KAAK,QAAQ,SAAS;AAChD,UAAM,MAAM,KAAK,KAAK;AACtB,QAAI,CAAC,UAAU,wBAAwB,wBAAwB,EAAE,SAAS,GAAG,GAAG;AAC9E,YAAM,IAAI,GAAG;AACb;AAAA,IACF;AACA,QAAI,CAAC,IAAI,WAAW,IAAI,KAAK,CAAC,KAAK,QAAQ,CAAC,EAAG,OAAM,IAAI,UAAU,qBAAqB,GAAG,EAAE;AAC7F,KAAC,OAAO,GAAG,MAAM,CAAC,GAAG,KAAK,KAAK,EAAE,KAAK,CAAE;AAAA,EAC1C;AACA,QAAM,WAAW,OAAO,YAAY,GAAG,GAAG,EAAE;AAC5C,QAAM,QAAQ,OAAO,SAAS,GAAG,GAAG,EAAE;AACtC,QAAM,SAAS,OAAO,UAAU,GAAG,GAAG,EAAE,KAAK;AAC7C,MAAI,CAAC,YAAY,CAAC,SAAS,CAAC,CAAC,QAAQ,aAAa,UAAU,QAAQ,EAAE,SAAS,MAAM,EAAG,OAAM,IAAI,UAAU,MAAM,CAAC;AACnH,QAAM,aAAqC,CAAC;AAC5C,aAAW,WAAW,OAAO,aAAa,KAAK,CAAC,GAAG;AACjD,UAAM,SAAS,QAAQ,QAAQ,GAAG;AAClC,UAAM,MAAM,QAAQ,MAAM,GAAG,MAAM;AACnC,UAAM,OAAO,QAAQ,MAAM,SAAS,CAAC;AACrC,QAAI,SAAS,KAAK,CAAC,6BAA6B,KAAK,GAAG,KAAK,CAAC,MAAM;AAClE,YAAM,IAAI,UAAU,8BAA8B,OAAO,EAAE;AAAA,IAC7D;AACA,eAAW,GAAG,QAAI,2BAAQ,IAAI;AAAA,EAChC;AACA,MAAI,CAAC,OAAO,KAAK,UAAU,EAAE,OAAQ,OAAM,IAAI,UAAU,yDAAyD;AAClH,QAAM,qBAAqB,MAAM,IAAI,wBAAwB;AAC7D,MAAI,sBAAsB,QAAQ,IAAI,gCAAgC,KAAK;AACzE,UAAM,IAAI,UAAU,+DAA+D;AAAA,EACrF;AACA,QAAM,SAAS,OAAO,OAAO,WAAW,GAAG,GAAG,EAAE,KAAK,GAAK;AAC1D,MAAI,CAAC,OAAO,cAAc,MAAM,KAAK,SAAS,OAAO,SAAS,KAAQ;AACpE,UAAM,IAAI,UAAU,gDAAgD;AAAA,EACtE;AACA,SAAO;AAAA,IACL;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA,MAAM,MAAM,IAAI,QAAQ;AAAA,IACxB;AAAA,IACA,mBAAmB,MAAM,IAAI,sBAAsB;AAAA,IACnD;AAAA,EACF;AACF;AAEA,eAAe,OAAsB;AACnC,QAAM,QAAQ,QAAQ,IAAI;AAC1B,MAAI,CAAC,MAAO,OAAM,IAAI,UAAU,gCAAgC;AAChE,QAAM,UAAU,MAAM,QAAQ,KAAK,MAAM,CAAC,CAAC;AAC3C,QAAM,aAAa,IAAI,gBAAgB;AACvC,aAAW,UAAU,CAAC,UAAU,SAAS,EAAY,SAAQ,KAAK,QAAQ,MAAM,WAAW,MAAM,MAAM,CAAC;AACxG,QAAM,SAAS,MAAM,sBAAsB,QAAQ,MAAM;AACzD,MAAI,QAAQ,aAAa,WAAW,WAAW,UAAU;AACvD,YAAQ,OAAO,MAAM,2GAA2G;AAAA,EAClI;AACA,QAAM,iBAAiB;AAAA,IACrB,GAAG;AAAA,IACH;AAAA,IACA,SAAS,2BAA2B,EAAE,UAAU,QAAQ,UAAU,OAAO,QAAQ,WAAW,OAAO,CAAC;AAAA,IACpG,QAAQ,WAAW;AAAA,IACnB,KAAK,CAAC,YAAY,QAAQ,OAAO,MAAM,kBAAkB,OAAO;AAAA,CAAI;AAAA,EACtE,CAAC;AACH;AAEA,KAAK,EAAE,MAAM,CAAC,UAAU;AACtB,UAAQ,OAAO,MAAM,GAAG,iBAAiB,QAAQ,MAAM,UAAU,OAAO,KAAK,CAAC;AAAA,CAAI;AAClF,UAAQ,WAAW;AACrB,CAAC;","names":["import_node_path","resolve","access","import_promises","import_promises","import_node_path","import_node_child_process","import_node_path","maxBytes","response","delay"]}
package/dist/cli.js CHANGED
@@ -4,12 +4,12 @@ import {
4
4
  } from "./chunk-PTXZVYD4.js";
5
5
  import {
6
6
  runHarnessRunner
7
- } from "./chunk-CIKYMC67.js";
7
+ } from "./chunk-OZBJNTML.js";
8
8
  import {
9
9
  selectContainerEngine
10
- } from "./chunk-HDIR4MM5.js";
11
- import "./chunk-VGNIDRKM.js";
12
- import "./chunk-I43KTCJ2.js";
10
+ } from "./chunk-5LRYJKUI.js";
11
+ import "./chunk-VDY5V7ZG.js";
12
+ import "./chunk-U324RQ4N.js";
13
13
 
14
14
  // src/cli.ts
15
15
  import { resolve } from "path";