Files
orca/config/tsconfig.cli.json
T
OrcaWinandOrca Worker 7909732283 perf(claude): run the Windows Claude hook as a signed native claude-hook.exe (#27719)
* perf(claude): run the Windows Claude hook as a native orca-hook.exe

Each Claude hook event on Windows started cmd.exe (plus the user's cmd
AutoRun) and then curl.exe on top of the agent's own shell. A small signed
Rust binary now does the same synchronous POST in one process, under Git
Bash, PowerShell and direct CreateProcess alike.

- native/windows-agent-hook: std-only crate, same contract as the .cmd hook
  (prints {}, env guards before stdin, endpoint re-read, 0.5s/1.5s caps,
  waits for the listener reply, always exit 0). Its installed file name
  selects the agent profile, so the registration stays a bare path.
- Packaged as resources/bin/orca-hook.exe (SignPath signs it with the other
  inner PEs); afterPack fails on a missing or wrong-machine binary.
- Claude install copies it verbatim to ~/.orca/agent-hooks/claude-hook.exe
  (temp + rename, running copy moved aside) and registers it; it falls back
  to the .cmd hook when the bundle is missing, unsigned or cannot be copied.
  Only Claude opts in, via windowsNativeHookExecutable.
- The managed-command matcher sweeps .exe entries alongside .cmd/.ps1/.sh.
- The CLI launcher and hook builds share windows-rust-executable-build.mjs,
  which now also checks the PE machine.

Refs #20913

* fix(build): publish native Windows binaries atomically so parallel builds cannot collide

The Windows CI lane runs every orca-hook.exe suite in one vitest
invocation, each building through build-windows-agent-hook.mjs. The build
copied straight onto native/windows-agent-hook/.build/orca-hook.exe, and
CopyFile opens its destination unshared, so a second build (or a scanner
still holding the fresh image) failed with EBUSY.

- windows-rust-executable-build.mjs skips the publish when the output
  already has the built bytes, otherwise stages a per-process temp file and
  renames it over the output, retrying briefly while another handle holds it.
- The test fixture hands each suite a private copy of the build output, so
  no suite reads or starts the shared file while another build replaces it.

Refs #20913

* refactor(claude): simplify the native Windows hook to one Claude binary

Review follow-up on the native hook (#20913): the same behaviour with less
machinery.

- The binary is built, shipped and installed as claude-hook.exe, so the
  installed name matches its PE OriginalFilename. It is Claude-only, so the
  file-name profile table and the per-agent opt-in flag are gone; the
  registration is gated by the existing Claude-only usesWindowsEntry check.
- Install and refresh reuse writeManagedScript / refreshManagedScriptIfPresent
  (now accepting bytes): temp file, rename, skip when identical. A copy whose
  hook is still running cannot be replaced; install then registers the .cmd
  hook and refresh keeps the old build until a later start, instead of the
  rename-aside and *.retired sweep.
- The install-time Authenticode-presence check is dropped. Release CI now
  requires resources\bin\claude-hook.exe to be signed (release-cut and the
  signing rehearsal), next to resources\bin\orca.exe.
- getStatus counts either Windows form through findManagedEventHookForms in
  hook-settings.ts, replacing managed-event-hook-status.ts.
- Rust: plain Claude constants, one endpoint-file lookup (last assignment
  wins, as under `call`), one request write and a deadline-bounded drain.
  Guard order and form encoding are unchanged.
- Build: PR CI builds the hook once before the Windows tests, so the suites
  only read it; the launcher publish goes back to copyFileSync and the retry
  loop and its test are gone. The PE-machine check lives only in afterPack.
  Cargo.lock joins both crates' build fingerprints, and the launcher's alias
  exports are removed.

Refs #20913

* test(ci): run the managed hook stdin-lifecycle suite in the Windows lane

Its claude-hook.exe case (and the other Windows-only cases) are gated per
test, so the lane-registration guard did not require the file and it ran
only on Linux, where those cases skip. Register it in both Windows lists.

Refs #20913

* feat(agent-hooks): ship the native hook as orca-agent-hook.exe <agent>

The native Windows hook (#20913) becomes one general binary that stays
Claude-only in behaviour.

- Named orca-agent-hook.exe everywhere: build output, PE OriginalFilename
  and InternalName, resources\bin, the afterPack check, the installed copy
  in ~/.orca/agent-hooks, and the release signed-target lists.
- It takes the agent as its first argument and Claude registers
  `<path> claude`. The CLAUDE_JOB_DIR exit and the Grok/Devin drain belong
  to that agent; an unknown or missing agent answers {} without reading
  stdin. The managed-command matcher owns `orca-agent-hook.exe claude` and
  still owns the old claude-hook.exe entry, so installs migrate; install
  deletes a leftover claude-hook.exe when nothing runs it.
- A copy still running from the previous build no longer forces the .cmd
  fallback. Identical bytes are not rewritten; otherwise the temp file is
  renamed over the target, and when Windows refuses because the image is
  mapped, the running copy is renamed to orca-agent-hook.exe.old first.
  Install deletes a stale .old; only when that copy is also still running
  does the install fall back to .cmd. writeManagedScript and
  refreshManagedScriptIfPresent take the aside path, sharing one helper.

Refs #20913

* fix(agent-hooks): roll back a failed aside rename and keep an installed hook exe

Design-review follow-up on the native hook (#20913).

- If the running copy was moved to orca-agent-hook.exe.old but the new
  file then could not take its name, the copy is renamed back before the
  error is rethrown, so settings.json never points at a missing exe. The
  rename helper now owns the `.old` name, next to the comment that
  explains it; a mocked-fs unit test covers both the sync and async paths.
- A failed write, or a build with no bundled exe, keeps registering a copy
  that is already installed (every build knows `claude`), so a dev checkout
  and an installed build no longer flip settings.json between forms.
- The claude-hook.exe migration is gone: no release ever shipped that
  name, so the legacy sweep, the `.exe` matcher needle and their test are
  removed.

Refs #20913

* fix(agent-hooks): derive the native hook's agent with win32 path rules

getWindowsNativeHookAgent took the host's basename of the managed script
path, so on a POSIX host (Linux CI) a Windows path was not split and the
registered command became `orca-agent-hook.exe C:\...\claude`. It now takes
the path and applies path.win32.basename itself. The install destination
and the `.old` aside stay on host paths: they name files the host opens.

Refs #20913

---------

Co-authored-by: Orca Worker <orca-worker@localhost>
2026-10-12 16:09:30 -07:00

303 lines
17 KiB
JSON

{
"extends": "@electron-toolkit/tsconfig/tsconfig.node.json",
"include": [
"../src/cli/**/*",
"../src/shared/**/*",
"../src/packages/process-host/src/__fixtures__/**/*",
"../src/main/agent-state-file-reader.ts",
"../src/main/gitlab/project-ref-parser.ts",
"../src/main/agent-hooks/grok-replay-guard.ts",
"../src/main/claude/hook-script.ts",
"../src/main/claude/claude-hook-event-versions.ts",
"../src/main/claude/claude-managed-hook-events.ts",
"../src/main/qoder/hook-service.ts",
"../src/main/qwen-code/hook-service.ts",
"../src/main/codebuddy/hook-service.ts",
"../src/main/agent-hooks/hook-stdin-contract.ts",
"../src/main/agent-hooks/hook-post-command.ts",
"../src/main/agent-hooks/hook-process-capture.ts",
"../src/main/agent-hooks/hook-config-write-path.ts",
"../src/main/agent-hooks/hooks-json-read.ts",
"../src/main/agent-hooks/installer-utils.ts",
"../src/main/agent-hooks/installer-utils-remote.ts",
"../src/main/agent-hooks/local-agent-cli-presence.ts",
"../src/main/agent-hooks/managed-toml-ownership.ts",
"../src/main/agent-hooks/managed-agent-hook-controls.ts",
"../src/main/agent-hooks/managed-agent-hook-registry.ts",
"../src/main/agent-hooks/managed-hook-script-refresh.ts",
"../src/main/agent-hooks/managed-hooks-json-events.ts",
"../src/main/agent-hooks/posix-hook-command.ts",
"../src/main/agent-hooks/runtime-home-hook-command.ts",
"../src/main/orca-profiles/profile-storage-paths.ts",
"../src/main/orca-profiles/profile-index-store.ts",
"../src/main/orca-profiles/profile-telemetry-consent-seed.ts",
"../src/main/orca-profiles/profile-legacy-state-import.ts",
"../src/main/persistence/profile-state/profile-state-migration.ts",
"../src/main/persistence/profile-state/profile-state-database-publication.ts",
"../src/main/persistence/profile-state/profile-state-authority-marker.ts",
"../src/main/persistence/profile-state/profile-state-database.ts",
"../src/main/persistence/profile-state/profile-state-database-errors.ts",
"../src/main/persistence/profile-state/profile-state-database-validation.ts",
"../src/main/persistence/profile-state/profile-state-database-schema.ts",
"../src/main/persistence/profile-state/profile-state-documents.ts",
"../src/main/persistence/profile-state/legacy-json/profile-state-json-acceptance.ts",
"../src/main/persistence/profile-state/profile-state-revision.ts",
"../src/main/persistence/profile-state/profile-state-read-snapshot.ts",
"../src/main/persistence/profile-state/profile-state-sqlite-authority.ts",
"../src/main/persistence/profile-state/legacy-json/profile-state-authority-exports.ts",
"../src/main/persistence/profile-state/profile-state-complete-replacements.ts",
"../src/main/persistence/profile-state/profile-state-revision-readmission.ts",
"../src/main/persistence/profile-state/profile-state-writer-protocol.ts",
"../src/main/persistence/loading-store/profile-state-authority.ts",
"../src/main/persistence/profile-state/profile-state-automation-runs-migration.ts",
"../src/main/persistence/profile-state/profile-state-document-reader.ts",
"../src/main/persistence/profile-state/profile-state-document-validation.ts",
"../src/main/persistence/profile-state/profile-state-domain-writes.ts",
"../src/main/persistence/profile-state/profile-state-write-transaction.ts",
"../src/main/persistence/profile-state/profile-state-domain-write-validation.ts",
"../src/main/persistence/profile-state/profile-state-domain-reader.ts",
"../src/main/persistence/profile-state/profile-state-automation-runs.ts",
"../src/main/persistence/profile-state/profile-state-automation-runs-model.ts",
"../src/main/persistence/profile-state/profile-state-automation-runs-payload.ts",
"../src/main/persistence/profile-state/profile-state-automation-runs-reader.ts",
"../src/main/persistence/profile-state/profile-state-automation-runs-storage.ts",
"../src/main/persistence/profile-state/profile-state-automation-runs-validation.ts",
"../src/main/persistence/profile-state/profile-state-automation-runs-writer.ts",
"../src/main/persistence/profile-state/profile-state-offline-settings.ts",
"../src/main/persistence/profile-state/legacy-json/profile-state-export-path.ts",
"../src/main/persistence/profile-state/legacy-json/profile-state-legacy-backup-path.ts",
"../src/main/persistence/profile-state/profile-state-backup-path.ts",
"../src/main/persistence/profile-state/profile-state-backup-rotation.ts",
"../src/main/persistence/profile-state/profile-state-backup-job.ts",
"../src/main/persistence/profile-state/profile-state-backup-worker.ts",
"../src/main/persistence/profile-state/profile-state-backup-worker-entry.ts",
"../src/main/worker-thread-entry-path.ts",
"../src/main/persistence/profile-state/profile-state-database-snapshot.ts",
"../src/main/persistence/profile-state/profile-state-database-recovery.ts",
"../src/main/persistence/profile-state/profile-state-recovery-required.ts",
"../src/main/persistence/profile-state/legacy-json/profile-state-recovery.ts",
"../src/main/persistence/profile-state/profile-state-recovery-copy.ts",
"../src/main/persistence/profile-state/profile-state-recovery-command.ts",
"../src/main/orca-profiles/profile-project-move-record.ts",
"../src/main/orca-profiles/profile-project-domain-changes.ts",
"../src/main/persistence/profile-state/profile-state-active-location.ts",
"../src/main/persistence/profile-state/profile-state-access.ts",
"../src/main/persistence/profile-state/profile-state-access-owner.ts",
"../src/main/persistence/profile-state/profile-state-access-identity.ts",
"../src/main/windows-native-registry.ts",
"../src/main/windows/windows-command-line-recovery-health.ts",
"../src/main/windows/windows-process-table.ts",
"../src/main/windows/windows-pty-job.ts",
"../src/main/crash-reporting/crash-breadcrumb-store.ts",
"../src/main/crash-reporting/durable-crash-breadcrumb.ts",
"../src/main/crash-reporting/main-process-lifecycle-identity.ts",
"../src/main/crash-reporting/self-initiated-tree-kill-log.ts",
"../src/main/observability/redactor.ts",
"../src/main/observability/tracer.ts",
"../src/main/orca-chromium-process-pids.ts",
"../src/main/own-chromium-tree-kill-guard.ts",
"../src/main/providers/windows-foreground-process-rows.ts",
"../src/main/pty-descendant-exit-verification.ts",
"../src/main/pty-descendant-termination.ts",
"../src/main/pty-process-table-parser.ts",
"../src/main/windows-process-tree-kill.ts",
"../src/main/windows-pty-root-identity.ts",
"../src/main/windows/windows-process-table-cim-scan.ts",
"../src/main/windows/windows-process-table-timeout-error.ts",
"../src/main/daemon/daemon-process-start-time.ts",
"../src/main/daemon/daemon-process-identity-query.ts",
"../src/main/startup/startup-diagnostics.ts",
"../src/main/persistence/profile-state/legacy-json/profile-state-versioned-export.ts",
"../src/main/persistence/profile-state/profile-state-backup-temporary-files.ts",
"../src/main/persistence/profile-state/profile-state-database-quarantine.ts",
"../src/main/persistence/profile-state/profile-state-storage-classification.ts",
"../src/main/durable-file-write.ts",
"../src/shared/secure-file.ts",
"../src/main/sqlite/harden-database-files.ts",
"../src/main/startup/http1-compatibility-marker.ts",
"../src/main/startup/http1-compatibility-profile-state.ts",
"../src/main/agent-hooks/windows-direct-cmd-hook-command.ts",
"../src/main/agent-hooks/windows-hook-command.ts",
"../src/main/agent-hooks/windows-powershell-hook-launcher.ts",
"../src/main/amp/agent-status-plugin-source.ts",
"../src/main/amp/hook-service.ts",
"../src/main/amp/managed-plugin-install-status.ts",
"../src/main/antigravity/hook-events.ts",
"../src/main/antigravity/hook-script.ts",
"../src/main/antigravity/windows-hook-json-post.ts",
"../src/main/antigravity/hook-service.ts",
"../src/main/antigravity/hooks-json-bundle.ts",
"../src/main/claude/hook-settings.ts",
"../src/main/claude/hook-service.ts",
"../src/main/claude/claude-profile-hook-target.ts",
"../src/main/claude/statusline-script.ts",
"../src/main/claude/windows-hook-files.ts",
"../src/main/agent-hooks/windows-native-hook-executable.ts",
"../src/main/agent-hooks/locked-executable-rename.ts",
"../src/main/claude-accounts/keychain.ts",
"../src/main/macos-keychain/generic-password.ts",
"../src/main/codex/codex-app-server-capability-cache.ts",
"../src/main/codex/codex-app-server-capability-signal.ts",
"../src/main/codex/codex-app-server-client.ts",
"../src/main/codex/codex-app-server-process-tree-kill.ts",
"../src/main/provider-process/provider-record-reader.ts",
"../src/main/codex/codex-app-server-session.ts",
"../src/main/codex/codex-config-mirror.ts",
"../src/main/codex/codex-config-mirror-merge.ts",
"../src/main/codex/codex-config-path-reference-rewrite.ts",
"../src/main/codex/codex-config-settings-preservation.ts",
"../src/main/codex/codex-config-settings-removal.ts",
"../src/main/codex/codex-config-settings-upsert.ts",
"../src/main/codex/codex-daemon-socket-path-guard.ts",
"../src/main/codex/codex-home-paths.ts",
"../src/main/codex/codex-hook-command-form.ts",
"../src/main/codex/codex-hook-definition.ts",
"../src/main/codex/codex-managed-home-resource-copy-marker.ts",
"../src/main/codex/codex-managed-trust-grant-plan.ts",
"../src/main/codex/codex-path-observation.ts",
"../src/main/codex/codex-hook-identity.ts",
"../src/main/codex/codex-hook-legacy-cleanup.ts",
"../src/main/codex/codex-hook-local-install.ts",
"../src/main/codex/codex-hook-orca-approvals.ts",
"../src/main/codex/codex-hook-approval-first-write.ts",
"../src/main/codex/codex-hook-hash-lookup.ts",
"../src/main/codex/codex-hook-trust-derivation.ts",
"../src/main/codex/codex-hook-trust-memo.ts",
"../src/main/codex/codex-hook-reconcile.ts",
"../src/main/codex/codex-hook-local-maintenance.ts",
"../src/main/codex/codex-hook-remote-install.ts",
"../src/main/codex/codex-hook-script.ts",
"../src/main/codex/codex-hook-service-implementation.ts",
"../src/main/codex/codex-hook-status.ts",
"../src/main/codex/codex-hook-system-trust.ts",
"../src/main/codex/codex-hook-trust-cleanup.ts",
"../src/main/codex/codex-hook-trust-grant.ts",
"../src/main/codex/codex-hook-trust-queue.ts",
"../src/main/codex/codex-hook-user-mirroring.ts",
"../src/main/codex/codex-hook-retired-commands.ts",
"../src/main/codex/codex-hook-wsl-runtime.ts",
"../src/main/codex/codex-managed-trust-reconciliation.ts",
"../src/main/provider-process/provider-process-exit-deadline.ts",
"../src/main/provider-process/managed-provider-process.ts",
"../src/main/provider-process/provider-executable-missing.ts",
"../src/main/provider-process/provider-process-close.ts",
"../src/main/provider-process/provider-process-launch.ts",
"../src/main/provider-process/provider-process-supervisor.ts",
"../src/main/provider-process/provider-process-teardown.ts",
"../src/main/provider-process/provider-spawn-failure-report.ts",
"../src/main/codex/codex-real-home-hook-entry-plan.ts",
"../src/main/codex/codex-real-home-hook-install.ts",
"../src/main/codex/codex-real-home-hook-sweep.ts",
"../src/main/codex/codex-real-home-hooks-json.ts",
"../src/main/codex/codex-state-db.ts",
"../src/main/codex/codex-trust-identity.ts",
"../src/main/codex/codex-trust-config-mutation-queue.ts",
"../src/main/codex/codex-trust-grant-telemetry.ts",
"../src/main/codex/codex-trust-grant-host.ts",
"../src/main/codex/codex-trust-grant-cooldown.ts",
"../src/main/codex/codex-trust-grant-ledger.ts",
"../src/main/codex/codex-user-hook-trust-moves.ts",
"../src/main/codex/codex-wsl-hook-install-plan.ts",
"../src/main/codex/config-settings-baseline.ts",
"../src/main/codex/config-settings-conflict-resolution.ts",
"../src/main/codex/config-plugin-registration-promotion.ts",
"../src/main/codex/config-toml-plugin-registration-tables.ts",
"../src/main/codex/config-toml-promoted-setting-values.ts",
"../src/main/codex/config-settings-promotion.ts",
"../src/main/codex/config-settings-promotion-write-target.ts",
"../src/main/codex/config-sync-stall.ts",
"../src/main/codex/config-toml-atomic-write.ts",
"../src/main/codex/config-toml-deprecated-hook-flag.ts",
"../src/main/codex/config-toml-hook-trust-blocks.ts",
"../src/main/codex/config-toml-hook-trust-edit.ts",
"../src/main/codex/config-toml-hook-trust-read.ts",
"../src/main/codex/config-toml-key-path.ts",
"../src/main/codex/config-toml-line-scan.ts",
"../src/main/codex/config-toml-mcp-servers.ts",
"../src/main/codex/config-toml-project-trust.ts",
"../src/main/codex/config-toml-project-trust-level.ts",
"../src/main/codex/config-toml-project-duplicate-repair.ts",
"../src/main/codex/config-toml-runtime-owned-sections.ts",
"../src/main/codex/config-toml-syntax.ts",
"../src/main/codex/config-toml-trust.ts",
"../src/main/codex/hook-service.ts",
"../src/main/codex/hook-trust-promotion.ts",
"../src/main/codex-accounts/fs-utils.ts",
"../src/main/codex-accounts/wsl-codex-command.ts",
"../src/main/codex-cli/command.ts",
"../src/main/codex-cli/codex-read-only-app-server-args.ts",
"../src/main/command-code/command-code-managed-script.ts",
"../src/main/command-code/hook-service.ts",
"../src/main/copilot/copilot-managed-hook-definitions.ts",
"../src/main/copilot/copilot-managed-script.ts",
"../src/main/copilot/copilot-remote-hook-install.ts",
"../src/main/copilot/hook-service.ts",
"../src/main/cursor/hook-events.ts",
"../src/main/cursor/hook-script.ts",
"../src/main/cursor/hook-service.ts",
"../src/main/droid/hook-service.ts",
"../src/main/gemini/hook-service.ts",
"../src/main/grok/grok-hook-config.ts",
"../src/main/grok/grok-hook-config-cleanup.ts",
"../src/main/grok/grok-hook-config-file.ts",
"../src/main/grok/grok-hook-owners.ts",
"../src/main/grok/grok-hook-remote-install.ts",
"../src/main/grok/grok-hook-script.ts",
"../src/main/grok/grok-hook-symlink-cleanup-marker.ts",
"../src/main/grok/hook-service.ts",
"../src/main/grok/windows-grok-hook-script.ts",
"../src/main/devin/hook-settings.ts",
"../src/main/devin/hook-service.ts",
"../src/main/devin/hook-config-json.ts",
"../src/main/hermes/hermes-config-document.ts",
"../src/main/hermes/hermes-config-source-edits.ts",
"../src/main/hermes/hermes-config-yaml.ts",
"../src/main/hermes/hermes-home-filesystem.ts",
"../src/main/hermes/hermes-managed-plugin-source.ts",
"../src/main/hermes/hook-service.ts",
"../src/main/git-bash.ts",
"../src/main/in-flight-run-dedupe.ts",
"../src/main/jcode/hook-settings.ts",
"../src/main/jcode/hook-config.ts",
"../src/main/jcode/hook-service.ts",
"../src/main/kimi/hook-service.ts",
"../src/main/kimi/kimi-hook-config-toml.ts",
"../src/main/kiro/hook-service.ts",
"../src/main/kiro/hook-settings.ts",
"../src/main/dsh/dsh-home-patch.ts",
"../src/main/dsh/hook-service.ts",
"../src/main/dsh/hook-settings.ts",
"../src/main/muse/hook-config-json.ts",
"../src/main/muse/hook-service.ts",
"../src/main/muse/hook-settings.ts",
"../src/main/zcode/hook-config-json.ts",
"../src/main/zcode/hook-service.ts",
"../src/main/zcode/hook-settings.ts",
"../src/main/openclaude/hook-service.ts",
"../src/main/rolling-file-backup.ts",
"../src/main/startup/hydrate-shell-path.ts",
"../src/main/startup/shell-path-probe.ts",
"../src/main/startup/windows-shell-path-ownership.ts",
// Why: serve-electron-flag-parity.test.ts checks the Electron-side serve argv rewrite against this
// project's serve spec; the module has no imports, so listing it pulls in nothing else.
"../src/main/startup/serve-mode-argv.ts",
// The parity test keeps this import-free list aligned with COMMAND_SPECS.
"../src/main/startup/cli-command-names.ts",
"../src/main/runtime/runtime-metadata.ts",
"../src/main/sqlite/sync-database.ts",
"../src/main/sqlite/sqlite-statement.ts",
"../src/main/sqlite/sqlite-integer-reader.ts",
"../src/main/sqlite/node-sqlite-reader-api.ts",
"../src/main/sqlite/node-sqlite-statement.ts",
"../src/main/win32-utils.ts"
],
"compilerOptions": {
"composite": true,
// The CLI runs on Node 24; Node20 models synchronous ESM imports from CommonJS.
"module": "Node20",
"moduleResolution": "Node16",
"rootDir": "../src",
"outDir": "../out"
}
}