Skip to content

Restore pending request review after time away - #181

Merged
sudoHG merged 1 commit into
mainfrom
sudoHG/180-pending-after-away
Oct 11, 2026
Merged

sudoHG merged 1 commit into
mainfrom
sudoHG/180-pending-after-away

Conversation

@sudoHG

@sudoHG sudoHG commented Oct 11, 2026 •

Copy link
Copy Markdown
Owner

Closes #180

Summary

  • Manual review from locked management, the menu bar, or Pending requests brings an existing approval panel forward on the pointer display; initial presentation uses that display too, with key-window/main-screen fallbacks.
  • Esc advances to the next request while keeping deferred requests available for explicit review; expired or missing selections receive short generic feedback.
  • Expiration uses wall time and refreshes on wake/unlock; access records distinguish expiration as Expired without decision / 过期未处理.
  • The existing screen privacy policy, authentication, capability/payload binding, and delivery checks remain in force; replaced panels' stale callbacks cannot decide another request.

Diff stat

Compared with origin/main (7911b85cec8a43796c35d49752275471bf6776fa): 20 files changed, 676 insertions, 47 deletions. Production changes cover approval presentation/placement, wake cleanup, expiration scheduling, terminal-result copy and menu feedback; tests add injected screen/panel/clock coverage and update the organization expiry expectation.

Tests

  • Diagnosis gate: swift test --scratch-path .build/issue-180 --filter 'AgentApprovalPresentationCoordinatorTests|ApprovalAwayExpirationTests|AgentApprovalExpiryRecordTests' passed 6 / 0 failed / 0 skipped before behavior changes, after extracting the presentation seam without changing behavior. These observational tests reproduced the current faults, then became regression assertions.
  • swift build --scratch-path .build/issue-180: PASS.
  • swift test --scratch-path .build/issue-180 --filter 'AgentApprovalPresentationCoordinatorTests|AgentApprovalPanelPlacementTests|AgentApprovalPrivacyTests|AgentApprovalScreenSessionTests|AgentApprovalPanelTests|ScreenPresentationTests|ManagementAuthenticationTests|ApprovalStateMachine.*Tests|ApprovalAwayExpirationTests|AgentTextWriteApprovalLifecycleTests|AgentApprovalExpiryRecordTests|AgentOrganizationConcurrencyTests|CredentialAccessRecordTests|AppLanguageCatalogTests': 96 passed / 0 failed / 0 skipped (Vault 25, Broker 20, App 51).
  • Baseline comparison: the same existing suites total 72 passed / 0 failed in main CI at 7911b85; this PR adds 24 tests. The full suite is reserved for PR CI.
  • Final-head PR CI at 94ecdcdd243635b73f3f23186c98374a62c0cd2e: run 38101185262 is SUCCESS; build-and-test and basic-ui-flows are both SUCCESS.
  • CI swift test: 1,130 executed = 1,127 passed / 0 failed / 3 skipped, versus main 1,106 executed = 1,103 passed / 0 failed / 3 skipped at 7911b85 (+24 tests, unchanged skips).
  • CI bash scripts/run-e2e.sh: 15 passed / 0 failed / 0 skipped, with the required basic E2E gate passed; optional screenshots and evidence upload also succeeded. This does not verify real Touch ID, two-display placement, or external client environments.
  • CI python3 -m unittest discover -s Tests/Automation -v: 183 passed / 0 failed / 0 skipped.

Checks

  • python3 scripts/check_hygiene.py: PASS; all seven violation counts zero, including source size and test-support rules.
  • python3 scripts/check_module_deps.py: PASS.
  • git diff --check: PASS.
  • CI release-symbol, optimized cancellation (debug and release), isolated development launcher, hygiene, and module checks: all PASS.
  • Disk admission: 365 GiB free before the final local run; only task-specific scratch output was used, with no ASKKEY_* overrides.
  • Cleanup: the task scratch directory (approximately 1 GiB) was deleted after lsof found no open files; consumed local/CI logs were deleted. Current disk availability is 365 GiB.
  • No app launch, desktop driving, screenshots, local E2E, real credentials, production vault/keychain access, installation, or changes to authentication/broker protocol.

Confirmed root causes and limits:

  1. An already-open panel was ignored by presentingApproval, and initial panel.center() used the main display; injected panel state proves manual review did not focus/move it. Physical occlusion and the exact display of the reported incident remain device-only evidence.
  2. Esc's finish(nil) did not advance. The old expiry/request-ended timer already advanced explicitly, so this diagnosis is narrower than the issue's initial hypothesis. The coordinator now owns all dismissal transitions and avoids reopening a deferred request in a loop.
  3. An expired synthetic create request produced .denied; organization and runtime terminal cleanup shared that mapping. New expiry records use .expired, while explicit denial/cancellation retain their previous result. Historical denied records are unchanged because the old format cannot distinguish these causes.
  4. Pausing the timer and advancing the injected clock left pending observers stale until another clock-checking call. Wake/unlock now explicitly refresh expiration before the privacy gate, and scheduling uses wall time. Apple's DispatchTime documentation confirms uptime excludes sleep; this is a related defect, not an explanation for the reported no-sleep brief absence.
  5. A missing/expired selected request previously returned without feedback; locked/unknown system screens could also suppress repeated notifications. Manual actions now give generic feedback without loading request details on those screens.

Deviations and questions

The Orca diagnosis gate was answered and approved in task task_7993e3ade9bf, dispatch ctx_2a4dc9099adf; the coordinator additionally required pointer-display placement for initial automatic presentation and one-line feedback. No issue comments or status-label changes were made.

Device repro: NOT_RUN under the task's no-local-desktop restriction. After approving a candidate, the maintainer can:

  1. With two displays, leave management locked and macOS unlocked; submit a synthetic create request, work on display 2 and cover the first prompt, then click the locked-management review action. Verify the same bound prompt moves forward on display 2; repeat from the menu bar and a selected Pending row.
  2. Queue requests A and B, defer A with Esc, and verify B opens; defer B and verify both remain available for explicit review without reopening in a loop.
  3. Leave a request beyond five minutes; verify the pending count clears, an old review action reports that it ended, and the access record says 过期未处理 / Expired without decision without creating the credential.
  4. Separately sleep across the TTL, wake while macOS stays locked, and verify no request details appear; after system unlock verify the count is zero and the expired record is present. This does not attribute the original no-sleep incident to sleep.

@sudoHG
sudoHG merged commit f99baf7 into main Oct 11, 2026
2 checks passed
@sudoHG
sudoHG deleted the sudoHG/180-pending-after-away branch October 11, 2026 01:32
This was referenced Oct 11, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Pending agent requests can't be handled after the Mac was away

1 participant