Add attach_tab() and new_tab(background=True) for focus-preserving automation - #504
Add attach_tab() and new_tab(background=True) for focus-preserving automation#504icekinder wants to merge 1 commit into
Conversation
…tomation When the harness drives a user's live browser, new_tab()/switch_tab() activate the target and yank the user out of whatever tab they are working in. This adds: - attach_tab(target): attach a session without activating the tab (switch_tab() keeps its behavior and is now activate + attach_tab) - new_tab(url, background=True): create via Target.createTarget's background flag and attach without activating The reuse-a-blank-current-tab shortcut in new_tab() is skipped when background=True, since the current tab may be the user's visible one. Documented both in interaction-skills/tabs.md. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
✅ Skill review passedReviewed 1 file(s) — no findings. |
Kastan97
left a comment
There was a problem hiding this comment.
Ollie (CTO) Review: APPROVED ✅
What this does: Adds attach_tab(target) for attach-without-activate and new_tab(url, background=True) for creating tabs without stealing OS focus. Refactors switch_tab to call attach_tab internally.
Verification:
- 21+/6- across helpers.py + tabs.md docs
- Clean separation: switch_tab = activate + attach, attach_tab = attach only
- new_tab background=True bypasses blank-tab reuse (doesn't touch user's current tab) and passes background to CDP
- Docs updated
Good to merge once CI passes.
|
I've been running background-tab automation on macOS for a while via my own opt-in variant (#469), and hit two things downstream of 1.
I work around it by launching the automation browser pointed at a static local sentinel page, so the window always holds at least one real tab and 2. Background tabs report Two failure modes I hit, both silent — input is delivered and simply has no effect:
Worth noting the stated justification in #498 for that call — that a hidden Environment for all of the above: macOS 15, Brave 150 (Chromium 150), dedicated debugging profile on a non-default port, daemon attached over CDP. Happy to close #469 in favour of this one — the opt-in-parameter approach here is cleaner than my env var, and there's no sense in four open PRs for the same problem. |
Motivation
When the harness drives a user's live browser (the daemon attached to their real Chrome),
new_tab()andswitch_tab()activate the target — which visibly yanks the user out of whatever tab they're working in every time automation runs. For background/batch workflows (CSV imports, polling a web app's UI, scraping a logged-in dashboard) the automation has no reason to be visible at all.Changes
attach_tab(target)— attach a session to a tab without activating it.switch_tab()keeps its exact behavior and is now literally activate +attach_tab().new_tab(url, background=False)— withbackground=True, the tab is created viaTarget.createTarget'sbackgroundflag and only attached, never activated. Default behavior unchanged.new_tab()is skipped whenbackground=True: the current tab may be the user's visible one, andbackgroundis an explicit request not to touch what they see.interaction-skills/tabs.md(code block + a "rules that held up" line).Notes
Running this against a live daily-driver Chrome for a few weeks now — background CSV-import/enrichment runs no longer steal focus while the user keeps browsing.
🤖 Generated with Claude Code
Summary by cubic
Adds attach_tab() and new_tab(background=True) so automation can attach to tabs without activating them, preventing focus theft in a user’s live browser. Default behavior remains unchanged.
Written for commit 5702b58. Summary will update on new commits.