diff --git a/CHANGELOG.md b/CHANGELOG.md index 6e81ec31108..7d686f93e58 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -22,6 +22,7 @@ Docs: https://docs.openclaw.ai - Slack: route handled top-level channel turns in implicit-conversation channels to thread-scoped sessions when Slack reply threading is enabled, keeping the root turn and later thread replies on one OpenClaw session. (#78522) Thanks @zeroth-blip. - Telegram: re-probe the primary fetch transport after repeated sticky fallback success so transient IPv4 or pinned-IP fallback promotion can recover without a gateway restart. Fixes #77088. (#77157) Thanks @MkDev11. - Runtime/install: raise the supported Node 22 floor to `22.16+` so native SQLite query handling can rely on the `node:sqlite` statement metadata API while continuing to recommend Node 24. (#78921) +- Gateway/macOS: include Apple Silicon Homebrew bin directories in generated LaunchAgent PATH and service-audit expectations, so Homebrew Node installs stay resolvable after gateway repair/restart. Fixes #79232. Thanks @TurboTheTurtle. - Discord/voice: make duplicate same-guild auto-join entries resolve to the last configured channel so moving an agent between voice channels does not keep joining the stale channel. - Discord/voice: include a bounded one-line STT transcript preview in verbose voice logs so live voice debugging shows what speakers said before the agent reply. - Codex app-server: pin the managed Codex harness and Codex CLI smoke package to `@openai/codex@0.129.0`, defer OpenClaw integration dynamic tools behind Codex tool search by default, and accept current Codex service-tier values so legacy `fast` settings survive the stable harness upgrade as `priority`. diff --git a/src/daemon/service-audit.test.ts b/src/daemon/service-audit.test.ts index 98e434719bd..b4d3dfe503b 100644 --- a/src/daemon/service-audit.test.ts +++ b/src/daemon/service-audit.test.ts @@ -124,8 +124,10 @@ describe("auditGatewayServiceConfig", () => { it("accepts canonical macOS gateway service PATH without user-bin defaults", async () => { const home = await fs.mkdtemp(path.join(os.tmpdir(), "openclaw-service-audit-home-")); try { - const servicePath = - "/opt/homebrew/bin:/opt/homebrew/sbin:/usr/local/bin:/usr/bin:/bin:/usr/sbin:/sbin"; + const servicePath = buildMinimalServicePath({ platform: "darwin", env: { HOME: home } }); + expect(servicePath).toBe( + "/opt/homebrew/bin:/opt/homebrew/sbin:/usr/local/bin:/usr/bin:/bin:/usr/sbin:/sbin", + ); const audit = await auditGatewayServiceConfig({ env: { HOME: home }, @@ -142,6 +144,28 @@ describe("auditGatewayServiceConfig", () => { } }); + it("requires Homebrew directories in canonical macOS gateway service PATH", async () => { + const home = await fs.mkdtemp(path.join(os.tmpdir(), "openclaw-service-audit-home-")); + try { + const audit = await auditGatewayServiceConfig({ + env: { HOME: home }, + platform: "darwin", + command: { + programArguments: ["/usr/bin/node", "gateway"], + environment: { PATH: "/usr/local/bin:/usr/bin:/bin:/usr/sbin:/sbin" }, + }, + }); + + const issue = audit.issues.find( + (entry) => entry.code === SERVICE_AUDIT_CODES.gatewayPathMissingDirs, + ); + expect(issue?.message).toContain("/opt/homebrew/bin"); + expect(issue?.message).toContain("/opt/homebrew/sbin"); + } finally { + await fs.rm(home, { recursive: true, force: true }); + } + }); + it("still requires explicit env-configured tool roots in gateway service PATH", async () => { const audit = await auditGatewayServiceConfig({ env: { HOME: "/tmp/openclaw-testuser", PNPM_HOME: "/opt/pnpm" },