microsoft / microsoft/winappCli
[Feature]: Add bounded ui tab-trace focus diagnostic
Nobody has claimed this yet.
- Dominant language
- C#
- Stars
- 1.3k
- Forks
- 80
- Avg merge
- 3d 6h
- Merged PRs (30d)
- 51
Description
### Is your feature request related to a problem? Please describe.
Tracing keyboard focus today requires repeatedly composing `winapp ui get-focused` and `winapp ui send-keys`, which is slow and race-prone for agents and developers. A hands-on Paint trace captured 13 focus states but took many commands. Existing accessibility tooling was intrusive/incomplete for this debugging task.
This is blocked by #691. For hosted apps such as Calculator, the visible HWND belongs to `ApplicationFrameHost` while focused UIA controls belong to `CalculatorApp`; current PID equality filtering makes `ui get-focused -w ` report no focus.
### Describe the solution you'd like
After **#691 Stage 1** lands, add a narrow diagnostic:
```powershell
winapp ui tab-trace -a
winapp ui tab-trace -w
winapp ui tab-trace -a --reverse
winapp ui tab-trace -a --max-steps 20 --json
```
#### Job to be done
Send bounded, user-equivalent `Tab` or `Shift+Tab` input to a selected window and factually record the UIA keyboard-focus state observed before and after each key.
It is **not** an accessibility-compliance checker, a tab-order correctness validator, or a complete keyboard-navigation audit. It must not output pass/fail, valid/invalid, expected order, or compliance claims.
#### V1 UX
- `--app/-a` or `--window/-w` selects the target using existing conventions.
- Default traversal is `Tab`; `--reverse` sends `Shift+Tab`.
- `--max-steps` defaults to **20** and is bounded.
- Existing `--timeout` bounds the whole run (default 30 seconds).
- Use guarded `SendInput` only; do **not** expose a `--via` transport option. `post-message` can silently fail for XAML/UWP controls.
- Start at the currently focused element. No selector/start-focus option in v1.
- Before every key, verify the selected input-root HWND is foreground. Stop before any later injection on foreground loss, focus escape, or scope uncertainty.
- Stop normally on maximum steps, target escape, scope uncertainty, or overall timeout. A repeated focus identity is reported as `revisitedStep`; it is not a correctness verdict.
Example text:
```text
Tracing Tab focus in Paint (HWND 0x0001A2B3)
0 observed Button "Paste"
1 Tab observed Button "Select"
2 Tab observed Button "Crop"
Stopped: focus escaped the target window after 13 steps.
```
#### Required shared prerequisite
Consume the focus snapshot/membership operation from #691 rather than reimplementing it. A focus snapshot must distinguish no focus, provider/read error, focus outside target, and focus in a hosted foreign-PID descendant. Target membership is based on top-level HWND/UIA subtree containment, never PID equality.
#### Output and exit behavior
- Text output is factual and concise.
- `--json` emits one NativeAOT-safe result document with `schemaVersion`, provenance, initial snapshot, steps, warnings, and terminal reason.
- Each step records requested key, injection outcome (`injected` means Windows accepted input only), before/after snapshots, target relation, settle timing, and optional `revisitedStep`.
- Return **0** for a finalized factual trace, including escape, revisit, max steps, unchanged focus, or timeout.
- Return **1** for invalid options/target, unavailable interactive desktop, foreground loss, injection failure, or unrecoverable UIA sampling failure. Emit valid partial JSON before a mid-run failure where possible.
- Return **130** after Ctrl+C finalizes partial output.
- Do not ship NDJSON in v1. Reconsider only if a demonstrated streaming consumer needs it.
#### Implementation and validation boundaries
1. #691 Stage 1: shared focus snapshot + UIA/HWND membership, including hosted Calculator focus.
2. Add `UiTabTraceCommand` and a bounded trace state machine using SendInput plus polling/settled snapshots. Do not depend on `ui watch` or UIA event callbacks in v1.
3. Update CLI schema, UI automation docs, skill fragment/generated skills, and tests.
Acceptance criteria:
- One invocation reproduces the existing Paint 13-state trace in order across three local interactive runs.
- Targeting Calculator by app/frame HWND reports CalculatorApp focus as in-target; a child-process PID is not required.
- Tests prove no key is injected after foreground loss, target escape, or scope uncertainty.
- Launch evidence covers local interactive Win32/WinForms, WPF, WinUI 3, and packaged/UWP hosted apps on Windows 10 19041+ and current Windows 11. Electron/WebView2, RDP, IME, and popups are staged/report-only until independently validated.
Kill/redesign if hosted focus cannot be classified safely, any wrong-target input is possible, or Paint/Calculator traces are not reliable.
### Additional context
This intentionally does **not** replace or depend on PR #602 (`ui watch`). `ui watch` is a broad live-event stream with NDJSON/callback complexity and does not provide per-key causality or input safety. If general event watching has a demonstrated future need, it should be reconsidered separately after #691; it is not needed for this diagnostic.
Contributor guide
No contributing guide indexed for this repository
First steps
- Read the whole issue, then the project's contributing guide.
- Comment on the issue to say you are picking it up — it saves two people doing the same work.
- Fork the repository and make your change on a branch.
- Open a pull request that references the issue number.
Research direction
Start with the shared focus snapshot and UIA/HWND membership work required by #691 Stage 1, then trace the existing CLI command conventions before adding UiTabTraceCommand. Review the CLI schema, UI automation documentation, skill fragments, generated skills, and tests mentioned in the issue. Done means bounded SendInput traversal, safe stop conditions, factual text/JSON output, and validation across the listed Windows app types.
Written by the indexing model from the issue text.
Assessment
- Tech stack
- csharp
- Domain
- cli, devtools, operating-systems
- Issue type
- Feature
- Difficulty
- 5/5
- Estimated time
- Over a week
- Activity status
- Quiet
- Clarity
- Mostly clear
- Newbie friendliness
- 35/100