Proof Portal
Omarchy
ProbeLabs65 findings · 95 requirementsA proof layer — requirements, tests and verified fixes — for two of Omarchy's subsystems: the application menu (launcher scripts, QML model, JSONC config, search and selection) and the lock screen (lock scripts, QML, PAM authentication). Scope is deliberately limited to those components of omacom/omarchy; the rest of the distribution is not covered.
Menu: a route summoned while the shell starts opens the main menu instead
Reported by buger · filed Oct 2, 2026 · open at source · 3 revisions
At a glance
- 1 · What is claimed?
- ConfirmedViolates SYS-REQ-260922-R8DQ: a route summoned while the shell starts (before the menu files have loaded) opens the main menu instead of the item it denotes, and an action alias does not run
- ConfirmedReproducible: summon system before the JSONC files answer, then let both answer: activeMenu stays root
- ConfirmedAffects the menu component
- LinkedMatches known issue KI-MENU-PENDING-INITIAL-MENU-DEAD
- 2 · What does it affect?
- 3 · Is it reproducible?
- An engine-executed run exited 1 and showed the defect signal. See reproducer
- 4 · What remains unclear?
- Nothing recorded as open.
- 5 · What happens next?
- Decided by agents and verified by a second, independent agent — see the decision.
Original report
TL;DR: If a menu keybind fires while the shell is still starting (right after login, or after omarchy-restart-shell, which omarchy update runs), you get the main menu instead of the menu you asked for. Super+Escape gives the main menu, not System. A route that is an action alias (Super+Ctrl+Space background, Super+Shift+Ctrl+Space theme, Super+Ctrl+R reminder) also opens the main menu, and its action never runs. A summon after startup works.
Steps to reproduce
On quattro 821ae589:
omarchy-restart-shell
# straight away, before the shell has finished starting:
omarchy menu summon system # or press Super+EscapeYou get the main menu (Apps, Learn, Trigger, Style, …), not System (Screensaver, Lock, Suspend, …). It stays on the main menu. Run the same command a second later and System opens.
This reproduces every time if you retry the summon until the shell accepts it. I ran it on a private headless sway with the real shell (quickshell -p shell):
| Summon during startup | Result on 821ae589 |
|---|---|
{"menu":"system"}: no user extension, the stock one, or one with items | main menu, 3/3 runs each |
{"menu":"power-menu"} (alias of system) | main menu |
{"menu":"personal"} (a menu from ~/.config/omarchy/extensions/omarchy-menu.jsonc) | main menu |
| an action alias from the user extension | main menu; the action does not run |
| the same summons after startup | the requested menu, or the action runs |
Cause
The shell queues a summon that arrives before the menu plugin has loaded. It hands the summon to open() as soon as the plugin's Loader registers (shell/shell.qml:1171-1179, :1221-1226). At that point neither FileView in shell/plugins/menu/Menu.qml has read its JSONC file. Both files load asynchronously (:968-985), and the user extension usually answers first, a few milliseconds before the default file.
openRoute()cannot resolvesystemagainst an empty item set.openExistingMenu()then falls back to root (Menu.qml:846).- When the files land,
rebuildItemsFromSources()(:249-263) redraws whatever menu is active, which is now root. openRoute()stores the route inpendingInitialMenu(:911), but nothing reads that property.
History
pendingInitialMenu (Menu.qml:19) was the replay slot of the bash menu: its menuJsonFileView.onLoaded called openMenu(text(), root.pendingInitialMenu, …) once the menu data arrived, so a route summoned through the bash menu never raced the data (0e135bbb). On 2026-05-14 the menu data moved into the shell. a960d2b1 added the JSONC FileViews and the direct IPC path, which opens from the cached items and does not wait for them. 4a665af5 moved the keybinds off the bash menu, and edfd68d4 removed the bash path together with its replay. Since 4cd6593b ("Use plugin IPC routes", which added openRoute()), the property is written and never read.
Fix with tests: #14055
Reproduction on quattro 393a43d, with the fix PR checked against it: https://portal.reqproof.com/projects/omarchy/inbox/2178
View raw text
**TL;DR:** If a menu keybind fires while the shell is still starting (right after login, or after `omarchy-restart-shell`, which `omarchy update` runs), you get the main menu instead of the menu you asked for. Super+Escape gives the main menu, not System. A route that is an action alias (Super+Ctrl+Space background, Super+Shift+Ctrl+Space theme, Super+Ctrl+R reminder) also opens the main menu, and its action never runs. A summon after startup works.
### Steps to reproduce
On `quattro` 821ae589:
```bash
omarchy-restart-shell
# straight away, before the shell has finished starting:
omarchy menu summon system # or press Super+Escape
```
You get the main menu (Apps, Learn, Trigger, Style, …), not System (Screensaver, Lock, Suspend, …). It stays on the main menu. Run the same command a second later and System opens.
This reproduces every time if you retry the summon until the shell accepts it. I ran it on a private headless sway with the real shell (`quickshell -p shell`):
| Summon during startup | Result on 821ae589 |
|---|---|
| `{"menu":"system"}`: no user extension, the stock one, or one with items | main menu, 3/3 runs each |
| `{"menu":"power-menu"}` (alias of `system`) | main menu |
| `{"menu":"personal"}` (a menu from `~/.config/omarchy/extensions/omarchy-menu.jsonc`) | main menu |
| an action alias from the user extension | main menu; the action does not run |
| the same summons after startup | the requested menu, or the action runs |
### Cause
The shell queues a summon that arrives before the menu plugin has loaded. It hands the summon to `open()` as soon as the plugin's Loader registers (`shell/shell.qml:1171-1179`, `:1221-1226`). At that point neither `FileView` in `shell/plugins/menu/Menu.qml` has read its JSONC file. Both files load asynchronously (`:968-985`), and the user extension usually answers first, a few milliseconds before the default file.
- `openRoute()` cannot resolve `system` against an empty item set. `openExistingMenu()` then falls back to root (`Menu.qml:846`).
- When the files land, `rebuildItemsFromSources()` (`:249-263`) redraws whatever menu is active, which is now root.
- `openRoute()` stores the route in `pendingInitialMenu` (`:911`), but nothing reads that property.
### History
`pendingInitialMenu` (`Menu.qml:19`) was the replay slot of the bash menu: its `menuJsonFileView.onLoaded` called `openMenu(text(), root.pendingInitialMenu, …)` once the menu data arrived, so a route summoned through the bash menu never raced the data (0e135bbb). On 2026-05-14 the menu data moved into the shell. a960d2b1 added the JSONC `FileView`s and the direct IPC path, which opens from the cached items and does not wait for them. 4a665af5 moved the keybinds off the bash menu, and edfd68d4 removed the bash path together with its replay. Since 4cd6593b ("Use plugin IPC routes", which added `openRoute()`), the property is written and never read.
Fix with tests: #14055
Reproduction on `quattro` `393a43d`, with the fix PR checked against it: https://portal.reqproof.com/projects/omarchy/inbox/2178
Validation
AI validator claude-code (claude-opus-5.5) · evaluated revision 3 at product commit 1e43373287af · sealed 2026-10-04T21:45:47Z
Validation of omacom/omarchy#14053 on quattro-proof 1e433732 (upstream quattro 035ce29f product code plus the proof layer). The report is the auditor's own; it is checked against the same bar as third-party reports. A summon that reaches Menu.qml before its JSONC FileViews have answered cannot resolve the route against the empty item set, so openExistingMenu falls back to root. openRoute stores the route in pendingInitialMenu, but nothing reads it, and when the files land rebuildItemsFromSources redraws root. Parser level (no compositor): the reproducer runs the real Menu.qml route and FileView code with the real MenuModel.js and the stock default menu in node, summons before either file answers, then lets each file answer (both orders). system, power-menu (alias), a user-extension menu and a user-extension action alias all end on root and the action never runs; the same summon after both files answered opens system (control). Live shell, checked separately in the real shell (the tree's own, under Quickshell on a headless sway session), summoning from shell start until the shell accepts it: system, power-menu and personal open root and the hello action does not run, 3/3 runs each; a summon after startup opens system. With upstream PR #14055 (head 48405669) merged, every startup summon opens what it denotes (the action runs and closes the menu), in the reproducer and in the live shell, 3/3. #14054 (an unrelated menu fix) is the control and still shows the defect. The baseline tracks this as KI-MENU-PENDING-INITIAL-MENU-DEAD (open). Since 311d29c7 the baseline merged upstream 035ce29f, whose only menu changes are two data rows in the stock omarchy-menu.jsonc (Install/Remove > Service > Microsoft), the image-picker helper bin/omarchy-menu-images and one display property on the bar's menu button; Menu.qml, MenuModel.js, ConfirmDialog.qml and omarchy-menu-select are byte-identical, and the rest is lock-screen and other non-menu upstream changes plus proof-layer records. The reproducer was re-run on 1e433732 with identical output; the live-shell runs are reused from 20d4e6ae (author-recorded): Menu.qml, MenuModel.js and omarchy-menu-select are unchanged since then apart from comment-only trace lines, and the two stock-menu rows added since (Install/Remove > Service > Microsoft) are outside what these runs exercise.
- ConfirmedViolates a requirementA route string (exact id, declared alias, or normalized… SYS-REQ-260922-R8DQ
Violates SYS-REQ-260922-R8DQ: a route summoned while the shell starts (before the menu files have loaded) opens the main menu instead of the item it denotes, and an action alias does not run
Engine: engine-executed run exited 1 and showed the defect signal
What “confirmed” means here: the requirement exists and the engine reproduced the defect. That the reproducer exercises THIS requirement is the validator's argument (see rationale).
Evidence: requirement SYS-REQ-260922-R8DQ · file test/reports/report-cmur1322x0043rfw4mlkd1o4o.sh
Validator's rationale (commentary): SYS-REQ-260922-R8DQ: 'a route string (exact id, declared alias, or normalized spelling) opens the item it denotes'. During startup system, power-menu and personal open root; SW-REQ-260922-N3RM's action route (hello) opens root instead of running.
- ConfirmedReproducible
Reproducible: summon system before the JSONC files answer, then let both answer: activeMenu stays root
Engine: engine-executed run exited 1 and showed the defect signal
Evidence: file test/reports/report-cmur1322x0043rfw4mlkd1o4o.sh
Affects the menu component
Engine: confirmed violation of SYS-REQ-260922-R8DQ owned by menu
Evidence: requirement SYS-REQ-260922-R8DQ · file test/reports/report-cmur1322x0043rfw4mlkd1o4o.sh
- LinkedDuplicate ofpendingInitialMenu is stored and never read: a route summoned before the JSONC loads opens root and stays there KI-MENU-PENDING-INITIAL-MENU-DEAD
Matches known issue KI-MENU-PENDING-INITIAL-MENU-DEAD
Engine: the known issue exists; whether the report duplicates it is settled by a human disposition; it affects the mapped requirement(s) SW-REQ-260922-50RE, SW-REQ-260922-N3RM
Evidence: known_issue KI-MENU-PENDING-INITIAL-MENU-DEAD · requirement SW-REQ-260922-50RE · requirement SW-REQ-260922-N3RM
Validator's rationale (commentary): Exact match: the KI records that pendingInitialMenu is written and never read, so a route summoned before the JSONC loads opens root and stays there.
Engine reference checks at 93f1f11c6131 (11/11 ok)
- okcommit93f1f11c6131393df7865b35a77f51772571952e
- okbase commit1e43373287afbd6dca4674ad463d5b5db7812358
- okbase ancestry1e43373287afbd6dca4674ad463d5b5db7812358
- okproduct code untouchedthis report's reproducer branch
- okbranchthis report's reproducer branch
- okfiletest/reports/report-cmur1322x0043rfw4mlkd1o4o.sh
- okrequirementSW-REQ-260922-50RE
- okrequirementSW-REQ-260922-N3RM
- okrequirementSYS-REQ-260922-R8DQ
- okcomponentmenu
- okknown issueKI-MENU-PENDING-INITIAL-MENU-DEAD
The engine's own check, at validation time, that the commits, the reproducer branch (touching only reproducer files), the reproducer files and every mapped requirement / component / known issue really exist.
8 earlier checks — superseded by the newest one above
Each new check of the report replaces the previous one; only the newest result above counts. Earlier results are kept for the record.
- Reproduced— checked report revision 3 on Oct 4, 2026; earlier check, superseded
- Reproduced— checked report revision 2 on Oct 3, 2026; earlier check, superseded
- Reproduced— checked report revision 2 on Oct 3, 2026; earlier check, superseded
- Reproduced— checked report revision 2 on Oct 2, 2026; earlier check, superseded
- Reproduced— checked report revision 2 on Oct 2, 2026; earlier check, superseded
- Reproduced— checked report revision 2 on Oct 2, 2026; earlier check, superseded
- Reproduced— checked report revision 2 on Oct 2, 2026; earlier check, superseded
- Reproduced— checked report revision 1 on Oct 2, 2026; earlier check, superseded
Validator-authored hypothesis. Each claim's verification is engine-computed: confirmed only from an engine-executed reproducer run recorded in this record, refuted when recorded evidence contradicts it. Prose is commentary. The disposition of the report is a human decision.
Reproducer
sh test/reports/report-cmur1322x0043rfw4mlkd1o4o.sh
Setup failure: exit 2 means the reproducer could not set up (e.g. the product did not build) — such a run decides nothing.
Defect signal: output contains DEFECT:
DEFECT: summon system during startup (no user file; it answers first, then the default file) -> activeMenu=root opened=true (expected menu system) DEFECT: summon system during startup (no user file; the default file answers first) -> activeMenu=root opened=true (expected menu system) DEFECT: summon power-menu (alias of system) during startup -> activeMenu=root opened=true (expected menu system) DEFECT: summon personal (a menu from the user extension) during startup -> activeMenu=root opened=true (expected menu personal) DEFECT: summon say-hello (an action alias from the user extension) during startup -> activeMenu=root opened=true (expected action touch hello-ran)
control: summon system after both files answered -> activeMenu=system DEFECT: summon system during startup (no user file; it answers first, then the default file) -> activeMenu=root opened=true (expected menu system) DEFECT: summon system during startup (no user file; the default file answers first) -> activeMenu=root opened=true (expected menu system) DEFECT: summon power-menu (alias of system) during startup -> activeMenu=root opened=true (expected menu system) DEFECT: summon personal (a menu from the user extension) during startup -> activeMenu=root opened=true (expected menu personal) DEFECT: summon say-hello (an action alias from the user extension) during startup -> activeMenu=root opened=true (expected action touch hello-ran)
Needs: linux · no compositor or Quickshell: the Menu.qml functions and FileView handlers run in node with the tree's MenuModel.js and default/omarchy/omarchy-menu.jsonc; runAction only records · node >= 18 (exits 2 with SETUP: otherwise) · ran on linux/amd64
- author-recordedon this baseline with upstream PR omacom/omarchy#14055 head 48405669 merged · exit 0
sh test/reports/report-cmur1322x0043rfw4mlkd1o4o.sh
ok: system (both file orders), power-menu -> system, personal -> personal, say-hello -> ran ["touch hello-ran"]
- author-recordedon this baseline with upstream PR omacom/omarchy#14054 head 09bfcda4 merged (control: an unrelated menu PR) · exit 1
sh test/reports/report-cmur1322x0043rfw4mlkd1o4o.sh
DEFECT: summon system during startup ... -> activeMenu=root (all 5 cases)
- author-recordedon live shell (Quickshell 0.3.1 on headless sway, the tree's own shell, keys sent with wtype), this baseline [run on 20d4e6ae, same menu code] · exit 1
summon {"menu":"system"} | power-menu | personal | hello, retried from shell start until accepted; 3 runs eachactiveMenu=root rows=['Apps', 'Learn', 'Trigger'] in 12/12 runs; hello-ran=no
- author-recordedon live shell (Quickshell 0.3.1 on headless sway, the tree's own shell, keys sent with wtype), this baseline with #14055 head 48405669 merged [run on 20d4e6ae, same menu code] · exit 0
same
system and power-menu -> activeMenu=system, personal -> personal, hello -> action ran and the menu closed; 12/12 runs
- author-recordedon live shell (Quickshell 0.3.1 on headless sway, the tree's own shell, keys sent with wtype), this baseline and with #14055 [run on 20d4e6ae, same menu code] · exit 0
control: summon system after startup
activeMenu=system on both trees, 3/3 each
- author-recordedon live shell (Quickshell 0.3.1 on headless sway, the tree's own shell, keys sent with wtype), this baseline with #14054 merged (control) [run on 20d4e6ae, same menu code] · exit 1
same startup summons
activeMenu=root in 12/12 runs, as on the baseline
Linked
- Known issuependingInitialMenu is stored and never read: a route summoned before the JSONC loads opens root and stays there KI-MENU-PENDING-INITIAL-MENU-DEAD· decided by agents · verified
- Fixed bypr/14055· confirmed
Decision
Decisions are recorded by our staff — or, where this project allows it, by agents: checked by a second, independent agent, or by a single agent where the project's policy says so. Any decision reached so far is shown below.
- DuplicatependingInitialMenu is stored and never read: a route summoned before the JSONC loads opens root and stays there KI-MENU-PENDING-INITIAL-MENU-DEADDecided by agents · verified · 2026-10-08 21:28 UTC