diff --git a/scripts/write-cli-compat.ts b/scripts/write-cli-compat.ts index e9d5b44f58..f818a56ea1 100644 --- a/scripts/write-cli-compat.ts +++ b/scripts/write-cli-compat.ts @@ -51,13 +51,23 @@ if (!resolved?.accessors) { const target = resolved.entry; const relPath = `../${target}`; const { accessors } = resolved; +const missingExportError = (name: string) => + `Legacy daemon CLI export "${name}" is unavailable in this build. Please upgrade OpenClaw.`; +const buildExportLine = (name: (typeof LEGACY_DAEMON_CLI_EXPORTS)[number]) => { + const accessor = accessors[name]; + if (accessor) { + return `export const ${name} = daemonCli.${accessor};`; + } + if (name === "registerDaemonCli") { + return `export const ${name} = () => { throw new Error(${JSON.stringify(missingExportError(name))}); };`; + } + return `export const ${name} = async () => { throw new Error(${JSON.stringify(missingExportError(name))}); };`; +}; const contents = "// Legacy shim for pre-tsdown update-cli imports.\n" + `import * as daemonCli from "${relPath}";\n` + - LEGACY_DAEMON_CLI_EXPORTS.map( - (name) => `export const ${name} = daemonCli.${accessors[name]};`, - ).join("\n") + + LEGACY_DAEMON_CLI_EXPORTS.map(buildExportLine).join("\n") + "\n"; fs.mkdirSync(cliDir, { recursive: true }); diff --git a/src/cli/daemon-cli-compat.test.ts b/src/cli/daemon-cli-compat.test.ts index 46c63014a5..8937933694 100644 --- a/src/cli/daemon-cli-compat.test.ts +++ b/src/cli/daemon-cli-compat.test.ts @@ -25,6 +25,18 @@ describe("resolveLegacyDaemonCliAccessors", () => { export { runDaemonRestart as r, daemon_cli_exports as t }; `; + expect(resolveLegacyDaemonCliAccessors(bundle)).toEqual({ + registerDaemonCli: "t.registerDaemonCli", + runDaemonRestart: "r", + }); + }); + + it("returns null when the required restart alias is missing", () => { + const bundle = ` + var daemon_cli_exports = /* @__PURE__ */ __exportAll({ registerDaemonCli: () => registerDaemonCli }); + export { daemon_cli_exports as t }; + `; + expect(resolveLegacyDaemonCliAccessors(bundle)).toBeNull(); }); }); diff --git a/src/cli/daemon-cli-compat.ts b/src/cli/daemon-cli-compat.ts index 58cd80fd88..b5a217d8f7 100644 --- a/src/cli/daemon-cli-compat.ts +++ b/src/cli/daemon-cli-compat.ts @@ -9,6 +9,12 @@ export const LEGACY_DAEMON_CLI_EXPORTS = [ ] as const; type LegacyDaemonCliExport = (typeof LEGACY_DAEMON_CLI_EXPORTS)[number]; +export type LegacyDaemonCliAccessors = { + registerDaemonCli: string; + runDaemonRestart: string; +} & Partial< + Record, string> +>; const EXPORT_SPEC_RE = /^([A-Za-z_$][\w$]*)(?:\s+as\s+([A-Za-z_$][\w$]*))?$/; const REGISTER_CONTAINER_RE = @@ -48,7 +54,7 @@ function findRegisterContainerSymbol(bundleSource: string): string | null { export function resolveLegacyDaemonCliAccessors( bundleSource: string, -): Record | null { +): LegacyDaemonCliAccessors | null { const aliases = parseExportAliases(bundleSource); if (!aliases) { return null; @@ -64,27 +70,30 @@ export function resolveLegacyDaemonCliAccessors( const runDaemonStatus = aliases.get("runDaemonStatus"); const runDaemonStop = aliases.get("runDaemonStop"); const runDaemonUninstall = aliases.get("runDaemonUninstall"); - if ( - !(registerContainerAlias || registerDirectAlias) || - !runDaemonInstall || - !runDaemonRestart || - !runDaemonStart || - !runDaemonStatus || - !runDaemonStop || - !runDaemonUninstall - ) { + if (!(registerContainerAlias || registerDirectAlias) || !runDaemonRestart) { return null; } - return { + const accessors: LegacyDaemonCliAccessors = { registerDaemonCli: registerContainerAlias ? `${registerContainerAlias}.registerDaemonCli` : registerDirectAlias!, - runDaemonInstall, runDaemonRestart, - runDaemonStart, - runDaemonStatus, - runDaemonStop, - runDaemonUninstall, }; + if (runDaemonInstall) { + accessors.runDaemonInstall = runDaemonInstall; + } + if (runDaemonStart) { + accessors.runDaemonStart = runDaemonStart; + } + if (runDaemonStatus) { + accessors.runDaemonStatus = runDaemonStatus; + } + if (runDaemonStop) { + accessors.runDaemonStop = runDaemonStop; + } + if (runDaemonUninstall) { + accessors.runDaemonUninstall = runDaemonUninstall; + } + return accessors; }