Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
218 commits
Select commit Hold shift + click to select a range
7f2ba67
fix: wait for OpenCode worker composer before first dispatch
nwparker Oct 2, 2026
76b1a90
chore(deps): update reviewed dependencies across Orca (#24561)
nwparker Oct 2, 2026
700d4de
fix(antigravity): discover global skills from the CLI configuration r…
nwparker Oct 2, 2026
b45f403
fix(antigravity): keep quota probes free and visible without Gemini O…
nwparker Oct 2, 2026
92d2b71
fix(antigravity): launch POSIX hooks through sh with bounded JSON std…
nwparker Oct 2, 2026
0f167ac
test: check plugin fixture worktree cleanup (#24779)
nwparker Oct 2, 2026
4d2f235
fix(files): ignore nested generated directories on macOS (#24620)
nwparker Oct 2, 2026
5706d14
Check E2E packages where the installer reads them (#24785)
nwparker Oct 2, 2026
ddcc279
Preserve Mermaid exports through mobile bundling (#24661)
nwparker Oct 2, 2026
1fc24d3
Update README downloads badge
github-actions[bot] Oct 2, 2026
e2f2b70
ci: skip installed glibc tools in SSH host qualification (#24733)
nwparker Oct 2, 2026
de8bffe
Fix terminal width cutoff on wide panes (#24687)
nwparker Oct 2, 2026
caa4228
fix(runtime): report an open agent question as blocked to tui-idle wa…
Jinwoo-H Oct 2, 2026
4ea6673
fix(runtime): read Codex's 'Implement this plan?' menu as blocked (#2…
Jinwoo-H Oct 2, 2026
564f4d0
feat: live updates for agent state rules (#24387)
Jinwoo-H Oct 2, 2026
9503f9d
fix(runtime): settle Codex tui-idle waits on its hook done, leaving w…
Jinwoo-H Oct 2, 2026
b3f39ee
fix(release): accept the build identity as a later declarator in the …
Jinwoo-H Oct 2, 2026
bdab91e
fix(windows): link the CLI launcher's C runtime statically so orca.ex…
Jinwoo-H Oct 2, 2026
1e600a8
feat(terminal): point an old terminal's Codex shared-server banner at…
Jinwoo-H Oct 2, 2026
0f91540
fix(filesystem): deleting a workspace no longer fails as 'outside all…
brennanb2025 Oct 2, 2026
f2257ff
fix: dismiss Codex account prompt and return focus to terminal (#24683)
nwparker Oct 2, 2026
d6d2795
chore(worktree): include create timing and spare outcome in the works…
brennanb2025 Oct 2, 2026
d3e5923
ci(release): skip the orcad template for tags that predate it (#24872)
Jinwoo-H Oct 2, 2026
44a2ee5
fix(runtime): make OMP 18.4 workers ready at the composer and keep st…
brennanb2025 Oct 2, 2026
1913d27
fix(files): replace watcher subscriptions after native failure (#24723)
nwparker Oct 2, 2026
5f1dece
fix(files): retry failed shallow directory watch replacement (#24724)
nwparker Oct 2, 2026
9273b5f
fix(git): share pending watcher reconciliation startup (#24725)
nwparker Oct 2, 2026
ac28e8c
Skip dependency installation for known headless build inputs (#24716)
nwparker Oct 2, 2026
b94c75c
Reuse pnpm verification records in Alpine CI (#24817)
nwparker Oct 2, 2026
cc73c8e
ci: overlap ARM SSH setup and independent observation waits (#24714)
nwparker Oct 2, 2026
b4ff7fe
fix(tests): run watcher crash harness against current code (#24705)
nwparker Oct 2, 2026
d3a406f
ci(release): publish after a skipped orcad template (#24882)
Jinwoo-H Oct 2, 2026
61836f6
Reduce scheduled CI cache warming to every six hours (#24881)
nwparker Oct 2, 2026
75be95f
ci: move ARM Mac qualification to macOS 15 (#24760)
nwparker Oct 2, 2026
57c786a
fix(files): keep watcher streams across SSH reconnect races (#24722)
nwparker Oct 2, 2026
1aa0860
Keep large Markdown previews responsive (#24880)
nwparker Oct 2, 2026
add1c55
Skip slower Windows root package-store restores in CI (#24885)
nwparker Oct 2, 2026
1f8570e
Advance full shutdown deadlines in mocked Codex connection tests (#24…
nwparker Oct 2, 2026
d88d28a
fix(plugins): restore development watchers after folder replacement (…
nwparker Oct 2, 2026
13ce9a7
fix(watchers): preserve directory identities when checking replacemen…
nwparker Oct 2, 2026
a1da632
fix(opencode-go): don't fall back to OPENCODE_API_KEY when the creden…
Jinwoo-H Oct 2, 2026
a8ee94d
fix(codex): skip the hook trust RPC when Codex's session index is unr…
Jinwoo-H Oct 2, 2026
f8a31ed
refactor(cursor): move the desktop-login read onto the shared foreign…
Jinwoo-H Oct 2, 2026
58cf72d
Skip slower root package-store restores in Linux PR jobs (#24896)
nwparker Oct 2, 2026
58d0e99
test: advance mocked Claude child exit deadlines (#24897)
nwparker Oct 2, 2026
3fba195
perf(tab-bar): a change to one tab no longer re-renders every tab (#2…
AmoabaKelvin Oct 2, 2026
a824fb7
Reuse the headless detector compiler without installing full dependen…
nwparker Oct 2, 2026
533446d
Stop mocked renderer imports from qualifying headless CI (#24902)
nwparker Oct 2, 2026
b06f40f
fix(opencode): read the binder's session store off the main thread; s…
Jinwoo-H Oct 2, 2026
40e60b7
refactor(ai-vault): delete the unused session-scanner worker thread (…
Jinwoo-H Oct 2, 2026
1241ce1
Skip slower root package-store restores in macOS PR jobs (#24908)
nwparker Oct 3, 2026
75f8f34
Overlap independent Linux headless runtime builds (#24910)
nwparker Oct 3, 2026
65deb4b
test(persistence): wait for real worker readiness before timeout (#24…
nwparker Oct 3, 2026
f97ca2a
Add Qoder session history and search (#24614)
nwparker Oct 3, 2026
00da8e1
fix(cursor): show the primary model pool in compact usage (#24830)
nwparker Oct 3, 2026
56427f1
fix(native-chat): one ordered journal writer (#24127)
brennanb2025 Oct 3, 2026
de77c4b
fix(worktrees): list a folder once when git reports it twice (#24357)
AmoabaKelvin Oct 3, 2026
94b4116
Bound AI Vault cache loading and keep atomic saves responsive (#24789)
nwparker Oct 3, 2026
1d5d02e
Resolve explicitly configured command aliases for workers (#24648)
nwparker Oct 3, 2026
e80b550
Cancel the journal import test sampler before database teardown (#24767)
nwparker Oct 3, 2026
bdaeb6c
fix(antigravity): bound Windows hook stdin on the owning runtime (#24…
nwparker Oct 3, 2026
9e27050
Add verified native Antigravity Accounts on the owning runtime (#24691)
nwparker Oct 3, 2026
b5869ee
fix(worktrees): a worktree delete git fails partway stays listed and …
brennanb2025 Oct 3, 2026
2c2dfd0
test: run committed OpenCode redraw capture replay (#24811)
nwparker Oct 3, 2026
328caa2
fix(git): reduce queries and preserve data across execution hosts (#2…
nwparker Oct 3, 2026
c99b202
Use released table parser fix and remove redundant preview work (#24919)
nwparker Oct 3, 2026
3793c58
fix(mobile): release notification and account streams from the transp…
brennanb2025 Oct 3, 2026
603af90
fix(browser): avoid a redundant copy of document preview bytes (#24861)
OrcaWin Oct 3, 2026
613944b
fix(browser): release upload buffers after native staging (#24869)
OrcaWin Oct 3, 2026
501ad0e
fix(editor): release Markdown selection listeners after close (#24875)
OrcaWin Oct 3, 2026
a3524c5
fix(browser): release obsolete state during close replay (#24892)
OrcaWin Oct 3, 2026
aeba62a
fix(journal): encode only the retained tool-output preview (#24696)
OrcaWin Oct 3, 2026
f690319
fix(ssh): release response chunks after the sink accepts them (#24719)
OrcaWin Oct 3, 2026
e1c5232
fix(codex): release full messages behind completed child previews (#2…
OrcaWin Oct 3, 2026
7f388b7
fix(mobile): avoid backtick match arrays when editing Markdown (#24778)
OrcaWin Oct 3, 2026
233f049
fix(editor): avoid newline match arrays when saving LF Markdown (#24795)
OrcaWin Oct 3, 2026
2e9ab41
fix(terminal): cancel viewport retries when panes close (#24745)
OrcaWin Oct 3, 2026
7f12b29
fix(chat): encode only the retained prefix when streamed output overf…
OrcaWin Oct 3, 2026
467ed33
fix(reconnect): release obsolete app state held by handle-gap watcher…
OrcaWin Oct 3, 2026
e0f4adb
fix(activity): release unrelated editor state during the Undo window …
OrcaWin Oct 3, 2026
192fb8f
fix(chat): let idle session readers release retired journal folds (#2…
OrcaWin Oct 3, 2026
b805b77
fix(automations): release unused run output from dashboard rows (#24847)
OrcaWin Oct 3, 2026
709d9bf
fix(notebook): cancel kernel starts when the notebook closes (#24858)
OrcaWin Oct 3, 2026
5e5a992
fix(markdown): reduce Find memory for ordinary text (#24635)
OrcaWin Oct 3, 2026
7e0db0e
fix(clipboard): decode uploaded images without joining all chunks (#2…
OrcaWin Oct 3, 2026
5c52dce
fix(mobile): release file previews after their tabs close (#24655)
OrcaWin Oct 3, 2026
d9a3d3c
fix(editor): expire saved-file snapshots while the editor is idle (#2…
OrcaWin Oct 3, 2026
74609c6
fix(ai-vault): bound transcript text before joining message blocks (#…
OrcaWin Oct 3, 2026
b457583
fix(terminal): release retired status sources from the agent type cac…
OrcaWin Oct 3, 2026
97ab687
fix(jira): expire cached attachment images while idle (#24678)
OrcaWin Oct 3, 2026
1061ded
fix(mobile): merge terminal backlogs without rescanning growing strin…
OrcaWin Oct 3, 2026
7c6a37e
fix(terminal): release retired scrollback layouts from status routing…
OrcaWin Oct 3, 2026
0b0152a
fix(files): release expired mobile path inventories while idle (#24694)
OrcaWin Oct 3, 2026
eb44511
fix(jira): discard detail replies after closing an issue (#24835)
OrcaWin Oct 3, 2026
84a4e8a
fix(browser): avoid a redundant copy of live screencast images (#24851)
OrcaWin Oct 3, 2026
a25f730
fix(terminal): release closed layouts while reveal frames are paused …
OrcaWin Oct 3, 2026
9592159
fix(quick-open): release expired legacy file inventories while idle (…
OrcaWin Oct 3, 2026
87a2c3c
fix(ssh): keep terminal buffers out of failed workspace sync status (…
OrcaWin Oct 3, 2026
2165558
fix(native-chat): the desktop declares structured chat support to pai…
brennanb2025 Oct 3, 2026
18b99ac
fix(ai-vault): release expired host results while idle (#24766)
OrcaWin Oct 3, 2026
ac6c27e
fix(orchestration): avoid loading task descriptions during promotion …
OrcaWin Oct 3, 2026
bd6d7b9
feat(codex): run Windows Codex on the real ~/.codex (#24356)
Jinwoo-H Oct 3, 2026
3c9c2ab
fix(mobile): release callbacks retained by canceled streams (#24625)
OrcaWin Oct 3, 2026
3ad2648
fix(mobile): reduce base64 allocations for encrypted text frames (#24…
OrcaWin Oct 3, 2026
9a1bef4
fix(cursor): resume exact conversation after startup status replay (#…
nwparker Oct 3, 2026
610c048
fix(claude): inspect child tool IDs without rebuilding their output (…
OrcaWin Oct 3, 2026
5c62cb5
fix(native-chat): remove the "still starting" notice that flashed on …
brennanb2025 Oct 3, 2026
a5915b2
fix(native-chat): no loading flash on open, one report for a failed s…
brennanb2025 Oct 3, 2026
ac46d9e
fix(native-chat): plain wording for chat errors and status rows (#24594)
brennanb2025 Oct 3, 2026
6e6f651
Avoid repeated pnpm archive downloads in cache producers (#24927)
nwparker Oct 3, 2026
f146368
fix(usage): include OpenCode cached input in totals
nwparker Oct 3, 2026
fee8143
fix(opencode): atomically install status plugin entrypoints
nwparker Oct 3, 2026
f7b1f9d
fix(opencode): select tmux status on the execution host
nwparker Oct 3, 2026
b032867
feat(accounts): link standalone GLM Coding Plans (#24618)
nwparker Oct 3, 2026
77ad467
fix(ci): prevent concurrent pnpm refresh during mobile typechecks (#2…
nwparker Oct 3, 2026
54ddebf
test(terminal): restore the live fish fixture prerequisites (#24947)
nwparker Oct 3, 2026
08ee7ba
fix(shortcuts): defer TUI editing chords in terminal-first mode (#24640)
nwparker Oct 3, 2026
843607b
Register supervised Qoder China and Qwen Code (#24616)
nwparker Oct 3, 2026
8f26bfa
Use the measured pnpm lookup policy automatically in hosted root CI (…
nwparker Oct 3, 2026
055871a
Continue Antigravity IDE and 2.0 history in new CLI conversations (#2…
nwparker Oct 3, 2026
e8402b4
fix(opencode): retry timed-out SSH plugin updates (#24666)
nwparker Oct 3, 2026
53f9ea7
fix(opencode): keep Go credentials private and resolve backend keys (…
nwparker Oct 3, 2026
0b15a20
Skip store notifications when refreshed work items are unchanged (#24…
nwparker Oct 3, 2026
7a3ce0b
Read project activity once while sorting the sidebar (#24549)
nwparker Oct 3, 2026
7539d19
Skip impossible link and tag matches in docs search results (#24646)
nwparker Oct 3, 2026
29e7adf
Decode complete transcript lines without copying their bytes (#24546)
nwparker Oct 3, 2026
37b1f47
Clear unused speech worker timers after errors and exit (#24924)
nwparker Oct 3, 2026
87f5a98
Reuse documentation search excerpts during result navigation (#24574)
nwparker Oct 3, 2026
abd2b49
Append subagent handoffs without recopying their message list (#24672)
nwparker Oct 3, 2026
072f25e
Cancel plugin retry timers when their fetch is replaced (#24700)
nwparker Oct 3, 2026
c0a673b
Avoid rebuilding visible file paths for single-row selection (#24743)
nwparker Oct 3, 2026
76adcce
Reuse prepared reads while searching saved agent conversations (#24535)
nwparker Oct 3, 2026
c71753b
Reuse discovered mobile chunks during static traversal (#24774)
nwparker Oct 3, 2026
14ab734
Skip unused image-size calculations in mobile web browser requests (#…
nwparker Oct 3, 2026
b109544
Skip diff analysis after a result has been discarded (#24711)
nwparker Oct 3, 2026
7bbe421
Skip late browser grab toasts after their surface closes (#24727)
nwparker Oct 3, 2026
9142169
Classify native chat waiting messages once (#24771)
nwparker Oct 3, 2026
9d68ae3
Skip discarded Kanban pruning for an empty selection (#24782)
nwparker Oct 3, 2026
cf73a97
Index discovered test files once during shard selection validation (#…
nwparker Oct 3, 2026
1198d06
Clear the watchdog benchmark heartbeat when CPU sampling fails (#24802)
nwparker Oct 3, 2026
3b13282
Reuse the parsed notification when leasing a push delivery (#24645)
nwparker Oct 3, 2026
36d0086
Update README downloads badge
github-actions[bot] Oct 3, 2026
30e0cca
Let retired-cache GC observations settle across the existing six-turn…
nwparker Oct 3, 2026
f93808d
Collect test-selection evidence when full unit tests fail (#24955)
nwparker Oct 3, 2026
ebe7702
Check each project repository once while filtering mobile cards (#24540)
nwparker Oct 3, 2026
d2c9636
Skip renderer callbacks after their request has ended (#24631)
nwparker Oct 3, 2026
9e11375
Decode single-piece saved-session tails without copying them (#24632)
nwparker Oct 3, 2026
832caea
Avoid irrelevant scroll-action searches in Mac snapshots (#24731)
nwparker Oct 3, 2026
1c8d281
Stop copying every retained browser page before attachment (#24553)
nwparker Oct 3, 2026
0afc7b1
Reuse event byte sizes when relay watchers notify several clients (#2…
nwparker Oct 3, 2026
cca14bd
Stop building unused import candidates in the test planner (#24611)
nwparker Oct 3, 2026
c792386
docs(terminal): explain local macOS/Linux shell startup files
brynnclaw Oct 3, 2026
97fd7ed
fix(editor): recognize Ruby task and configuration files
ggbdpq Oct 3, 2026
b332742
Speed up large Markdown Find and render oversized tables (#24948)
nwparker Oct 3, 2026
fa2d50f
fix(source-control): generate clean OpenCode messages locally and ove…
nwparker Oct 3, 2026
81e69f3
fix(persistence): preserve projectGroupOrder on restart for flat fold…
lurunzi Oct 3, 2026
6565a3f
fix(runtime): reclaim temp files orphaned by interrupted mobile store…
LDH1103 Oct 3, 2026
8c4d63e
fix(terminal): show actionable copy for missing folder workspace paths
Waynting Oct 3, 2026
6486624
docs: reference local orca.yaml and .worktreeinclude
nwparker Oct 3, 2026
4f46f5b
fix(orchestration): allow model selection for OMP workers
nwparker Oct 3, 2026
c39f5f2
fix(cli): preserve primitive success results in JSON output
nwparker Oct 3, 2026
f255574
Show loaded file changes before deleting a workspace
nwparker Oct 3, 2026
0f1bbce
fix(keybindings): record and match Option+digit shortcuts on macOS
marcuslannister Oct 3, 2026
9f5c520
fix(editor): don't throw closing a stale active file
OrcaWin Oct 3, 2026
5f5c266
Fix Project Settings targeting for multiple local checkouts
fsmeier Oct 3, 2026
130b2ef
feat(documents): open CSV and TSV files from the OS
nwparker Oct 3, 2026
c1d403a
feat(cli): link GitHub and GitLab items on worktree create and set
SongMarco Oct 3, 2026
7b8498b
feat(sidebar): include folder workspaces in keyboard navigation
nwparker Oct 3, 2026
126f709
fix(build): turn off MSBuild file tracking for Windows native rebuilds
b1nhm1nh Oct 3, 2026
f113d35
Fix Ctrl+M in Linux and Windows terminals
yuzhichang Oct 3, 2026
98a6d20
fix(startup): read a nushell login PATH from $env.PATH
Kh05ifr4nD Oct 3, 2026
8919f3d
fix(cursor): run local hooks through sh for non-POSIX login shells
Kh05ifr4nD Oct 3, 2026
a5f28f2
Fix word wrap for both panes in side-by-side diffs
innocarpe Oct 3, 2026
df9acd8
fix(monaco): highlight Svelte block closers inside markup
innocarpe Oct 3, 2026
752dbc9
fix(repos): keep active clone dialog open on outside clicks
nwparker Oct 3, 2026
8ccc336
fix(editor): keep chat visible after closing Markdown tabs
nwparker Oct 3, 2026
44c584e
Honor typed starting numbers in chat ordered lists
nwparker Oct 3, 2026
4a5f00f
Normalize base source once while checking changed-code diagnostics (#…
nwparker Oct 3, 2026
a2896f5
Support real OpenCode sessions in native Chat (#24647)
nwparker Oct 3, 2026
ec47f0c
Drain removal fixture jobs before resetting and deleting their record…
nwparker Oct 3, 2026
668d6d4
Reuse measured Electron preparation for current Terminal Perf refs (#…
nwparker Oct 3, 2026
4049e63
feat(jcode): add Jcode as a supported TUI agent with managed hooks
czzczz Sep 23, 2026
2ca85d2
feat(jcode): evidence-backed status pipeline (turn_start, live pre_to…
nwparker Sep 23, 2026
6164d3f
fix(jcode): register vault fixture, dynamic model discovery, script r…
nwparker Sep 23, 2026
5b43e20
fix(jcode): keep finished-turn detail so completion notifications fire
nwparker Sep 23, 2026
5ab36cc
fix(jcode): show the prompt in agent rows instead of jcode's repainti…
nwparker Sep 23, 2026
33cab24
fix(jcode): pre-warm the per-pane daemon so a cold runtime dir cannot…
nwparker Sep 23, 2026
7fb201f
fix(jcode): stop the OSC color skip from crashing every pane connect
nwparker Sep 23, 2026
0a45ad5
refactor(jcode): fold three reverse-scan copies into one, reuse the s…
nwparker Sep 23, 2026
4f2007a
fix(jcode): narrow dynamic reads with predicates, pin the Windows hoo…
nwparker Sep 23, 2026
2c04f79
test(jcode): measure the gate against the synchronous path, not the c…
nwparker Sep 24, 2026
888e3c4
test(jcode): drop the wall-clock gate assertion
nwparker Sep 24, 2026
a7b9358
fix(jcode): address CodeRabbit review on #22539
nwparker Sep 24, 2026
fe76440
fix(jcode): read the journal once per turn, key prompts by byte offset
nwparker Sep 24, 2026
4c2cb3c
fix(jcode): quote the managed hook path, drop tools from patch prompts
nwparker Sep 24, 2026
07d8aff
test(jcode): pin the tool-profile flag in the generation plan too
nwparker Sep 24, 2026
154b2fd
fix(text-generation): refuse an oversized argv prompt on Linux too
nwparker Sep 24, 2026
84d246b
fix(jcode): register in main's remote-installer guard, drop our dupli…
nwparker Oct 3, 2026
af4c3e2
fix(jcode): decompose the four files jcode pushed over max-lines
nwparker Oct 3, 2026
8dc16a7
feat(native-chat): open structured chats on the paired Orca server th…
brennanb2025 Oct 3, 2026
2fc517c
feat(cli): add --unread/--read to orca worktree set
razshlomo Oct 3, 2026
deee1bc
Prepare immutable strict worker readiness restack
nwparker Oct 3, 2026
bde1c09
feat(cli): configure external worktree visibility per repo
nwparker Oct 3, 2026
a40e501
perf(git): reuse queries and stop canceled catalog scans (#24923)
nwparker Oct 3, 2026
dad41e5
Prepare immutable strict worker readiness restack
nwparker Oct 3, 2026
1001118
test(e2e): require exact Linux package tokens (#24995)
nwparker Oct 3, 2026
0e36159
Allow cold node-pty setup on Windows ARM CI (#24997)
nwparker Oct 3, 2026
aca2d51
fix(jcode): harden Windows hooks and negotiate remote history (#24998)
nwparker Oct 3, 2026
40d9038
STRICT launch CI contract correction
nwparker Oct 3, 2026
6245192
fix(git): preserve SSH review context and worktree ownership (#24945)
nwparker Oct 3, 2026
7c2ca76
Preserve frozen main and reviewed strict OpenCode layer
nwparker Oct 3, 2026
5e65871
fix(opencode): keep shared-session TUI activity with its owning pane …
nwparker Oct 3, 2026
b601b98
fix(ci): wait for the fragment navigation policy report (#25017)
nwparker Oct 3, 2026
2d6636a
fix(opencode): compose reviewed strict launch boundary with current main
nwparker Oct 3, 2026
c2dba12
Add host-owned OpenCode and Devin managed account profiles (#24636)
nwparker Oct 3, 2026
786a040
Read OpenCode Go usage from the selected account (#24770)
nwparker Oct 3, 2026
a62e9ba
fix(opencode): preserve managed account environment in strict launch …
nwparker Oct 3, 2026
4ecbf29
fix(opencode): preserve current Caller main in strict launch boundary
nwparker Oct 3, 2026
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
The table of contents is too big for display.
Diff view
Diff view
  •  
  •  
  •  
98 changes: 70 additions & 28 deletions .github/actions/install-node-dependencies/action.yml
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,14 @@ name: Install Node dependencies
description: Installs the Node toolchain and repository dependencies for CI jobs, with optional Electron archive caching.

inputs:
cache-pnpm-store:
description: Restore or save the pnpm download store; verification and native caches are independent.
required: false
default: 'true'
cache-pnpm-store-lookup-only:
description: Auto uses measured hosted Node 24 root installs; true forces lookup, false retains archive restoration.
required: false
default: auto
cache-pnpm-verification:
description: Restore pnpm's policy-checked lockfile verification record.
required: false
Expand All @@ -28,9 +36,12 @@ inputs:
default: 'false'

outputs:
pnpm-store-cache-hit:
description: Whether the requested download store matched an existing cache.
value: ${{ steps.pnpm-store-lookup.outputs.cache-hit || steps.pnpm-store-restore.outputs.cache-hit || steps.requested-node.outputs.cache-hit || steps.default-node.outputs.cache-hit }}
verification-cache-hit:
description: Whether pnpm's verification record was restored.
value: ${{ steps.verification-cache-restore.outputs.cache-hit }}
value: ${{ steps.verification-cache.outputs.cache-hit }}
verification-cache-path:
description: The small pnpm-owned verification record, without registry metadata.
value: ${{ steps.verification-cache.outputs.path }}
Expand All @@ -56,6 +67,30 @@ outputs:
runs:
using: composite
steps:
- name: Resolve pnpm store mode
id: pnpm-store-mode
if: >-
github.event_name != 'pull_request' && inputs.cache-pnpm-store != 'false' &&
(inputs.cache-pnpm-store-lookup-only == 'true' ||
(inputs.cache-pnpm-store-lookup-only == 'auto' &&
inputs.cache-dependency-path == 'pnpm-lock.yaml' &&
runner.environment == 'github-hosted' && job.container.id == '' &&
(runner.os == 'Linux' || runner.os == 'macOS' || runner.os == 'Windows') &&
(runner.arch == 'X64' || runner.arch == 'ARM64') &&
(inputs.node-version == '' || inputs.node-version == '24')))
shell: bash
env:
LOOKUP_REQUEST: ${{ inputs.cache-pnpm-store-lookup-only }}
run: |
lookup_only=true
case "$LOOKUP_REQUEST" in
[aA][uU][tT][oO])
# Hosted runners have Node for this manifest-only check before toolchain setup.
lookup_only="$(node -p 'const p = require("./package.json"); p.engines?.node === "24" && typeof p.packageManager === "string" && p.packageManager.split("+")[0] === "pnpm@12.8.1"')"
;;
esac
printf 'lookup-only=%s\n' "$lookup_only" >> "$GITHUB_OUTPUT"

# setup-node needs pnpm on PATH to locate and restore its store.
- name: Setup pnpm
uses: pnpm/setup@v2
Expand All @@ -69,7 +104,7 @@ runs:
uses: actions/setup-node@v6
with:
node-version-file: package.json
cache: ${{ github.event_name != 'pull_request' && 'pnpm' || '' }}
cache: ${{ github.event_name != 'pull_request' && inputs.cache-pnpm-store != 'false' && steps.pnpm-store-mode.outputs.lookup-only != 'true' && 'pnpm' || '' }}
cache-dependency-path: ${{ inputs.cache-dependency-path }}
package-manager-cache: false

Expand All @@ -79,59 +114,66 @@ runs:
uses: actions/setup-node@v6
with:
node-version: ${{ inputs.node-version }}
cache: ${{ github.event_name != 'pull_request' && 'pnpm' || '' }}
cache: ${{ github.event_name != 'pull_request' && inputs.cache-pnpm-store != 'false' && steps.pnpm-store-mode.outputs.lookup-only != 'true' && 'pnpm' || '' }}
cache-dependency-path: ${{ inputs.cache-dependency-path }}
package-manager-cache: false

# PR-local stores compete with reusable build caches for the repository quota.
- name: Resolve pnpm download store
id: pnpm-store
if: >-
github.event_name == 'pull_request' &&
(runner.os != 'Windows' || runner.arch != 'X64' || !contains(inputs.cache-dependency-path, 'mobile/pnpm-lock.yaml'))
github.event_name == 'pull_request' && inputs.cache-pnpm-store != 'false' &&
!((runner.os == 'Linux' || runner.os == 'macOS') && (runner.arch == 'X64' || runner.arch == 'ARM64') && inputs.cache-dependency-path == 'pnpm-lock.yaml') &&
(runner.os != 'Windows' ||
!(runner.arch == 'X64' && contains(inputs.cache-dependency-path, 'mobile/pnpm-lock.yaml')) &&
!((runner.arch == 'X64' || runner.arch == 'ARM64') && inputs.cache-dependency-path == 'pnpm-lock.yaml')) ||
(github.event_name != 'pull_request' && inputs.cache-pnpm-store != 'false' &&
steps.pnpm-store-mode.outputs.lookup-only == 'true')
shell: bash
env:
LOCKFILE_HASH: ${{ hashFiles(inputs.cache-dependency-path) }}
STORE_LOOKUP_ONLY: ${{ steps.pnpm-store-mode.outputs.lookup-only == 'true' }}
run: |
test -n "$LOCKFILE_HASH"
cache_path="$(pnpm store path --silent)"
test -n "$cache_path"
printf 'path=%s\n' "$cache_path" >> "$GITHUB_OUTPUT"
printf 'arch=%s\n' "$(node -p 'require("node:os").arch()')" >> "$GITHUB_OUTPUT"
if [ "$STORE_LOOKUP_ONLY" = 'true' ]; then
printf 'ORCA_PNPM_STORE_CACHE_PATH=%s\n' "$cache_path" >> "$GITHUB_ENV"
fi

# Match setup-node's key and path so existing default-branch stores remain reusable.
# Hosted Windows x64 mixed installs cost less than restoring their root/mobile store.
# Direct downloads beat store restoration for the measured Linux, macOS and Windows installs.
- name: Restore pnpm download store without saving
id: pnpm-store-restore
if: >-
github.event_name == 'pull_request' &&
(runner.os != 'Windows' || runner.arch != 'X64' || !contains(inputs.cache-dependency-path, 'mobile/pnpm-lock.yaml'))
github.event_name == 'pull_request' && inputs.cache-pnpm-store != 'false' &&
!((runner.os == 'Linux' || runner.os == 'macOS') && (runner.arch == 'X64' || runner.arch == 'ARM64') && inputs.cache-dependency-path == 'pnpm-lock.yaml') &&
(runner.os != 'Windows' ||
!(runner.arch == 'X64' && contains(inputs.cache-dependency-path, 'mobile/pnpm-lock.yaml')) &&
!((runner.arch == 'X64' || runner.arch == 'ARM64') && inputs.cache-dependency-path == 'pnpm-lock.yaml'))
uses: actions/cache/restore@v5
with:
path: ${{ steps.pnpm-store.outputs.path }}
key: node-cache-${{ runner.os }}-${{ steps.pnpm-store.outputs.arch }}-pnpm-${{ hashFiles(inputs.cache-dependency-path) }}

- name: Resolve pnpm verification cache
id: verification-cache
if: >-
inputs.cache-pnpm-verification == 'true' &&
(runner.os == 'Linux' ||
(runner.os == 'Windows' && (runner.arch == 'X64' || runner.arch == 'ARM64')) ||
(runner.os == 'macOS' && runner.arch == 'X64'))
shell: bash
env:
POLICY_HASH: ${{ hashFiles('pnpm-lock.yaml', 'pnpm-workspace.yaml', '.npmrc') }}
run: |
printf 'path=%s/lockfile-verified.jsonl\n' "$(pnpm cache path)" >> "$GITHUB_OUTPUT"
printf 'key=pnpm-verification-v1-%s-%s-%s-%s\n' "$RUNNER_OS" "$RUNNER_ARCH" "$(pnpm --version)" "$POLICY_HASH" >> "$GITHUB_OUTPUT"
# Producers can refresh access and publish misses without downloading existing archives.
- name: Keep pnpm download store without restoring
id: pnpm-store-lookup
if: steps.pnpm-store-mode.outputs.lookup-only == 'true'
uses: actions/cache@v5
with:
# Twice-nested composite cleanup loses internal step outputs.
path: ${{ env.ORCA_PNPM_STORE_CACHE_PATH }}
key: node-cache-${{ runner.os }}-${{ steps.pnpm-store.outputs.arch }}-pnpm-${{ hashFiles(inputs.cache-dependency-path) }}
lookup-only: true

- name: Restore pnpm verification record
id: verification-cache-restore
if: steps.verification-cache.outputs.key != ''
continue-on-error: true
uses: actions/cache/restore@v5
id: verification-cache
uses: ./.github/actions/restore-pnpm-verification
with:
path: ${{ steps.verification-cache.outputs.path }}
key: ${{ steps.verification-cache.outputs.key }}
enabled: ${{ inputs.cache-pnpm-verification }}

- name: Validate native runtime
shell: bash
Expand Down Expand Up @@ -169,7 +211,7 @@ runs:

# pnpm checks the cached record's policy and validity; never bypass verification.
- name: Save pnpm verification record on main
if: github.ref == 'refs/heads/main' && github.event_name != 'pull_request' && steps.verification-cache.outputs.key != '' && steps.verification-cache-restore.outputs.cache-hit != 'true'
if: github.ref == 'refs/heads/main' && github.event_name != 'pull_request' && steps.verification-cache.outputs.key != '' && steps.verification-cache.outputs.cache-hit != 'true'
continue-on-error: true
uses: actions/cache/save@v5
with:
Expand Down
9 changes: 6 additions & 3 deletions .github/actions/prepare-git-compatibility/action.yml
Original file line number Diff line number Diff line change
Expand Up @@ -10,15 +10,17 @@ runs:
uses: actions/cache@v5
with:
path: ~/.cache/orca-git-compat/git-2.25.5
key: git-compat-baseline-${{ runner.os }}-${{ runner.arch }}-2.25.5
key: git-compat-baseline-${{ runner.os }}-${{ runner.arch }}-2.25.5-submodule

# Finish the CPU-heavy build before any timed compatibility lanes start.
- name: Build the baseline Git binary
shell: bash
run: |
archive="$RUNNER_TEMP/git-2.25.5.tar.gz"
source="$HOME/.cache/orca-git-compat/git-2.25.5"
if [ -x "$source/git" ]; then
if [ -x "$source/git" ] && [ -x "$source/git-submodule" ] \
&& [ -f "$source/git-sh-setup" ] && [ -f "$source/git-sh-i18n" ] \
&& [ -f "$source/git-parse-remote" ] && [ -x "$source/git-sh-i18n--envsubst" ]; then
exit 0
fi
curl -fsSL https://www.kernel.org/pub/software/scm/git/git-2.25.5.tar.gz -o "$archive"
Expand All @@ -27,6 +29,7 @@ runs:
mkdir -p "$source"
tar -xzf "$archive" -C "$source" --strip-components=1
make -C "$source" -j"$(nproc)" \
NO_GETTEXT=YesPlease NO_TCLTK=YesPlease NO_PYTHON=YesPlease git
NO_GETTEXT=YesPlease NO_TCLTK=YesPlease NO_PYTHON=YesPlease \
git git-submodule git-sh-setup git-sh-i18n git-parse-remote git-sh-i18n--envsubst
# Object files are no longer needed after linking the cached binary.
find "$source" -name '*.o' -delete
45 changes: 45 additions & 0 deletions .github/actions/prepare-headless-compiler/action.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,45 @@
name: Prepare headless detector compiler
description: Reuse the policy-checked compiler from main; callers install normally on a miss.
inputs:
seed:
description: Pack an already installed compiler instead of activating a cached compiler.
default: 'false'
outputs:
available:
description: Whether the cached compiler was validated and activated.
value: ${{ steps.activate.outputs.available }}
runs:
using: composite
steps:
- id: identity
shell: bash
env:
COMPILER_POLICY_HASH: ${{ hashFiles('package.json', 'pnpm-lock.yaml', 'pnpm-workspace.yaml', '.npmrc', '.pnpmfile.cjs', 'config/patches/**', '.github/actions/install-node-dependencies/**', '.github/actions/restore-pnpm-verification/**', 'config/scripts/headless-detector-compiler-cache.mjs', '.github/actions/prepare-headless-compiler/action.yml') }}
run: node config/scripts/headless-detector-compiler-cache.mjs identity
- id: cache
uses: actions/cache/restore@v5
continue-on-error: true
with:
path: ${{ steps.identity.outputs.path }}
key: ${{ steps.identity.outputs.key }}
- id: activate
if: inputs.seed != 'true' && steps.cache.outputs.cache-hit == 'true'
shell: bash
env:
COMPILER_CACHE_KEY: ${{ steps.identity.outputs.key }}
COMPILER_CACHE_PATH: ${{ steps.identity.outputs.path }}
run: node config/scripts/headless-detector-compiler-cache.mjs activate
- name: Pack installed compiler
if: inputs.seed == 'true' && steps.cache.outputs.cache-hit != 'true'
shell: bash
env:
COMPILER_CACHE_KEY: ${{ steps.identity.outputs.key }}
COMPILER_CACHE_PATH: ${{ steps.identity.outputs.path }}
run: node config/scripts/headless-detector-compiler-cache.mjs pack
- name: Save compiler only from main
if: inputs.seed == 'true' && steps.cache.outputs.cache-hit != 'true' && github.ref == 'refs/heads/main' && github.event_name != 'pull_request'
uses: actions/cache/save@v5
continue-on-error: true
with:
path: ${{ steps.identity.outputs.path }}
key: ${{ steps.identity.outputs.key }}
58 changes: 58 additions & 0 deletions .github/actions/restore-pnpm-verification/action.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,58 @@
name: Restore pnpm verification
description: Restore the pnpm-owned lockfile verdict without installing dependencies.

inputs:
enabled:
description: Restore a verification record on supported runners.
default: 'true'
container-toolchain:
description: Use the manifest's pnpm version and default Linux cache path without installing host pnpm.
default: 'false'

outputs:
path:
description: The pnpm-owned verification record.
value: ${{ steps.verification-cache.outputs.path }}
key:
description: Exact OS, architecture, pnpm version and policy key.
value: ${{ steps.verification-cache.outputs.key }}
cache-hit:
description: Whether the exact record was restored.
value: ${{ steps.verification-cache-restore.outputs.cache-hit }}

runs:
using: composite
steps:
- name: Resolve pnpm verification cache
id: verification-cache
if: >-
inputs.enabled == 'true' &&
(runner.os == 'Linux' ||
(runner.os == 'Windows' && (runner.arch == 'X64' || runner.arch == 'ARM64')) ||
(runner.os == 'macOS' && runner.arch == 'X64'))
shell: bash
env:
POLICY_HASH: ${{ hashFiles('pnpm-lock.yaml', 'pnpm-workspace.yaml', '.npmrc') }}
CONTAINER_TOOLCHAIN: ${{ inputs.container-toolchain }}
run: |
if [ "$CONTAINER_TOOLCHAIN" = true ]; then
test "$RUNNER_OS" = Linux
# Cache versions include paths, so match the native Linux producer.
cache_path="$(node -p "require('node:path').join(process.env.XDG_CACHE_HOME || require('node:path').join(require('node:os').homedir(), '.cache'), 'pnpm')")"
pnpm_version="$(node -p "require('./package.json').packageManager.match(/^pnpm@([^+]+)/)[1]")"
mkdir -p "$cache_path"
else
cache_path="$(pnpm cache path)"
pnpm_version="$(pnpm --version)"
fi
printf 'path=%s/lockfile-verified.jsonl\n' "$cache_path" >> "$GITHUB_OUTPUT"
printf 'key=pnpm-verification-v1-%s-%s-%s-%s\n' "$RUNNER_OS" "$RUNNER_ARCH" "$pnpm_version" "$POLICY_HASH" >> "$GITHUB_OUTPUT"

- name: Restore pnpm verification record
id: verification-cache-restore
if: steps.verification-cache.outputs.key != ''
continue-on-error: true
uses: actions/cache/restore@v5
with:
path: ${{ steps.verification-cache.outputs.path }}
key: ${{ steps.verification-cache.outputs.key }}
41 changes: 26 additions & 15 deletions .github/scripts/render-readme-downloads-badge.mjs
Original file line number Diff line number Diff line change
@@ -1,5 +1,7 @@
import { mkdir, writeFile } from 'node:fs/promises'
import { dirname } from 'node:path'
import { pathToFileURL } from 'node:url'
import { isAgentStateRulesTag } from '../../config/scripts/release-tag-patterns.mjs'

const repository = process.env.GITHUB_REPOSITORY ?? 'stablyai/orca'
const token = process.env.GITHUB_TOKEN
Expand All @@ -24,6 +26,22 @@ async function fetchJson(url) {
return response.json()
}

// Why rules releases are excluded: every running app fetches them every few hours, so they
// count fetches, not installs.
export function countReleaseDownloads(releases) {
let total = 0
for (const release of releases) {
if (release.draft || isAgentStateRulesTag(release.tag_name ?? '')) {
continue
}

for (const asset of release.assets ?? []) {
total += asset.download_count ?? 0
}
}
return total
}

async function getTotalReleaseDownloads() {
let page = 1
let total = 0
Expand All @@ -37,16 +55,7 @@ async function getTotalReleaseDownloads() {
return total
}

for (const release of releases) {
if (release.draft) {
continue
}

for (const asset of release.assets ?? []) {
total += asset.download_count ?? 0
}
}

total += countReleaseDownloads(releases)
page += 1
}
}
Expand Down Expand Up @@ -104,9 +113,11 @@ function renderBadge(value) {
`
}

const total = await getTotalReleaseDownloads()
const badge = renderBadge(formatDownloads(total))
if (import.meta.url === pathToFileURL(process.argv[1] ?? '').href) {
const total = await getTotalReleaseDownloads()
const badge = renderBadge(formatDownloads(total))

await mkdir(dirname(outputPath), { recursive: true })
await writeFile(outputPath, badge)
console.log(`Rendered ${outputPath} from ${total} downloads.`)
await mkdir(dirname(outputPath), { recursive: true })
await writeFile(outputPath, badge)
console.log(`Rendered ${outputPath} from ${total} downloads.`)
}
Loading
Loading