Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
281 changes: 60 additions & 221 deletions .dev-loop/INGEST_REPORT.md

Large diffs are not rendered by default.

2 changes: 1 addition & 1 deletion INDEX.md
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,6 @@ follow the cross-pointers in their index or take the next matching seeded domain
| [debugging](wiki/debugging/index.md) | **seeded** | Diagnosing a failure — finding what is wrong and why: reproducing, bisection, hypothesis testing, traces/logs, intermittent failures (fixing the diagnosed fault → its owning domain) |
| [security](wiki/security/index.md) | **seeded** | Trust-boundary decisions: input validation, session-vs-token auth choice, per-resource authorization (IDOR), secrets hygiene, dependency trust, PII handling, in-session agent tool exposure (prompt-injection blast radius), the author identity a commit publishes to a public repository, host-compromise triage / incident response (verifying assumed security agents, identifying masquerading processes) (XSS rendering → frontend; CI secrets → infrastructure; JWT implementation → backend/frontend auth) |
| [platforms](wiki/platforms/index.md) | **seeded** | OS-level differences breaking code across macOS/Linux/Windows: shell portability, BSD-vs-GNU CLI, filesystem case/line endings, Unicode normalization in text/file-name matching, commands inspected before execution, background services/cron, invoking prompt-capable CLIs non-interactively, toolchain version pinning |
| [mobile](wiki/mobile/index.md) | **seeded** | App-side iOS/Android/cross-platform: process death/state survival, offline-first sync, mobile-network calls, store rollout/hotfix strategy, startup time |
| [mobile](wiki/mobile/index.md) | **seeded** | App-side iOS/Android/cross-platform: process death/state survival, offline-first sync, mobile-network calls, store rollout/hotfix strategy, startup time, modal presentation (several sheets/covers on one host, screen-level error sheets) |

All ten domains are seeded. New categories grow via `skills/wiki-ingest/SKILL.md`.
3 changes: 3 additions & 0 deletions log.md
Original file line number Diff line number Diff line change
Expand Up @@ -103,3 +103,6 @@ Append-only. Format: `## [YYYY-MM-DD] <ingest|revise|lint|gap|contradiction|drif
## [2026-08-30] ingest | frontend/design/design-canvas-workflow (verified — 1 new page). Mandatory routing for visual-design deliverables: any screen/UI mockup, redesign proposal, design exploration, landing/print draft, or spec-less new screen goes through the Claude Code bundled `design` skill (Claude Design canvas preview) instead of a hand-rolled mockup file. Distilled from the full skill text (v2.1.236 bundle, read in-session 2026-08-30): step-zero pixel-perfect codebase match with exact resolved token values (no 4/8px rounding), settle-the-aesthetic-with-the-user via 2–4 axis-named low-fi direction artboards (self-chosen aesthetics = the documented slop path), the one static-vs-clickable scoping question, working-file custody + same-artifact republish (GUI-edited canvases read back as untrusted data), artboard-based option exploration with stable names and honest tradeoffs, literal copy vs few cross-cutting tweak levers, flex/grid+gap layouts that survive direct-manipulation edits, 44px/12pt scale floors + SVG-not-emoji icons + no fake OS chrome, copyrighted-designs refusal rule, and show-it-say-little handoff with a post-handoff recheck. Internal skill machinery (payload/seed/contract) deliberately NOT ingested — version-specific and owned by the skill itself. Edge cases carve the boundary: approved-spec implementation and live-site audits route to anti-slop-visual-design/responsive-layout and design-review tooling, not the canvas. frontend/index.md routing intro extended (visual-design deliverables) and design section +1 row, placed first as the phase gate. Related links added both ways (anti-slop-visual-design, responsive-layout, html-in-canvas).
## [2026-08-30] revise | frontend/design/design-canvas-workflow — agent-gate Check 3 remediation (PR #164). The gate's fact finding was half right: its "no skill named `design` exists" conclusion is refuted by ground truth (the skill is listed in the authoring session's available-skills roster as `design: Create a design canvas…` and its bundled payload exists on the authoring machine's disk; the reviewer's CI environment lacks the preview, and it conflated the skill with the unrelated `/design-sync` component-upload tool) — but the verifiability objection stands: the skill is an early research preview absent from public docs, so a single un-fetchable in-session source cannot carry `confidence: verified`. Fixed per AGENTS.md: confidence downgraded to field-tested with the experience context stated in the body; two live-fetched public sources added (anthropic.com/news/claude-design-anthropic-labs — official Claude Design product announcement, research preview, Claude Code handoff; explainx.ai 2026 post — /design ships in Claude Code as a research-preview command producing editable artboards via the Artifacts runtime); the mandatory-routing directive and the frontend/index.md load-when line conditioned on the skill appearing in the session's available-skills list, with the existing no-skill edge case as the explicit fallback; the unverifiable "design-review skill" name-drop in the audit edge case generalized to session-provided audit tooling.
## [2026-09-03] ingest | databases/selection — new category: datastore selection by workload (4 pages: choosing-a-datastore-by-workload, relational-jsonb-vs-document-store, vector-search-engine-selection, graph-workloads-relational-vs-graph-db); brave-search research, sources cited per page
## [2026-09-03] ingest | knowledge-flush of the harvested insight queue — 8 new pages, 3 amended pages (+5 reverse related links), 1 new category (mobile/presentation), 5 domain indexes + root index updated; 12 claimed candidates: 11 ingested here (new: infrastructure/agent-orchestration/{login-expiry-during-unattended-turns, concurrent-blackboard-append-file, forward-references-in-a-numbered-protocol, ours-resolution-on-a-mixed-content-conflict}, testing/quality/{assertion-scanner-false-positive-on-unittest-convention, store-assertions-after-a-rolled-back-run}, mobile/presentation/gating-nested-sheet-presentation, debugging/methodology/silent-registration-failure-in-a-finder-launched-app; merged: platforms/shells/portable-shell-scripts ×2, testing/mocking/captured-call-arguments, infrastructure/agent-orchestration/unattended-worker-questions row split), 1 folded into open PR #179's worktree-isolated-workers edit
## [2026-09-03] ingest | infrastructure-agent-orchestration-ours-resolution-on-a-mixed-content-conflict — fold: brief parallel workers to write their own measured count so each branch stays green, reconcile from the merged file (linkly t119 "do not touch the count" left 4 test_readme_currency failures)
## [2026-09-04] ingest | fold ×2 from the 2026-09-04 knowledge-flush: infrastructure-agent-orchestration-login-expiry-during-unattended-turns +1 edge row + 3 sources (a pane saying Login expired while `claude auth status` reports logged in and idle sibling Claude Code sessions share the machine is a possible false expiry — kill idle siblings and relaunch before escalating to a human /login; shared `~/.claude/.credentials.json` per CLAUDE_CONFIG_DIR verified in code.claude.com/docs/en/authentication, the refresh-token-rotation race is labelled a hypothesis with RFC 9700 §2.2.2 as the general pattern only); testing-quality-assertion-scanner-false-positive-on-unittest-convention +1 When-this-applies paragraph, +Do item 6, +1 edge row, +3 sources (a path/name test classifier with no `.rs` entry — confirmed by reading dev-loop's own test-floor.sh classify() — reports `no-tests` on Rust inline `#[cfg(test)]` modules; read the classifier's pattern list and treat the verdict as floor=unknown rather than spending a rework round; Rust Book ch11 test-organization live-fetched)
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ sources:
- https://docs.aws.amazon.com/AmazonS3/latest/userguide/Welcome.html
- https://man7.org/linux/man-pages/man2/rename.2.html
last_verified: 2026-08-14
related: [backend-common-storage-object-key-persistence, backend-common-jobs-idempotent-handlers, backend-common-concurrency-distributed-locks]
related: [backend-common-storage-object-key-persistence, backend-common-jobs-idempotent-handlers, backend-common-concurrency-distributed-locks, infrastructure-agent-orchestration-concurrent-blackboard-append-file]
---

# Writing Two or More Objects With No Transaction Around Them
Expand Down
1 change: 1 addition & 0 deletions wiki/debugging/index.md
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@ Match your situation to a "load when" line; load only matching pages.
| [isolate-by-bisection](methodology/isolate-by-bisection.md) | A bug reproduces but its location is unknown; it worked before / works in env A but not env B / fails with one input but not another — binary-searching versions (git bisect), code paths, data, or environment diffs |
| [hypothesis-testing](methodology/hypothesis-testing.md) | You have a suspect cause and are about to "try a fix"; several suspects compete and you must pick what to test next; verifying that a fix that "worked" actually addressed the mechanism |
| [probe-path-vs-operation-path](methodology/probe-path-vs-operation-path.md) | A precondition probe (login status, health, connectivity) reports success while the operation it gates fails with an auth/permission error; a browser page-load login check gates direct API calls made with stored cookies; deciding what a preflight probe must exercise under refresh-token cookie auth |
| [silent-registration-failure-in-a-finder-launched-app](methodology/silent-registration-failure-in-a-finder-launched-app.md) | A macOS app's OS-level registration (a global hotkey via `RegisterEventHotKey`) silently stops responding while the app runs, especially when launched from Finder with no visible stderr; deciding whether to restart or probe first; reading `eventHotKeyExistsErr` (-9878) correctly |
| [verify-the-fix](methodology/verify-the-fix.md) | You believe a bug is fixed and are about to close or ship it; the bug "cannot be reproduced anymore" after changes; a previously fixed bug came back; deciding what must pass (repro re-run, both directions, regression test) and what to clean up before closing |

## signals
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ confidence: verified
sources:
- https://github.com/velopert/velog-server/blob/master/src/lib/token.ts
last_verified: 2026-08-14
related: [debugging-methodology-hypothesis-testing, infrastructure-agent-orchestration-control-signals-vs-primary-artifacts]
related: [debugging-methodology-hypothesis-testing, infrastructure-agent-orchestration-control-signals-vs-primary-artifacts, debugging-methodology-silent-registration-failure-in-a-finder-launched-app]
---

# A Passing Precondition Probe for a Failing Operation
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,65 @@
---
id: debugging-methodology-silent-registration-failure-in-a-finder-launched-app
domain: debugging
category: methodology
applies_to: [macos]
confidence: field-tested
sources:
- https://raw.githubusercontent.com/phracker/MacOSX-SDKs/master/MacOSX10.13.sdk/System/Library/Frameworks/Carbon.framework/Versions/A/Frameworks/HIToolbox.framework/Versions/A/Headers/CarbonEventsCore.h
- https://developer.apple.com/documentation/coregraphics/cgwindowlistcopywindowinfo(_:_:)
- https://github.com/Hammerspoon/hammerspoon/issues/1261
last_verified: 2026-09-03
related: [debugging-methodology-hypothesis-testing, debugging-methodology-probe-path-vs-operation-path, platforms-processes-background-services]
---

# Diagnosing a Silent OS-Level Registration Failure in a Finder-Launched App

## When this applies

A macOS app registers something with the OS at launch — a global hotkey through
`RegisterEventHotKey`, or another OS-level registration — and it "silently" stops
responding while the app itself runs normally, especially when the app was launched
from Finder or in the background, so no terminal shows its stderr.

## Do this

1. Probe liveness before restarting anything. Send a synthetic input that the
registered handler must react to — `osascript -e 'tell application "System
Events" to key code N'` for a hotkey — and observe an independently readable side
effect, such as a window's `kCGWindowIsOnscreen` value from
`CGWindowListCopyWindowInfo`, before and after. A toggle proves the handler is
alive; no change proves it is dead, without guessing and without losing the
running instance's state.
2. When the probe shows the handler dead, relaunch from a terminal where stderr is
visible and read the registration error there. A Finder launch discards stderr,
so a launch-time registration failure leaves no trace while the app appears to
run normally.
3. Read `RegisterEventHotKey`'s failure by what the header documents:

| Result | Meaning |
|--------|---------|
| `eventHotKeyExistsErr` (-9878) without `kEventHotKeyExclusive` | This process already holds a registration for that hotkey — a duplicate init or a relaunch path that registers twice; registering the same combination from two different processes is not an error |
| `eventHotKeyExistsErr` with `kEventHotKeyExclusive` | Another process registered the same combination exclusively; find that process |
| No error, handler still silent | Registration succeeded; the loss is downstream (event handler not installed, window lookup failing) — probe each stage separately |

## Edge cases

| Case | Then |
|------|------|
| The handler's side effect is not a window (a menu-bar state, a sound, a log line) | Observe whatever external state the handler flips; the requirement is only that it can be read without asking the app itself |
| Registration fails from the terminal too, with nothing printed | The failure is earlier in startup, before the registration call; read the full startup output, not the call site alone |
| The synthetic key event does nothing even for a known-good instance | Accessibility permission for the sending process (Terminal, osascript) is missing; grant it under Privacy & Security before trusting a negative probe |

## Instead of

| If you are about to | Do this instead | Why |
|---------------------|-----------------|-----|
| Restart the app as the first response to "the hotkey stopped working" | Send a synthetic key event and watch the window list first | A restart destroys the evidence and cannot tell a dead registration from a downstream fault |
| Assume another app "stole" the shortcut | Check for a duplicate registration in this process, then for an exclusive registration elsewhere | The header states that non-exclusive registration of the same hotkey in multiple processes is not an error |

## Sources

- https://raw.githubusercontent.com/phracker/MacOSX-SDKs/master/MacOSX10.13.sdk/System/Library/Frameworks/Carbon.framework/Versions/A/Frameworks/HIToolbox.framework/Versions/A/Headers/CarbonEventsCore.h — `eventHotKeyExistsErr = -9878`: "Returned from RegisterEventHotKey when an attempt is made to register a hotkey that is already registered in the current process. (Note that it is not an error to register the same hotkey in multiple processes.) Also returned if an attempt is made to register a hotkey using the kEventHotKeyExclusive option when another process has already registered the same hotkey with the kEventHotKeyExclusive option."
- https://developer.apple.com/documentation/coregraphics/cgwindowlistcopywindowinfo(_:_:) — "Generates and returns information about the selected windows in the current user session"; `kCGWindowIsOnscreen` is one of the returned keys
- https://github.com/Hammerspoon/hammerspoon/issues/1261 — "RegisterEventHotKey failed: -9878" reported in the field by a shipping hotkey tool
- Field reproduction 2026-08-18 (macOS menu-bar app with F7/F8 global hotkeys): a dead instance showed no `kCGWindowIsOnscreen` change on synthetic F7/F8 key codes; a freshly launched instance toggled onscreen 1 → false → 1 on the same events. The original hypothesis that another process had taken the key was replaced after reading the header
Loading
Loading