




















@@ -94,11 +94,14 @@ interface MacosSummary {
9494}
95959696const guestPath =
97-"/opt/homebrew/bin:/opt/homebrew/opt/node/bin:/opt/homebrew/sbin:/usr/bin:/bin:/usr/sbin:/sbin";
98-const guestOpenClaw = "/opt/homebrew/bin/openclaw";
99-const guestOpenClawEntry = "/opt/homebrew/lib/node_modules/openclaw/openclaw.mjs";
100-const guestNode = "/opt/homebrew/bin/node";
101-const guestNpm = "/opt/homebrew/bin/npm";
97+"/opt/homebrew/bin:/opt/homebrew/opt/node/bin:/usr/local/bin:/usr/local/sbin:/opt/homebrew/sbin:/usr/bin:/bin:/usr/sbin:/sbin";
98+const guestOpenClaw = "openclaw";
99+const guestOpenClawEntry = '"$(npm root -g)/openclaw/openclaw.mjs"';
100+const guestOpenClawEntryRunner = `node ${guestOpenClawEntry}`;
101+const guestOpenClawEntryExecScript =
102+'entry="$(npm root -g)/openclaw/openclaw.mjs"; exec node "$entry" "$@"';
103+const guestNode = "node";
104+const guestNpm = "npm";
102105103106const defaultOptions = (): MacosOptions => ({
104107discordChannelId: undefined,
@@ -576,6 +579,16 @@ class MacosSmoke {
576579return this.guest.exec(args, options);
577580}
578581582+private guestOpenClawEntryExec(
583+args: string[],
584+options: { check?: boolean; env?: Record<string, string> } = {},
585+): string {
586+return this.guestExec(
587+["/bin/sh", "-c", guestOpenClawEntryExecScript, "openclaw-entry", ...args],
588+options,
589+);
590+}
591+579592private guestSh(script: string, env: Record<string, string> = {}): string {
580593return this.guest.sh(script, env);
581594}
@@ -790,7 +803,7 @@ ${guestOpenClaw} --version`);
790803791804private verifyBundlePermissions(): void {
792805this.guestSh(String.raw`set -eu
793-root=$(/opt/homebrew/bin/npm root -g)
806+root=$(npm root -g)
794807check_path() {
795808 path="$1"
796809 [ -e "$path" ] || return 0
@@ -852,7 +865,7 @@ fi
852865echo "bootstrap-pnpm: install"
853866rm -rf "$bootstrap_root"
854867mkdir -p "$bootstrap_root"
855-/opt/homebrew/bin/node /opt/homebrew/bin/npm install --prefix "$bootstrap_root" --no-save pnpm@11
868+npm install --prefix "$bootstrap_root" --no-save pnpm@11
856869"$bootstrap_bin/pnpm" --version`);
857870}
858871@@ -871,14 +884,14 @@ const config = JSON.parse(fs.readFileSync(configPath, "utf8"));
871884config.update = { ...(config.update || {}), channel: "dev" };
872885fs.writeFileSync(configPath, JSON.stringify(config, null, 2) + "\\n");
873886JS
874-/usr/bin/env NODE_OPTIONS=--max-old-space-size=8192 OPENCLAW_ALLOW_OLDER_BINARY_DESTRUCTIVE_ACTIONS=1 OPENCLAW_DISABLE_BUNDLED_PLUGINS=1 ${guestNode} ${guestOpenClawEntry} update --channel dev --yes --json
875-${guestNode} ${guestOpenClawEntry} --version
876-${guestNode} ${guestOpenClawEntry} update status --json`,
887+/usr/bin/env NODE_OPTIONS=--max-old-space-size=8192 OPENCLAW_ALLOW_OLDER_BINARY_DESTRUCTIVE_ACTIONS=1 OPENCLAW_DISABLE_BUNDLED_PLUGINS=1 ${guestOpenClawEntryRunner} update --channel dev --yes --json
888+${guestOpenClawEntryRunner} --version
889+${guestOpenClawEntryRunner} update status --json`,
877890);
878891}
879892880893private verifyDevChannelUpdate(): void {
881-const status = this.guestExec([guestNode, guestOpenClawEntry, "update", "status", "--json"]);
894+const status = this.guestOpenClawEntryExec(["update", "status", "--json"]);
882895for (const needle of ['"installKind": "git"', '"value": "dev"', '"branch": "main"']) {
883896if (!status.includes(needle)) {
884897throw new Error(`dev update status missing ${needle}`);
@@ -901,7 +914,7 @@ trap '' HUP
901914 `${this.auth.apiKeyEnv}=${this.auth.apiKeyValue}`,
902915 )} OPENCLAW_HOME=${shellQuote(home)} OPENCLAW_STATE_DIR=${shellQuote(`${home}/.openclaw`)} OPENCLAW_CONFIG_PATH=${shellQuote(
903916 `${home}/.openclaw/openclaw.json`,
904- )} ${guestNode} ${guestOpenClawEntry} gateway run --bind loopback --port 18789 --force </dev/null >/tmp/openclaw-parallels-macos-gateway.log 2>&1 &
917+ )} ${guestOpenClawEntryRunner} gateway run --bind loopback --port 18789 --force </dev/null >/tmp/openclaw-parallels-macos-gateway.log 2>&1 &
905918sleep 1`,
906919);
907920}
@@ -990,28 +1003,24 @@ exit 1`);
9901003}
99110049921005private verifyTurn(): void {
993-this.guestExec([guestNode, guestOpenClawEntry, "models", "set", this.auth.modelId]);
1006+this.guestOpenClawEntryExec(["models", "set", this.auth.modelId]);
9941007const modelProviderConfigBatch = modelProviderConfigBatchJson(this.auth.modelId, "macos");
9951008if (modelProviderConfigBatch) {
9961009this.guestSh(`provider_config_batch="$(mktemp)"
9971010cat >"$provider_config_batch" <<'JSON'
9981011${modelProviderConfigBatch}
9991012JSON
1000-${shellQuote(guestNode)} ${shellQuote(
1001- guestOpenClawEntry,
1002- )} config set --batch-file "$provider_config_batch" --strict-json
1013+${guestOpenClawEntryRunner} config set --batch-file "$provider_config_batch" --strict-json
10031014rm -f "$provider_config_batch"`);
10041015}
1005-this.guestExec([
1006-guestNode,
1007-guestOpenClawEntry,
1016+this.guestOpenClawEntryExec([
10081017"config",
10091018"set",
10101019"agents.defaults.skipBootstrap",
10111020"true",
10121021"--strict-json",
10131022]);
1014-this.guestExec([guestNode, guestOpenClawEntry, "config", "set", "tools.profile", "minimal"]);
1023+this.guestOpenClawEntryExec(["config", "set", "tools.profile", "minimal"]);
10151024this.restrictAgentTurnPlugins();
10161025this.guestSh(
10171026`${posixAgentWorkspaceScript("Parallels macOS smoke test assistant.")}
@@ -1022,7 +1031,7 @@ for attempt in 1 2; do
10221031 rm -f "$HOME/.openclaw/agents/main/sessions/$session_id.jsonl"
10231032 output_file="$(mktemp)"
10241033 set +e
1025- /usr/bin/env ${shellQuote(`${this.auth.apiKeyEnv}=${this.auth.apiKeyValue}`)} ${guestNode} ${guestOpenClawEntry} agent --local --agent main --session-id "$session_id" --message ${shellQuote(
1034+ /usr/bin/env ${shellQuote(`${this.auth.apiKeyEnv}=${this.auth.apiKeyValue}`)} ${guestOpenClawEntryRunner} agent --local --agent main --session-id "$session_id" --message ${shellQuote(
10261035 "Reply with exact ASCII text OK only.",
10271036 )} --thinking off --timeout ${resolveParallelsModelTimeoutSeconds("macos")} --json >"$output_file" 2>&1
10281037 rc=$?
此内容由惯性聚合(RSS阅读器)自动聚合整理,仅供阅读参考。 原文来自 — 版权归原作者所有。