From 20651ab231c58350d8258a38e84943e3bba82979 Mon Sep 17 00:00:00 2001 From: 134 Date: Tue, 20 Oct 2026 17:42:13 +0800 Subject: [PATCH] fix(canvas-agent): load sandbox host runtime outside web asset tracing --- lib/ai/zcode-agent/native-runtime.ts | 18 ++++++++++++++++++ lib/ai/zcode-agent/task.ts | 3 ++- scripts/zcode-agent/stage-runtime.mjs | 2 ++ services/zcode-agent/README.md | 2 ++ 4 files changed, 24 insertions(+), 1 deletion(-) create mode 100644 lib/ai/zcode-agent/native-runtime.ts diff --git a/lib/ai/zcode-agent/native-runtime.ts b/lib/ai/zcode-agent/native-runtime.ts new file mode 100644 index 000000000..fc3d8bc8e --- /dev/null +++ b/lib/ai/zcode-agent/native-runtime.ts @@ -0,0 +1,18 @@ +import "server-only"; +import { join } from "node:path"; +import { pathToFileURL } from "node:url"; +import type { runNativeZcode as NativeRun } from "@/services/zcode-agent/runner.mjs"; + +/** Load the installed host adapter outside Next's filesystem tracer. Task state + * and native session trees are runtime data, never web build input assets. */ +export const runNativeZcode: typeof NativeRun = async options => { + const root = process.env.CANVAS_ZCODE_RUNTIME_DIR || "/opt/yedir-canvas-zcode/current"; + const url = pathToFileURL(join(/* turbopackIgnore: true */ root, "host/runner.mjs")).href; + let module: { runNativeZcode: typeof NativeRun }; + try { + module = await import(/* webpackIgnore: true */ /* turbopackIgnore: true */ url); + } catch { + throw new Error("原生 ZCode 运行环境尚未正确安装,未启动任务。禁止在宿主直接执行。"); + } + return module.runNativeZcode(options); +}; diff --git a/lib/ai/zcode-agent/task.ts b/lib/ai/zcode-agent/task.ts index 77ae24b63..70df3e760 100644 --- a/lib/ai/zcode-agent/task.ts +++ b/lib/ai/zcode-agent/task.ts @@ -1,7 +1,8 @@ import "server-only"; import { asSchema, type ToolSet } from "ai"; import { join } from "node:path"; -import { runNativeZcode, type NativeEvent, type NativeResult } from "@/services/zcode-agent/runner.mjs"; +import type { NativeEvent, NativeResult } from "@/services/zcode-agent/runner.mjs"; +import { runNativeZcode } from "./native-runtime"; import type { CanvasAgentTool } from "@/lib/ai/canvas-agent-runtime/loop"; import { AgentToolRejectedError, publicAgentError, type AgentRunSnapshot, type CanvasAgentRunStatus } from "@/lib/ai/canvas-agent-runtime/protocol"; diff --git a/scripts/zcode-agent/stage-runtime.mjs b/scripts/zcode-agent/stage-runtime.mjs index 4fdcb86e5..c7aba4e53 100644 --- a/scripts/zcode-agent/stage-runtime.mjs +++ b/scripts/zcode-agent/stage-runtime.mjs @@ -15,6 +15,8 @@ for (const file of ['zcode.cjs', 'THIRD-PARTY-NOTICES.md']) await copyFile(join( await cp(join(built, 'provider'), join(destination, 'provider'), { recursive: true }); await copyFile(join(source, 'LICENSE'), join(destination, 'LICENSE')); await copyFile(resolve('services/zcode-agent/bridge.mjs'), join(destination, 'bridge.mjs')); +await mkdir(join(destination, 'host'), { recursive: true }); +for (const file of ['runner.mjs', 'sandbox.mjs', 'broker.mjs']) await copyFile(resolve('services/zcode-agent', file), join(destination, 'host', file)); // Deployment replaces this development binary with the verified Linux Node 24 // binary. No global Node installation or existing application runtime changes. await copyFile(process.execPath, join(destination, 'bin/node')); await chmod(join(destination, 'bin/node'), 0o755); diff --git a/services/zcode-agent/README.md b/services/zcode-agent/README.md index 29c582fe4..8a48e251a 100644 --- a/services/zcode-agent/README.md +++ b/services/zcode-agent/README.md @@ -62,3 +62,5 @@ canvas, authentication/ownership probes and static-resource checks before switching the active Next build. Current authorization: video canvas and storyboard Agent access is paused by the user. Image canvas and non-video project tools remain authorized; the real project workspace is checked server-side, so forged client mode cannot enable video. Full per-entry audit: authorization-audit.json / authorization-audit.html. + +The installed `host/` adapter is loaded as an external runtime module. Neither task state nor native home/workspace directories are Next build assets; the web bundler must not recursively trace them.