Conversation
1d4e0a6 to
ae5b1ba
Compare
ae5b1ba to
bf85705
Compare
a7a8424 to
f5ea382
Compare
(cherry picked from commit ef1e30a)
Salvaged from #2746. Co-authored-by: Francesco Bonacci <195596869+f-trycua@users.noreply.github.com> Co-authored-by: Zane Chee <zanechee@users.noreply.github.com>
Keep modality and focus as internal resolver facts. Publish only the window identity needed for logical rebinding, and ignore unrelated foreground changes. Co-authored-by: Francesco Bonacci <195596869+f-trycua@users.noreply.github.com>
Adapt pi-computer-use’s cheap signal and authoritative AX diff while retaining Cua Driver ownership proof, focus suppression, and typed action accounting.
f5ea382 to
b131ca4
Compare
|
successfully ran the lume e2e test |
|
@injaneity thanks — the target-scoped structure here is a real improvement over the global detector. I did a blast-radius pass; four questions gate merge for me, two are nice-to-have, and the items at the end are maintainer-side so I'll resolve them myself. Merge-gating1. Lume matrix evidence. Re "successfully ran the lume e2e test": which exact SHA did that certify, and was it the full 2. Consumers of the removed surface.
3. Focus-suppression divergence — intentional? 4. Ordering vs #3391. If this lands and #3391 lags, can the decorator's suppression lease and the existing admission path double-lease in the interim? If yes, what's the observable failure mode, and is it benign? Nice-to-have5. Windows/Linux follow-through. Does #2238 stay open to track equivalent observers on Windows (modal dialogs) and Linux (GTK/Qt file choosers)? A cheap per-platform test asserting 6. Why 400 ms? Tuned empirically on the host probe, or inherited from pi-computer-use? A one-line comment on Maintainer-side (I'll handle these)
|
|
thanks for the detailed review. i’m taking the follow-up here in this pr, not in a separate implementation. i added the exact lume SHA, full-matrix command, 158 passing rows, refusal counts, environment, and local evidence location to the description. the run was the full unfiltered matrix, not just the new TextEdit row. it certifies i’m treating the removed embedded opt-out, old evidence payload compatibility, foreground-without-window suppression, and interim lease ordering as unresolved until checked and covered. the current repository search finds the old opt-out helper/test but no caller on main; that alone does not establish that external embedding clients are unused. i’ll avoid claiming that it is safe to remove solely on that search. the requested rebase and any runtime/contract corrections will require a new exact-candidate run. the earlier approval and old certification should not be used to waive your re-review. #2238 remains open; this pr uses Refs rather than a closing keyword. |
f-trycua
left a comment
There was a problem hiding this comment.
I am withdrawing my earlier approval because the current diff has two release blockers:
- It removes the public UniFFI
ActionEvidenceKind::WindowChangeenum variant while the PR is titled as an additive non-breaking feature. Existing generated SDK consumers can depend on that variant. Preserve backward compatibility or explicitly treat and title this as a breaking release with a migration path. - Every affected macOS action now performs a post-action observation window with a 400 ms wait plus catch-up reads. That is a broad latency/behavior change across click, drag, key, text, scroll, value, and zoom, not a narrow topology annotation. The old 158/158 Lume evidence predates the requested rebase, and the branch now conflicts with
main; it cannot certify the current candidate.
Please rebase without dropping landed contributor work, settle the public contract/release semantics, measure action latency before and after on representative fast and no-new-window paths, and rerun the full canonical macOS matrix at the final exact SHA. The typed rebind direction is useful, but the present conflicted and breaking candidate is not ready.
f-trycua
left a comment
There was a problem hiding this comment.
I am withdrawing my earlier approval because the current diff has two release blockers:
- It removes the public UniFFI
ActionEvidenceKind::WindowChangeenum variant while the PR is titled as an additive non-breaking feature. Existing generated SDK consumers can depend on that variant. Preserve backward compatibility or explicitly treat and title this as a breaking release with a migration path. - Every affected macOS action now performs a post-action observation window with a 400 ms wait plus catch-up reads. That is a broad latency/behavior change across click, drag, key, text, scroll, value, and zoom, not a narrow topology annotation. The old 158/158 Lume evidence predates the requested rebase, and the branch now conflicts with
main; it cannot certify the current candidate.
Please rebase without dropping landed contributor work, settle the public contract/release semantics, measure action latency before and after on representative fast and no-new-window paths, and rerun the full canonical macOS matrix at the final exact SHA. The typed rebind direction is useful, but the present conflicted and breaking candidate is not ready.
|
I think there is one source-level contract bug beyond the already-recorded release/latency blockers: a surface rebind currently hides the actuator's own escalation. The internal API explicitly says: /// Attach observer facts without changing the actuator's effect or
/// overwriting its internal escalation account.
pub fn observe_surface_delta(&mut self, delta: ActionSurfaceDelta) {
self.surface_delta = Some(delta);
}But escalation: projection
.surface_delta
.as_ref()
.map(|delta| ActionEscalation {
target: Rebind,
reason: SurfaceChanged,
...
})
.or_else(|| projection.escalation.map(...))So whenever a surface delta exists, the That can lose information from a completely different axis. For example:
The action effect itself remains truthful, but the recovery plan no longer is. This seems especially risky because topology and actuation are deliberately independent in this PR: “a new surface appeared” does not prove that rebinding is the only or highest-priority next step. I would keep those facts structurally separate rather than choose one silently. The smallest contract shape may be to put the exact optional rebind target on A focused regression can construct:
This is the recovery lesson I'd preserve here: fresh topology tells the caller where to observe next; it must not erase what the actuator already proved about how the previous action failed. |
why
#2238 describes a stale-target failure: an action starts against window a, opens a sheet, dialog, popover, or Open/Save panel b, and leaves the caller bound to a. later snapshots and actions then target the blocked parent instead of the new interaction surface.
cua-driver already noticed some new macos windows, but its global detector could not prove that a desktop change belonged to the action. it also kept the result in diagnostic prose, so callers received neither a stable window address nor a machine-readable rebind instruction.
this pr resolves the structured-rediscovery part of the issue. after an action opens a target-owned surface, the result identifies the observed candidates and recommends
rebind. when exactly one candidate is owner-verified, the result includes its(pid, window_id)so the caller can take a fresh window-scoped snapshot without activating or raising it.design
retained from cua-driver
this keeps cua-driver's native action routes, focus-suppression leases, shared
ActionExecutionRecord, closedActionResult, and harness-owned escalation policy. it also retains the useful contract work from #2746: typedwindow_changemetadata, an explicitrebindescalation, and generated rust, python, typescript, and manifest bindings.it removes the unsafe parts of the old path: the desktop-global
WindowChangeDetector, seven per-tool diagnostic suffix mutations, the dead observation-skip hook, topology transport through legacy json, and window changes as evidence that an actuator succeeded.adapted from pi-computer-use
this adapts the target-root observation model from
injaneity/pi-computer-usecommit022a280a377065c95736cc15f684bf1fad46479e:the persistent ax-observer ring is intentionally not copied because the source commit established that sheet creation emits no reliable notification; it adds lifecycle state without improving correctness here. cua-driver instead merges
AXSheetswithAXChildren, keeps its focus-suppression lease across dispatch and observation, and resolves owners only after the authoritative ax diff. unresolved appeared roots retry WindowServer ownership independently; an incomplete owner set can return known candidates but never an exact target.combined result
observation and action accounting remain separate. a surface change can add
window_changeandescalation, but it cannot promoteeffecttoconfirmed; confirmation still requires value readback. ambiguous candidates are returned without an invented exact target and can be correlated with one freshlist_windowscall.issue coverage
this pr covers the structured rebind rung from #2238:
rebind, with an exact target only when ownership and modal/focused state make it unambiguous;it does not implement the issue's later privacy-sensitive desktop-frame fallback or inert-resnapshot backstop. those remain separate because this structured path recovers without widening capture scope. this pr therefore uses
Refs, not an issue-closing keyword.diff shape
the runtime production diff is
+899/-829(net+70). the new 411-line observer replaces the deleted 530-line global detector, while affected macos tool files remove 203 lines and add 79. most apparent growth is required generated contract output:+1103/-157across the manifest and python/typescript bindings.logical-root correction
host investigation found that AppKit can expose two Open-panel WindowServer records: an AX-addressable same-process TextEdit proxy and an AX-empty XPC duplicate.
pi-computer-usekeeps the target-scoped AX identity rather than requiring the foreign service pid. this branch now does the same: it preserves the appeared AX root's exact WindowServer identity, removes internal modal/focus eligibility state, and rebinds whenever exactly one owner-verified logical root appears. ambiguity still omits the exact target.on the host probe, the returned TextEdit proxy exposed 62 Open-panel AX elements; the XPC duplicate exposed none. a direct exact-head action returned
escalation.target: rebind, the proxy(pid, window_id), and a successful fresh scoped snapshot without changing the foreground app.compatibility and validation
macos emits the new optional topology. windows and linux emit none rather than substituting a global heuristic. generated sdk consumers gain optional
window_changeplus therebindandsurface_changedenum values.local validation passed:
cargo check --workspace --all-targetscargo test -p cua-driver-contract --lib— 33 passedcargo test -p cua-driver-core --lib— 587 passed at rebased headf5ea38210932db1389c199bc768891a21b9782e0cargo test -p platform-macos --lib— 338 passed, 2 ignored at the same shaa2d513b93ac6122ad4dd8639e3e1ec7c88bca5cf— one typed rebind to an AX-addressable logical root with 62 elements and unchanged foregrounda2d513b93ac6122ad4dd8639e3e1ec7c88bca5cfwith #2907 — 140 of 158 cells passed;macos-textedit-open-panel-background-rebindpassed all five declared oracles. the 18 unrelated failures were host input-isolation, cursor, desktop-coordinate, and video-finalization failures, so this is diagnostic evidence rather than canonical acceptancebefore this pull request is ready, the final candidate still needs the canonical macos Lume matrix. the local host can run the complete matrix when the foreground-sentinel fix in #2907 is included, but its active desktop is not an acceptance environment: cursor movement, global-coordinate delivery, and concurrent recordings caused unrelated failures. maintainers must also confirm whether this additive public contract requires a separate rfc.
Salvaged from #2746.
Refs #2238.
stacked scheduling follow-up
The stacked draft #3391 replaces duplicate native action admission with one scheduler and canonical lease plan, ensuring this pull request's before/action/after decorator remains inside the same desktop action lease. It does not add another observation owner or change the public tool contract.
canonical macos lume evidence — 2026-09-04
b131ca4f8e22650a8ed992df228f659b93eb9640(the current PR head, not a merge commit).libs/cua-driver/tests/runners/macos-lume/run-all.sh, full unfiltered matrix; no retry or single-cell selector.20260904T181935Z-11114.macos-tahoe-cua:26.5.2worker, macOS 26.5.2 build 25F84, SIP disabled, stable local certificate, app-owned grants seeded with the repository helper, and a logged-in guest Terminal session.macos-textedit-open-panel-background-rebind: passed AX state, focus, z-order, cursor, and no-leaked-input checks.failures.json:failure_count=0,preflight_failed=false,report_failed=false, no failed lanes or video failures.~/workspaces/cua-pr-3373-b131ca4f/artifacts/cua-driver/vm/lume_192.168.64.2/20260904T184538Z/(local evidence, not a public download link).This certifies only the SHA above. The requested rebase and review fixes remain outstanding; this evidence must not be presented as certification of a later candidate.