Skip to content

fix: validate remote observations before publishing files - #725

Merged
steipete merged 2 commits into
mainfrom
fix/phase5-observation-file-publication-20260912
Sep 13, 2026
Merged

fix: validate remote observations before publishing files#725
steipete merged 2 commits into
mainfrom
fix/phase5-observation-file-publication-20260912

Conversation

@steipete

Copy link
Copy Markdown
Collaborator

Remote observations could overwrite a caller's screenshot before the client rejected inconsistent response evidence. Ordinary captures now use the same private staging boundary as ROI captures: validate identity, raster, and digest before publishing caller files. Annotation-only and snapshot-only requests retain verified image data without modifying the raw destination. Host-owned snapshot behavior and ROI rollback semantics remain intact.

Addresses the remaining premature-file-publication problem reported in #710. The separate screen/Accessibility attribution fix landed in #722. Removes a stale description above the actual AX delegation while touching that path.

Validation: 30 focused remote capture ownership tests passed, including new rejected-evidence tests that failed against the old implementation. Isolated Codex review found no actionable P0–P2 findings; lint, format, and docs checks passed. The shared-process Bridge fixtures are serialized to prevent competing short-deadline fixture hosts; their existing deadlines and assertions remain unchanged.

Native proof used a signed external consumer of RemoteDesktopObservationService and two signed Bridge hosts, negotiating protocol 1.38. The old host reproduced the actual unexpected-application-evidence refusal. With the patched consumer, a rejected new destination remained absent and a rejected existing 21-byte sentinel remained unchanged. A valid host observation succeeded with 12 AX elements and a verified 1,617,793-byte raster. Images were removed after validation; only structural results were retained. This protects high-level remote caller destinations; it does not change the low-level Bridge API's publication contract.

@clawsweeper

clawsweeper Bot commented Sep 13, 2026

Copy link
Copy Markdown

🦞👀
ClawSweeper picked this up.

Pull request received. I will update this pull request when review starts.

ClawSweeper review complete

ClawSweeper finished reviewing this revision. The review result is being finalized.

View the workflow run.

@cursor

cursor Bot commented Sep 13, 2026

Copy link
Copy Markdown

PR Summary

Medium Risk
Changes when remote observation screenshot files hit caller paths—a security-sensitive publication boundary—but ROI rollback semantics are preserved and new rejection tests cover the failure modes.

Overview
Remote desktop observations that request screenshot files now follow the same quarantine-and-validate path previously used only for ROI captures, so caller --path destinations are not written until identity, raster, and digest checks succeed.

Ordinary captures with saveRawScreenshot, annotated output, or snapshots are staged under a private temp directory (mode 0700), the bridge is forced to write the raw raster to quarantine, and artifacts are installed atomically only after validation. Rejected accessibility evidence throws without touching an existing file or creating a new one at the caller path. Annotation-only / snapshot-only requests keep verified image data in the result without overwriting the raw destination when saveRawScreenshot is false.

ROI behavior is unchanged in spirit: deferred snapshot commit, staged rollback, and ROI-specific validation still apply; shared preparation is generalized (prepareObservationResult) with appropriate digest and imageData handling per request shape.

Adds serialized integration tests for publication ownership, changelog/docs notes, and trims a misleading long doc comment on detectElements to match AX delegation.

Reviewed by Cursor Bugbot for commit e1c642d. Bugbot is set up for automated code reviews on this repo. Configure here.

@clawsweeper clawsweeper Bot added P2 Normal priority bug or improvement with limited blast radius. merge-risk: 🚨 compatibility 🚨 Merging this PR could break existing users, config, migrations, defaults, or upgrades. proof: sufficient Contributor real behavior proof is sufficient. rating: 🦐 gold shrimp Decent PR readiness signal, but merge confidence is limited. status: ⏳ waiting on author ClawSweeper has contributor-facing work open and is waiting for author action. labels Sep 13, 2026
@clawsweeper

clawsweeper Bot commented Sep 13, 2026

Copy link
Copy Markdown

Codex review: blocked before merge. Reviewed September 12, 2026, 9:04 PM ET / September 13, 2026, 01:04 UTC (Revision 2).

ClawSweeper review

What this changes

Stages ordinary remote screenshots privately before validating and publishing them, preserves raw destinations for annotation-only and snapshot-only requests, and updates tests and documentation.

Regression provenance

Possible regression — suspected (reviewed change). No predecessor PR is attributed.

Merge readiness

Blocked before merge - 3 items remain

The publication fix remains necessary, but the previously reported Accessibility recovery regression is still present at the updated head. The contribution is useful and should remain open.

Priority: P2
Reviewed head: e1c642dadf6d0740e288909bdfec328f29270a8e

Review scores

Measure Result What it means
Overall readiness 🦐 gold shrimp (3/6) Useful implementation and native proof are offset by an unresolved, source-proven recovery regression.
Proof confidence 🐚 platinum hermit (4/6) Sufficient (live_output): The captured native run exercises the changed remote service through signed Bridge hosts and records protected destinations on rejection plus a valid verified capture. This remains positive proof of the central fix; the separate host-thrown Accessibility recovery defect still blocks merge.
Patch quality 🦐 gold shrimp (3/6) 1 actionable review finding remain.

Verification

Check Result Evidence
Real behavior Verified Sufficient (live_output): The captured native run exercises the changed remote service through signed Bridge hosts and records protected destinations on rejection plus a valid verified capture. This remains positive proof of the central fix; the separate host-thrown Accessibility recovery defect still blocks merge.
Evidence reviewed 7 items Introduced publication boundary: Ordinary requests that save artifacts now enter the quarantine path. The host receives that private destination, and the directory is removed on exit, including when the Bridge call throws.
Production error path loses the staged raster: The production observation service writes the valid raster, disables snapshot publication for unusable Accessibility evidence, and then throws before constructing its result. Bridge capture handling propagates that failure; the client's later evidenceError publication branch cannot receive this raster.
Established recovery contract: The existing combined-observation regression test requires accessibilityIncomplete while preserving the requested raster and publishing no snapshot. The same behavior is documented in docs/commands/see.md at line 181.
Findings 1 actionable finding [P1] Preserve valid rasters when the host reports incomplete Accessibility
Security None None.

How this fits together

Peekaboo’s remote observation service sends capture requests to a local Bridge host and validates the returned screenshots and Accessibility evidence. It then exposes image files and snapshot references to CLI and API callers.

flowchart TD
  A[CLI or API capture request] --> B[Remote observation service]
  B --> C[Bridge host capture]
  C --> D[Private screenshot staging]
  D --> E[Validate response and raster]
  E --> F[Publish requested files]
  C --> G[Host error]
  G --> H[Delete staged files]
Loading

Before merge

  • Preserve valid rasters when the host reports incomplete Accessibility (P1) - This previously reported blocker remains unresolved. Ordinary artifact requests now send a quarantine destination to the host. DesktopObservationService writes the valid raster and then throws accessibilityIncomplete before returning a result, so the Bridge call throws and the deferred cleanup deletes the only screenshot. The later evidenceError branch is never reached. This breaks the documented explicit-path recovery behavior. Preserve it through validated error-path evidence and add a Bridge regression using the production observation service; do not publish arbitrary staged files after an error.
  • Resolve merge risk (P1) - Existing callers that rely on the documented diagnostic screenshot after ACCESSIBILITY_INCOMPLETE would stop receiving it after upgrading.
  • Complete next step (P2) - Preserve validated diagnostic screenshots across host-thrown ACCESSIBILITY_INCOMPLETE and add production-service Bridge regression coverage.

Findings

  • [P1] Preserve valid rasters when the host reports incomplete Accessibility — Core/PeekabooCore/Sources/PeekabooCore/Support/RemoteDesktopObservationService.swift:131-135
Agent review details

Security

None.

Review metrics

Metric Value Why it matters
Source and test delta Production Swift +65/-86; tests +138/-2 The implementation growth is justified by publication staging; removal of a long obsolete comment makes the production source delta net negative.

Merge-risk options

Maintainer options:

  1. Preserve validated Accessibility failure output (recommended)
    Repair the host-error recovery path and cover it through the production observation service over Bridge before merging.
Copy recommended automerge instruction
@clawsweeper automerge

Special instructions:
Preserve explicitly requested diagnostic rasters on host-thrown ACCESSIBILITY_INCOMPLETE using validated response evidence; never publish arbitrary quarantine files after an error. Add production-observation-over-Bridge regression coverage and retain invalid-evidence rejection and ROI rollback behavior.

Technical review

Best possible solution:

Preserve validated diagnostic rasters across host-thrown Accessibility failures while keeping rejected identity/content evidence private and unusable snapshots unpublished.

Do we have a high-confidence way to reproduce the issue?

Yes, from source: a combined observation with empty Accessibility evidence writes its raster and throws on the host; the patched remote client then deletes that staged raster. No runtime tests were executed during this read-only review.

Is this the best way to solve the issue?

Not yet: private staging is appropriate, but recovery must carry validated diagnostic evidence through the host error path before the implementation preserves the existing contract.

Full review comments:

  • [P1] Preserve valid rasters when the host reports incomplete Accessibility — Core/PeekabooCore/Sources/PeekabooCore/Support/RemoteDesktopObservationService.swift:131-135
    This previously reported blocker remains unresolved. Ordinary artifact requests now send a quarantine destination to the host. DesktopObservationService writes the valid raster and then throws accessibilityIncomplete before returning a result, so the Bridge call throws and the deferred cleanup deletes the only screenshot. The later evidenceError branch is never reached. This breaks the documented explicit-path recovery behavior. Preserve it through validated error-path evidence and add a Bridge regression using the production observation service; do not publish arbitrary staged files after an error.
    Confidence: 0.99

Overall correctness: patch is incorrect
Overall confidence: 0.98

AGENTS.md: found and applied where relevant.

Codex review notes: model internal, reasoning medium; reviewed against 01b8b3118043.

Labels

Label justifications:

  • P2: This is a bounded remote screenshot publication repair with a specific compatibility blocker.
  • merge-risk: 🚨 compatibility: The new staging path removes the documented diagnostic raster when a production host throws ACCESSIBILITY_INCOMPLETE.
  • rating: 🦐 gold shrimp: Overall readiness is 🦐 gold shrimp; proof is 🐚 platinum hermit and patch quality is 🦐 gold shrimp.
  • status: ⏳ waiting on author: ClawSweeper has contributor-facing work open and is waiting for author action. Sufficient (live_output): The captured native run exercises the changed remote service through signed Bridge hosts and records protected destinations on rejection plus a valid verified capture. This remains positive proof of the central fix; the separate host-thrown Accessibility recovery defect still blocks merge.
  • proof: sufficient: Contributor real behavior proof is sufficient. The captured native run exercises the changed remote service through signed Bridge hosts and records protected destinations on rejection plus a valid verified capture. This remains positive proof of the central fix; the separate host-thrown Accessibility recovery defect still blocks merge.

Evidence

Acceptance criteria:

  • [P1] swift test --package-path Core/PeekabooCore --filter RemoteCaptureGateOwnershipTests.
  • [P1] swift test --package-path Core/PeekabooCore --filter RemoteDesktopObservationFailurePreservationTests.
  • [P1] swift test --package-path Core/PeekabooAutomationKit --filter DesktopObservationServiceTests.
  • [P1] pnpm run lint.
  • [P1] pnpm run format.

What I checked:

Likely related people:

  • steipete: Suggested for follow-up; no historical authorship or introduction is verified. (role: unverified routing candidate; confidence: low)

Rank-up moves

Optional improvements that raise the rating; they are not merge blockers.

  • Repair host-thrown ACCESSIBILITY_INCOMPLETE handling and verify through Bridge that the requested diagnostic raster survives while unusable snapshots remain unpublished.

Rating scale

Score Internal tier Crab rank Meaning
6/6 S 🦀 challenger crab Exceptional readiness
5/6 A 🦞 diamond lobster Very strong readiness
4/6 B 🐚 platinum hermit Good normal PR; ordinary maintainer review
3/6 C 🦐 gold shrimp Useful, but confidence is limited
2/6 D 🦪 silver shellfish Proof or implementation needs work
1/6 F 🧂 unranked krab Not merge-ready
N/A NA 🌊 off-meta tidepool Rating does not apply

Overall follows the weaker of proof and patch quality.
Shiny media proof means a screenshot, video, or linked artifact directly shows the changed behavior. Runtime, network, CSP, and security claims still need visible diagnostics.

Workflow

  • ClawSweeper keeps one durable marker-backed review comment per issue or PR.
  • Re-runs edit this comment so the latest verdict, findings, and automation markers stay together instead of adding duplicate bot comments.
  • A fresh review can be triggered by eligible @clawsweeper re-review comments, exact-item GitHub events, scheduled/background review runs, or manual workflow dispatch.
  • PR/issue authors and users with repository write access can comment @clawsweeper re-review or @clawsweeper re-run on an open PR or issue to request a fresh review only.
  • Maintainers can also comment @clawsweeper review to request a fresh review only.
  • Fresh-review commands do not start repair, autofix, rebase, CI repair, or automerge.
  • Maintainer-only repair and merge flows require explicit commands such as @clawsweeper autofix, @clawsweeper automerge, @clawsweeper fix ci, or @clawsweeper address review.
  • Maintainers can comment @clawsweeper explain to ask for more context, or @clawsweeper stop to stop active automation.

History

Review history (1 earlier review cycle)
  • reviewed 2026-09-13T00:50:29.064Z sha 703efd8 :: blocked before merge. :: [P1] Preserve valid rasters when the host reports incomplete Accessibility

@cursor cursor Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Cursor Bugbot has reviewed your changes using default effort and found 1 potential issue.

Fix All in Cursor

❌ Bugbot Autofix is OFF. To automatically fix reported issues with cloud agents, enable autofix in the Cursor dashboard.

Reviewed by Cursor Bugbot for commit 703efd8. Configure here.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

merge-risk: 🚨 compatibility 🚨 Merging this PR could break existing users, config, migrations, defaults, or upgrades. P2 Normal priority bug or improvement with limited blast radius. proof: sufficient Contributor real behavior proof is sufficient. rating: 🦐 gold shrimp Decent PR readiness signal, but merge confidence is limited. status: ⏳ waiting on author ClawSweeper has contributor-facing work open and is waiting for author action.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant