Skip to content

test(e2e): isolate Electron test profiles on macOS and Windows - #1910

Merged
benceruleanlu merged 21 commits into
bl/desktop-as-a-platformfrom
bl/shared-components-06-verification
Nov 3, 2026
Merged

benceruleanlu merged 21 commits into
bl/desktop-as-a-platformfrom
bl/shared-components-06-verification

Conversation

@benceruleanlu

@benceruleanlu benceruleanlu commented Nov 3, 2026 •

Copy link
Copy Markdown
Member

Electron tests on macOS could write into a developer's real Desktop profile, because macOS ignores HOME for Electron's paths. The test launcher now also sets CFFIXED_USER_HOME, so app state, sessions, logs and Downloads stay in a per-run temp folder. Windows now redirects LOCALAPPDATA as well as APPDATA. No test code is added to the app.

This lets macOS reuse a test profile, lets lifecycle cleanup read the isolated install list, and removes the macOS skip from the model-download lifecycle spec. e2e/profile-isolation.test.ts checks the folders on every OS. e2e/shared-controls-input.test.ts separately checks shared selects and tabs with real mouse and keyboard input.

The only product-code change is a comment in src/main/lib/opsFlag.ts.

Validation

  • macOS: both new specs pass locally.
  • Lifecycle CI only runs on Windows, so profile reuse and the unskipped model-download spec have not been run on macOS.
  • CI results are available in this PR's Checks tab.

Change breakdown

Net changes against the current base, excluding merge-only changes. Total changed lines = additions + deletions.

Category Files Added Deleted Share of changed lines
Product code 1 4 7 4.5%
Test code 10 147 72 89.8%
Documentation 1 11 3 5.7%
Product code paths (1)
  • src/main/lib/opsFlag.ts (+4/−7)
Test code paths (10)
  • e2e/beta-activation-notice-firstrun.test.ts (+3/−4)
  • e2e/beta-activation-notice-named.test.ts (+1/−2)
  • e2e/beta-activation-notice.test.ts (+3/−4)
  • e2e/lifecycle-model-downloads.test.ts (+0/−9)
  • e2e/lifecycle.test.ts (+13/−17)
  • e2e/process-ownership.test.ts (+1/−2)
  • e2e/profile-isolation.test.ts (+47/−0)
  • e2e/shared-controls-input.test.ts (+59/−0)
  • e2e/support/electronHarness.ts (+16/−25)
  • e2e/support/fakeComfyInstall.ts (+4/−9)
Documentation paths (1)
  • e2e/README.md (+11/−3)

@coderabbitai

coderabbitai Bot commented Nov 3, 2026 •

Copy link
Copy Markdown

Important

Review skipped

Auto reviews are disabled on base/target branches other than the default branch.

Please check the settings in the CodeRabbit UI or the .coderabbit.yaml file in this repository. To trigger a single review, invoke the @coderabbitai review command.

Run configuration
  • Source mode: Auto
  • Repository: Unavailable
  • Branch: Unavailable
  • File: No configuration file from this repository applied
  • Commit: Unavailable
  • Layers: Organization UI
  • Review profile: ASSERTIVE
  • Plan: Advanced
  • Run ID: 3f848e86-0753-4afa-8c5c-0f964a646ef4

You can disable this status message by setting the reviews.review_status to false in the CodeRabbit configuration file.

Use the checkbox below for a quick retry:

  • Trigger review
  • Autofix · Keep fixing CodeRabbit findings and required CI, and resolving merge conflicts

CodeRabbit Verify

  • Run CodeRabbit Verify to test the changes in this pull request.

@benceruleanlu
benceruleanlu added this pull request to stack #1907 November 3, 2026 10:13
@benceruleanlu
benceruleanlu force-pushed the bl/shared-components-06-verification branch from 83b9457 to c994719 Compare November 3, 2026 10:19
@benceruleanlu
benceruleanlu marked this pull request as ready for review November 3, 2026 10:26
@benceruleanlu
benceruleanlu requested review from a team as code owners November 3, 2026 10:26
@benceruleanlu
benceruleanlu force-pushed the bl/shared-components-06-verification branch 2 times, most recently from 6906565 to 8d70882 Compare November 3, 2026 12:21
@benceruleanlu
benceruleanlu force-pushed the bl/shared-components-06-verification branch 3 times, most recently from 48d8e9d to d54177d Compare November 3, 2026 12:44
The shared tabs activate on focus, and Electron refocuses the remembered
tab button when a hidden popup is shown again, so opening Settings on a
requested tab could snap back to the previous one. Rebuild the tab list
when a tab is requested so the old focus and keyboard stop are dropped.

Restore the opacity the shared download buttons lost, and remove the
empty wrapper and class names nothing references.
…gration

Restore the first-run Continue spinner, whose classes were overwritten with the
button's. Size the Cloud info button as an icon again.

Make open-path links block level. The shared button is a centred inline-flex, so
a long path lost its beginning and never showed an ellipsis, and the wizard's
40px path link sat above its icon.

Keep the performance test's Stop button destructive, matching the console's
Stop, keep the not-allowed cursor on the locked Continue button, and remove an
unused tile class.
@benceruleanlu
benceruleanlu force-pushed the bl/shared-components-06-verification branch from d54177d to 2db89aa Compare November 3, 2026 12:52
Isolate macOS test runs through CFFIXED_USER_HOME, which also moves home,
logs and downloads, and drop the app-side userData override it replaces.
Redirect LOCALAPPDATA on Windows and resolve relative profile dirs.

Run the visual job in the pinned Playwright image and upload regenerated
baselines whenever it fails. Commit Linux baselines only, shape the settings
fixture like the real snapshot, keep reports out of lint and tests out of
release builds, and remove macOS limitations that no longer apply.
Base automatically changed from bl/shared-components-05-views to bl/desktop-as-a-platform November 3, 2026 12:56
@benceruleanlu benceruleanlu changed the title test(ui): add visual regression gate and component migration handoff test(ui): compare PR visuals with the base branch Nov 3, 2026
… failures

The profile-isolation test read the Downloads folder on Windows, where Electron
cannot resolve it inside a redirected profile, so E2E (windows) failed every run
and its other assertions never ran. Read home and downloads only off Windows and
compare canonical paths, because Windows runners use 8.3 temp paths.

The report compared against the base branch's tip, so later base commits looked
like the PR's changes. It now resolves the merge base.

Both versions must pass the PR's fixture, so a PR that changes asserted text or
adds a scene could never pass on the base and lost its whole report. A failed
base render no longer fails the check, and both failure directions compare what
was captured and mark the rest as not compared.

The base now builds with its own Vite and Tailwind. Ctrl-C and SIGTERM remove the
temporary worktree. Title and description edits no longer rerun or cancel the job.
Packaging excludes visual-report/, and the handoff doc keeps only lasting guidance.
Comparing screenshots is work for whoever is doing the QA, not something the
repository needs to run and publish on every PR. Remove the CI job, comparison
scripts, Chromium fixture and image packages, along with the config that only
existed for them. The fixture's interaction checks go too, because they had no
other runner.

Keep the Electron test profile isolation, its test and the native-input test.
Move the isolation note into e2e/README.md, and stop adding the shared-components
doc. Formatting-only changes to fakeComfyInstall.ts are reverted.
@benceruleanlu benceruleanlu changed the title test(ui): compare PR visuals with the base branch test(e2e): isolate Electron test profiles on macOS and Windows Nov 3, 2026
@benceruleanlu
benceruleanlu merged commit 0ac336e into bl/desktop-as-a-platform Nov 3, 2026
16 checks passed
@benceruleanlu
benceruleanlu deleted the bl/shared-components-06-verification branch November 3, 2026 14:30
Penguinjanator pushed a commit to Penguinjanator/Comfy-Desktop that referenced this pull request Nov 10, 2026
* refactor(theme): bind Tailwind colors to the active desktop theme (Comfy-Org#1811)

* refactor(ui): migrate alert dialogs to Tailwind and shared buttons (Comfy-Org#1812)

* refactor(ui): migrate tooltip presentation to Tailwind (Comfy-Org#1814)

* refactor(ui): migrate shared form controls to Tailwind (Comfy-Org#1815)

* refactor(ui): migrate modal and prompt primitives to Tailwind (Comfy-Org#1816)

* refactor(ui): migrate action sheets to Tailwind and shared buttons (Comfy-Org#1817)

* refactor(ui): migrate expansion and detail primitives to Tailwind (Comfy-Org#1818)

* refactor(settings): migrate argument and environment controls to Tailwind (Comfy-Org#1819)

* refactor(styles): remove retired launcher layout rules (Comfy-Org#1820)

* refactor(storage): migrate directory controls to Tailwind (Comfy-Org#1821)

* refactor(ui): migrate account and workspace controls to Tailwind (Comfy-Org#1822)

* refactor(ui): migrate branded layout shells to Tailwind (Comfy-Org#1823)

* refactor(ui): migrate benchmark comparison screen to Tailwind (Comfy-Org#1824)

* refactor(ui): migrate performance test screen to Tailwind (Comfy-Org#1825)

* Migrate snapshot controls to Tailwind utilities (Comfy-Org#1826)

* refactor(ui): migrate transient popup shells to Tailwind (Comfy-Org#1827)

* refactor(ui): migrate installation chooser to Tailwind (Comfy-Org#1828)

* Migrate first-use takeover styles to Tailwind (Comfy-Org#1829)

* Migrate snapshot detail surfaces to Tailwind (Comfy-Org#1830)

* refactor(ui): migrate action menus to Tailwind (Comfy-Org#1831)

* Migrate onboarding choice card styles to Tailwind (Comfy-Org#1832)

* refactor(ui): migrate download progress primitives to Tailwind (Comfy-Org#1833)

* refactor(ui): migrate download views to Tailwind (Comfy-Org#1834)

* Remove retired component rules from global styles (Comfy-Org#1835)

* Migrate onboarding variant and template pickers to Tailwind (Comfy-Org#1836)

* Migrate status and version panels to Tailwind (Comfy-Org#1837)

* Migrate shared settings sections to Tailwind (Comfy-Org#1838)

* refactor(ui): migrate global settings layout to Tailwind (Comfy-Org#1839)

* refactor(ui): migrate global settings cards to Tailwind (Comfy-Org#1840)

* refactor(ui): migrate instance picker rows to Tailwind (Comfy-Org#1841)

* refactor(ui): migrate progress animation primitives to Tailwind (Comfy-Org#1842)

* refactor(ui): migrate finished status surface to Tailwind (Comfy-Org#1843)

* refactor(ui): migrate confirmation takeover controls to Tailwind (Comfy-Org#1844)

* Migrate beta argument pill to Tailwind (Comfy-Org#1845)

* Migrate startup argument editor to Tailwind (Comfy-Org#1846)

* Migrate update channel picker to Tailwind (Comfy-Org#1847)

* Migrate custom model paths dialog to Tailwind (Comfy-Org#1848)

* refactor(ui): migrate instance settings content to Tailwind (Comfy-Org#1849)

* refactor(ui): migrate instance picker layout to Tailwind (Comfy-Org#1850)

* Migrate title bar layout to Tailwind (Comfy-Org#1851)

* Migrate title bar menu and zoom buttons to Tailwind (Comfy-Org#1852)

* Migrate title bar identity controls to Tailwind (Comfy-Org#1853)

* Migrate title bar update and download indicators to Tailwind (Comfy-Org#1854)

* refactor(ui): migrate progress showcase helpers to Tailwind (Comfy-Org#1855)

* refactor(ui): migrate operation progress modal to Tailwind (Comfy-Org#1856)

* refactor(ui): migrate path and disk status styling to Tailwind (Comfy-Org#1857)

* refactor(ui): migrate install wizard to Tailwind (Comfy-Org#1858)

* refactor(ui): migrate environment and install path helpers (Comfy-Org#1859)

* refactor(ui): migrate console terminal presentation to Tailwind (Comfy-Org#1860)

* refactor(ui): migrate progress step presentation to Tailwind (Comfy-Org#1861)

* refactor(ui): migrate lifecycle placeholder to Tailwind (Comfy-Org#1862)

* refactor(ui): migrate panel shell presentation to Tailwind (Comfy-Org#1863)

* refactor(ui): migrate zoom banner to Tailwind (Comfy-Org#1864)

* refactor(ui): migrate legacy migration banner to Tailwind (Comfy-Org#1865)

* Migrate shared visual primitives to Tailwind (Comfy-Org#1866)

* refactor(ui): migrate legal dialog content to Tailwind (Comfy-Org#1867)

* refactor(ui): migrate feedback dialog content to Tailwind (Comfy-Org#1868)

* refactor(ui): migrate cloud promotion dialog to Tailwind (Comfy-Org#1869)

* refactor(ui): migrate announcement dialog to Tailwind (Comfy-Org#1870)

* refactor(ui): migrate console dialog presentation to Tailwind (Comfy-Org#1871)

* refactor(ui): migrate title popup menu to Tailwind (Comfy-Org#1872)

* Migrate snapshot loading takeover to Tailwind (Comfy-Org#1873)

* refactor: own legacy modal host presentation with Tailwind (Comfy-Org#1874)

* refactor: migrate snapshot confirmation dialogs to Tailwind (Comfy-Org#1875)

* refactor: own legacy dialog presentation with Tailwind (Comfy-Org#1876)

* refactor: migrate quick install presentation to Tailwind (Comfy-Org#1877)

* refactor(ui): migrate installation detail dialog to Tailwind (Comfy-Org#1878)

* refactor: migrate management dialog wrapper to Tailwind (Comfy-Org#1879)

* refactor: migrate track installation modal to Tailwind (Comfy-Org#1880)

* refactor(ui): own modal transitions with Tailwind props (Comfy-Org#1881)

* refactor(ui): preserve control styles without native defaults (Comfy-Org#1882)

* refactor: remove retired renderer component CSS (Comfy-Org#1883)

* refactor: consolidate Desktop palette runtime tokens (Comfy-Org#1884)

* refactor(ui): own progress viewport height with Tailwind (Comfy-Org#1885)

* refactor: compile standalone window utilities in main bundle (Comfy-Org#1886)

* refactor(ui): migrate checkout close chip to Tailwind (Comfy-Org#1887)

* refactor(ui): migrate standalone terminal presentation to Tailwind (Comfy-Org#1888)

* refactor: migrate log popout presentation to Tailwind (Comfy-Org#1889)

* fix(ui): preserve ellipsis for long install paths (Comfy-Org#1894)

* fix(ui): restore lighter design backgrounds across main screens (Comfy-Org#1895)

* fix(ui): restore light layers on Desktop content backgrounds

* refactor(ui): express content surface lighting with Tailwind

* Prevent new Vue style blocks after the Tailwind migration (Comfy-Org#1896)

* Enforce Tailwind styling for new Vue component styles

* Make CRLF coverage independent of checkout line endings

* Avoid TypeScript project startup in style rule configuration test

* Fail tests when a style exception outlives its block

Removing an allowed block left its manifest entry behind, and every test
still passed. The leftover entry would quietly re-permit pasting that exact
CSS back. Each entry must now match a block in its file; the hash function
is shared with the rule so both fingerprint identically.

* refactor(design-system): take the Void theme from the package (Comfy-Org#1899)

* refactor(design-system): take the Void theme from the package

Void's colors, type, radii, shadows and motion now come from
@comfyorg/design-system, so Desktop keeps only the tokens its own screens
use. The package's theme file also registers the compiled components for
Tailwind and supplies the icons, animations and stacking layers that its
Select, Dialog and Checkbox need.

The package's next release expects VueUse 14, so bump it here.

* chore(design-system): install the published 1.3.0-alpha.0 prerelease

Pin the prerelease that carries the Void theme until the real 1.3.0 is out.

* refactor(design-system): render BaseInput with the package's Input (Comfy-Org#1902)

First step of moving Desktop's own components onto the package. BaseInput
keeps its props and class names, so no screen changes. The overrides hold
today's look until the design moves to Void's inputs.

Only Input moves. InputGroup's padding rules outrank the overrides screens
apply through .ui-input-control, so adopting it now would move pixels.

* refactor(ui): share dropdown, menu, and tooltip primitives (Comfy-Org#1904)

* refactor(ui): share select menu and tooltip primitives

* fix(a11y): expose one accessible tooltip description

* test(e2e): send real input to shared popup controls

* fix(ui): repair keyboard, focus and layout regressions in shared popups

Review of the move onto the shared package found behaviour the old
components had and the adapters lost:

- Escape on a keyboard-focused tooltip also closed the popup or modal
  behind it. The guard sat on the bubble, which doesn't hold focus there,
  and Reka's escape-key-down runs on window, too late to stop anything.
- Enter or Space on a menu item's help icon ran the item's action.
- Long option descriptions made a dropdown 1,508px wide in a 1,200px
  window. The list now keeps the trigger's width and wraps.
- The first click outside an open dropdown only closed it. It now also
  reaches what was clicked, and the open trigger keeps its colour so the
  page under the pointer doesn't change the trigger's look.
- Closing a context menu dropped focus to the page body. It now returns
  to what had focus, unless the user clicked elsewhere or left the window.
- A window blur while the action menu was closed stopped the next close
  from returning focus. The exposed open/close/toggle had no other caller,
  so they go, along with BetaArgsPill's duplicate blur listener.
- Tooltips with links were unnamed dialogs for screen readers.
- Clicking a help icon closed its explanation.
- Clipped text could need a second pointer move before its tooltip showed,
  so the clip is now measured when the tooltip opens, as before.
- BetaArgsPill's list of active flags rendered at half opacity.

Restores the test for moving the pointer from a trigger onto linked
content. That path depends on a prop the package leaves out of its types.

* test(e2e): wait for real input to land and retry blocked clicks

click and pressKey returned once input was queued, so a test reading state
on the next line could see the page from before the click. They now wait
for the page to handle the event, bounded because the input may hide or
destroy the page.

A covered element made click throw straight through the retry loops in
clickUntilVisible and selectOption, ending a test with time left on its
deadline. No input was sent in that case, so those loops now retry. Direct
callers still get the error, which now names the element.

The beta args test's "other option" selector filtered on data-selected,
which shared select items don't set, so it could pick the selected option.

Adds an end-to-end test of dropdown width and one-layer-at-a-time Escape in
the install settings popup.

* refactor(ui): use shared form controls throughout Desktop (Comfy-Org#1905)

* refactor(ui): share grouped inputs, switches, and disclosure motion

* refactor(ui): adopt shared controls across desktop forms

* fix(ui): reconcile clamped run counts on field commit

* fix(ui): restore form control details lost in the shared migration

Size the arguments field's configure button with InputGroupButton, since
BaseInput no longer sizes buttons in its slots. Restore series colours on
selected benchmark checkboxes and the yellow terms nudge, and name
DetailSection switches for screen readers.

Cover run count correction with a component test and share the setChecked
test helper, which now confirms the control reached the requested state.

* chore(i18n): remove confirmed unused translation groups

* refactor(ui): consolidate Desktop dialogs and takeovers (Comfy-Org#1906)

* refactor(design-system): share Desktop dialog primitives

* refactor(design-system): share takeover and nested dialog lifecycle

* fix(a11y): name shared takeovers and finish dialog lifecycle migration

* fix(dialogs): honor explicit initial focus and safe fallback

* fix(dialogs): restore modal widths, field focus and takeover fade-in

- Modal: cap width with plain max-w utilities; the shared surface's own
  max-width outranked the zero-specificity defaults, so view modals filled
  the window.
- ModalDialog: let fixed-width boxes shrink with their wrapper so confirm
  buttons stay on screen in narrow popups.
- Mark initial focus with data-initial-focus. The package refocuses
  [autofocus] whenever the dialog content takes focus, so clicking blank
  dialog space jumped to the field and selected its text.
- BrandTakeoverLayout: animate the outer layer; the surface's animate-none
  overrode the fade-in on the content.
- Use lib/modalLinkify in ModalDialog and remove leftover no-op classes and
  pass-through wrappers.

* refactor(ui): share popup controls and settings navigation (Comfy-Org#1908)

* refactor(ui): share popup buttons tabs and directory menus

* fix(ui): keep requested settings tab and hover-only download cancel

The shared tabs activate on focus, and Electron refocuses the remembered
tab button when a hidden popup is shown again, so opening Settings on a
requested tab could snap back to the previous one. Rebuild the tab list
when a tab is requested so the old focus and keyboard stop are dropped.

Restore the opacity the shared download buttons lost, and remove the
empty wrapper and class names nothing references.

* refactor(ui): finish shared actions, menus, and form styling (Comfy-Org#1909)

* refactor(ui): standardize desktop action buttons

* refactor(ui): share account and workspace menu behavior

* refactor(ui): share settings tabs and action menus

* refactor(ui): finish benchmark controls and remove input overrides

* refactor(ui): remove obsolete tooltip forwarding wrapper

* fix(ui): repair spinner, path links and action sizing after button migration

Restore the first-run Continue spinner, whose classes were overwritten with the
button's. Size the Cloud info button as an icon again.

Make open-path links block level. The shared button is a centred inline-flex, so
a long path lost its beginning and never showed an ellipsis, and the wizard's
40px path link sat above its icon.

Keep the performance test's Stop button destructive, matching the console's
Stop, keep the not-allowed cursor on the locked Continue button, and remove an
unused tile class.

* chore: trim historical comments across Desktop (DESK-231) (Comfy-Org#1912)

* chore: trim stale code comments (DESK-231)

* chore: keep agent instructions unchanged

* chore: audit historical comments across Desktop

* chore: clear repository agent instructions (Comfy-Org#1914)

* chore: remove repository agent instructions

* chore: retain empty root agent files and integrity check

* test(e2e): isolate Electron test profiles on macOS and Windows (Comfy-Org#1910)

* refactor(ui): share popup buttons tabs and directory menus

* fix(ui): keep requested settings tab and hover-only download cancel

The shared tabs activate on focus, and Electron refocuses the remembered
tab button when a hidden popup is shown again, so opening Settings on a
requested tab could snap back to the previous one. Rebuild the tab list
when a tab is requested so the old focus and keyboard stop are dropped.

Restore the opacity the shared download buttons lost, and remove the
empty wrapper and class names nothing references.

* refactor(ui): standardize desktop action buttons

* refactor(ui): share account and workspace menu behavior

* refactor(ui): share settings tabs and action menus

* refactor(ui): finish benchmark controls and remove input overrides

* refactor(ui): remove obsolete tooltip forwarding wrapper

* fix(ui): repair spinner, path links and action sizing after button migration

Restore the first-run Continue spinner, whose classes were overwritten with the
button's. Size the Cloud info button as an icon again.

Make open-path links block level. The shared button is a centred inline-flex, so
a long path lost its beginning and never showed an ellipsis, and the wizard's
40px path link sat above its icon.

Keep the performance test's Stop button destructive, matching the console's
Stop, keep the not-allowed cursor on the locked Continue button, and remove an
unused tile class.

* test(e2e): isolate Electron app profiles on every platform

* test(ui): add deterministic visual regression coverage

* docs(ui): record component consolidation and visual handoff

* test(ui): fail closed while collecting initial Linux baselines

* test(e2e): drive shared controls through native input

* test(ui): add reviewed Linux visual baselines

* docs(ui): finalize shared component verification handoff

* test(ui): tighten test isolation and the visual gate

Isolate macOS test runs through CFFIXED_USER_HOME, which also moves home,
logs and downloads, and drop the app-side userData override it replaces.
Redirect LOCALAPPDATA on Windows and resolve relative profile dirs.

Run the visual job in the pinned Playwright image and upload regenerated
baselines whenever it fails. Commit Linux baselines only, shape the settings
fixture like the real snapshot, keep reports out of lint and tests out of
release builds, and remove macOS limitations that no longer apply.

* test(ui): report visual changes against the PR base

* fix(ci): trust the visual report checkout in the container

* fix(ci): compare visuals from the PR's branch point and tolerate base failures

The profile-isolation test read the Downloads folder on Windows, where Electron
cannot resolve it inside a redirected profile, so E2E (windows) failed every run
and its other assertions never ran. Read home and downloads only off Windows and
compare canonical paths, because Windows runners use 8.3 temp paths.

The report compared against the base branch's tip, so later base commits looked
like the PR's changes. It now resolves the merge base.

Both versions must pass the PR's fixture, so a PR that changes asserted text or
adds a scene could never pass on the base and lost its whole report. A failed
base render no longer fails the check, and both failure directions compare what
was captured and mark the rest as not compared.

The base now builds with its own Vite and Tailwind. Ctrl-C and SIGTERM remove the
temporary worktree. Title and description edits no longer rerun or cancel the job.
Packaging excludes visual-report/, and the handoff doc keeps only lasting guidance.

* test(e2e): drop the visual comparison report

Comparing screenshots is work for whoever is doing the QA, not something the
repository needs to run and publish on every PR. Remove the CI job, comparison
scripts, Chromium fixture and image packages, along with the config that only
existed for them. The fixture's interaction checks go too, because they had no
other runner.

Keep the Electron test profile isolation, its test and the native-input test.
Move the isolation note into e2e/README.md, and stop adding the shared-components
doc. Formatting-only changes to fakeComfyInstall.ts are reverted.

* fix(ui): preserve Desktop white control accents (Comfy-Org#1911)

* fix(build): keep Electron's install working on Node 26 (Comfy-Org#1916)

On Node 26, Electron's postinstall stops partway through extracting its zip
and still exits 0, so a fresh pnpm install leaves Electron unusable. pnpm then
caches the partial result, which makes reinstalling replay it. The stall is in
yauzl 2.10.0, which extract-zip uses. yauzl 3.4.0 extracts the same files on
Node 22, 24 and 26.

* test(e2e): let parallel Electron runs pick their own debugging port (Comfy-Org#1918)

The test launcher overrode Playwright's free-port request with 19200 plus the
worker index, which is the same number in every separate run. When another run
held it, Electron never reported ready, so launch hung for 45s and failed. No
test reads the port, so drop the override and the workarounds three specs
carried for it.

* refactor(design-system): own Void in Desktop on the package baseline (Comfy-Org#1920)

* refactor(design-system): own Void in Desktop on the package baseline

DrJKL asked that the package hold one shared baseline and that Desktop keep only
the values that differ. Desktop's look now lives in design-system-theme.css on
top of @comfyorg/design-system/css/baseline.css.

The baseline maps package colors to --accent, --border and --warning, so:
- Desktop's white highlight moves to --action, since --accent is now the
  package's hover fill.
- --border holds Void's value directly to avoid a variable cycle.
- --warning takes Void's amber, so legacy warnings match package warnings.

The rename touches the frozen gs-field-flash keyframes, so they move into the
theme and that style block and its exception go away.

* chore(design-system): take the shared baseline from 1.3.0-alpha.1

* feat(ui): add Mar's left sidebar to the dashboard window (Comfy-Org#1922)

* feat(ui): add Mar's left sidebar to the dashboard window

Dashboard, Benchmarks and Performance Tests now sit in Mar's floating panel
layout: a sidebar card and a content card on a near-black window, with the title
bar in the same colour. The sidebar collapses to an icon rail and remembers it.

Benchmarks and Performance Tests are reachable in place through a new
comfy-window:navigate-panel IPC, limited to dashboard windows. The menu still
opens them in a new window.

Log in, sign out and the workspace switch move from the screens into the
sidebar's foot, so DevPlatformAccountChip goes away. Those two screens' layout
breakpoints now measure the content area, because the sidebar takes window width.

* fix(ui): keep sidebar pages and test runs alive, match login images to Figma

Benchmarks lost its folder, filters and picked runs on every sidebar visit
because it unmounted. It now stays alive like Performance Tests and quietly
picks up runs that finished while it was off screen.

Picking an instance while this window ran a performance test attached it in
place, which destroys the panel that owns the run and its Stop button. The
instance now opens in its own window during a run.

The login card images ran through a black-and-white filter before the tint,
so they lost their colour against Mar's Figma. The filter is gone.

* feat(ui): turn the dashboard into Mar's Builds page (Comfy-Org#1925)

The dashboard now follows Mar's Builds page: a titled header with one primary
action, a toolbar with where-it-runs tabs, sort and search, and her text card,
which says where a build runs and leads with the action its state needs. A card
click still launches as before, until the build details page exists.

New Instance moves from a grid tile to the page header, the workspace count moves
onto the tabs, and first-use and no-match states get Mar's copy. The sidebar row
is now Builds, naming the page it opens, until a real Home arrives.

The repeated wordmark goes from Benchmarks and Performance Tests. The two style
blocks the old tile and grid needed go with their exceptions.

* feat(ui): add the build details page (Comfy-Org#1926)

* feat(ui): add the build details page

Clicking a build now opens its own page in the dashboard window: Mar's header
with the name, state and actions, segmented tabs, and today's settings for
update, startup args, snapshots, storage, terminal and about. The card's button
still launches, and the Manage menu item opens this page.

Update, migrate, copy and restore from a card or its menu keep using the picker
popup for now, because that flow reports progress differently.

The settings body gains a page mode that teleports its actions to the header. The
panel gets the shared storage data over a new IPC, and may now use the terminal,
which only trusted the popup and the popout before.

* fix(ui): make the build page's folder actions, refresh and new window work

The settings tabs still assumed they ran inside the picker popup, so on the
build page several actions failed without any error:

- Storage and About: Add Directory, Browse and open-folder did nothing, and
  Manage Shared Directories disappeared, because both tabs called the popup's
  own bridge. They now call window.api, which the popup's shim forwards. The
  panel gains revealPath, and the shim gains revealPath and platform. That also
  gives the popup's terminal its real platform for copy and paste shortcuts.
- After Update: the tabs kept the old release and Update action, because only
  the popup's operation state triggered a reload. The settings now reload when
  main reports an action on this build ended, whichever window started it.
- Open in new window on a cloud or remote build replaced the dashboard, because
  it ran the same launch as the main button. It now uses the primitive the
  popup uses, through a new panel IPC.

* refactor(ui): remove retired installation settings screens (Comfy-Org#1927)

* refactor(ui): remove retired installation settings screens

* refactor(ui): remove snapshot preview content orphaned by the import modal removal

* fix(ui): remove Log in from the hamburger menu (Comfy-Org#1933)

The hamburger menu still offered Log in, a leftover from before the dashboard
had its own sign-in. Mar's sidebar now carries a Log in card on Builds,
Benchmarks and Performance Tests, so the menu item was a second, confusing
way to sign in to Desktop that does not sign you in to ComfyUI.

Remove the item, its click handler and isSignedInToCloud(), which only the
menu used, plus the fileMenu.signIn strings. signInToCloud() stays: the
sidebar card, the install wizard and the embedded session still use it.

* test(e2e): keep local Windows runs from taking OS focus (Comfy-Org#1932)

Load a test-only Electron preload (-r) that shows windows inactive and
no-ops window, app and webContents focus, so a local Windows run no
longer interrupts the developer. Tests that need real focus can be
tagged @needs-focus and run with test:e2e:windows:focus. CI, lifecycle
and E2E_FOREGROUND=1 keep real focus behaviour.

Co-authored-by: Claude <noreply@anthropic.com>

* chore(lint): ban code comments and delete existing ones (Comfy-Org#1936)

* chore(lint): add desktop/no-comments rule banning code comments

Mirrors the frontend's comment ban, but enforced by lint. The rule
rejects every comment except tool directives and autofixes by deleting
the comment. It also strips prose reasons after ESLint directives and
@ts-expect-error, so ban-ts-comment now accepts a bare @ts-expect-error.

Co-authored-by: Claude <noreply@anthropic.com>

* chore: delete all code comments

Produced by `eslint --fix` with desktop/no-comments, then Prettier on
files that were already Prettier-clean. Bridge types regenerated.
progressStore's comment-only portConflict branch folded into the
condition.

Co-authored-by: Claude <noreply@anthropic.com>

* docs: state that the repository does not allow code comments

Co-authored-by: Claude <noreply@anthropic.com>

---------

Co-authored-by: Claude <noreply@anthropic.com>

* chore(format): make the whole repo Prettier-clean and check it (Comfy-Org#1937)

* docs: stop a wrapped '+' line rendering as a list item

In the nav-matrix e2e bullet, a hard-wrapped continuation line began with
'+ live', which Markdown parses as a nested list item. Reword it to 'and
live' so the sentence stays in one bullet.

Co-Authored-By: Claude <noreply@anthropic.com>

* style: run Prettier over the whole repository

Purely mechanical: the output of 'prettier --write .' with the existing
.prettierrc.json, over the files the old format scope never covered
(e2e/, scripts/, docs and README Markdown, one workflow YAML). No
hand edits.

Co-Authored-By: Claude <noreply@anthropic.com>

* chore(format): check every Prettier-supported file in the repo

format and format:check covered only src/**/*.{ts,vue} and root
*.{json,ts,yml}, so e2e/, scripts/, tests/, packages/, docs, Markdown
and workflow YAML were never checked and drifted. Both scripts now run
over '.', which also widens the pre-commit hook and the CI Format job,
since both call format:check.

.prettierignore skips pnpm-lock.yaml (written by pnpm), the
JSON.stringify output of scripts/starter-templates.mjs and
scripts/benchmark-templates.mjs, and .claude/ (local agent worktrees,
which would otherwise be scanned from the main checkout). Prettier
already honours .gitignore for out/, dist/, coverage/ and other build
output.

Co-Authored-By: Claude <noreply@anthropic.com>

---------

Co-authored-by: Claude <noreply@anthropic.com>

* chore(codeowners): remove deepme987 and Kosinkadink as root AGENTS.md owners (Comfy-Org#1941)

* fix(ui): clarify the new build button label (Comfy-Org#1942)

* fix(ui): put performance tests first and use build labels (Comfy-Org#1945)

* fix(ui): move build import actions beside New Build (Comfy-Org#1947)

* fix(i18n): add translation keys the UI references but en.json lacks (Comfy-Org#1948)

Twenty-eight keys used in the settings, snapshots, storage, feedback and
instance picker screens were never added to the locales. Each call passed
inline English, so the UI looked right in English but those strings
could not be translated. The keys now exist in en.json and zh.json with
the same English text, and the call sites no longer carry an inline
copy. The snapshots Export All button uses the existing
snapshots.exportAllSnapshots key, which already had that text.

The Comfy API announcement read announcement.comfyApi.highlights, which
that announcement never defined, so its highlights list was always empty.
The list is removed.

localeCoverage.test.ts now fails when source code passes a literal key
that en.json does not define, naming the file, line and key.

* test(renderer): use the shared i18n setup instead of local dictionaries (Comfy-Org#1949)

Renderer tests built their own vue-i18n instances, most with handwritten
dictionaries that had drifted from locales/en.json, so a test could pass
on copy the app never shows. Every mount now relies on the instance
vitest.setup.ts installs, and assertions use the production wording.

The setup no longer hides duplicate-registration and missing-key
warnings, so a reintroduced local instance shows up in test output.

* test(renderer): translate mocked useI18n with the app's messages (Comfy-Org#1951)

Composables that call useI18n() outside a component are tested with
vi.mock('vue-i18n'). Each of the nine mocks invented its own t(): some
echoed the key, some echoed the inline fallback text, some formatted
params into the key. None showed what a user reads, and the fallback
echoes would keep passing on copy that has drifted from en.json.

vueI18nWithAppMessages builds the mock from the real vue-i18n with the
same options as createAppI18n, now shared through i18nOptions.ts, so
these tests assert the production English. useActionGuard and
useListAction set window.api instead of replacing window, because real
translation needs window.performance.

* refactor(i18n): read UI copy only from the locale files (Comfy-Org#1952)

213 translation calls in the renderer passed an inline English default
alongside a key that en.json already defines. The renderer bundles
en.json, so those defaults never rendered, but they were a second copy
of the copy: 20 had already drifted, for example "Delete" where the app
says "Uninstall" and "Browse" where it says "Browse…". The calls now
pass only the key.

localeCoverage.test.ts now fails when a translation call passes inline
text, naming the file, line and key.

* test(renderer): load slow components before the first test's timer starts (Comfy-Org#1954)

ComfyUISettingsContent.test.ts and InstancePickerView.test.ts imported
their component inside the mount helper, so the first test paid to
compile it. On CI that took up to 3.8 s of the 5 s per-test limit, and
the first ComfyUISettingsContent test timed out at 5,082 ms on Comfy-Org#1949.

Import both components at the top of the file so Vitest loads them while
collecting the file. Locally the first tests drop from 1,267 ms and
2,217 ms to 54 ms and 35 ms.

* chore: delete comments that ESLint cannot reach (Comfy-Org#1938)

One-time cleanup of comments in Python, shell, PowerShell, NSIS, Swift,
CSS, HTML, Vue style blocks, and workflow YAML. AGENTS.md keeps new ones
out from here.

Kept: shebangs, PowerShell Get-Help blocks, and the version comments
after pinned action SHAs. The reset scripts printed their header comment
as --help, so that text moved into a usage() function (bash) and a
Get-Help block (reset-windows.ps1). Vue style exception fingerprints are
regenerated for blocks that lost a comment.

Co-authored-by: Claude <noreply@anthropic.com>

* fix(i18n): use build naming for add, restore, duplicate and upload (Comfy-Org#1955)

Rename the remaining instance copy from the Milestone 1 QA thread, in
English and Chinese:

- Add Existing Instance becomes Add Existing Build, its subtitle reads
  Add an existing ComfyUI install to Comfy Desktop, and Track Install
  becomes Add Build.
- The Restore From Snapshot page names the source and the new install
  as builds.
- Duplicate Instance becomes Duplicate, with a Duplicate Build dialog.
- Create Build becomes Upload Build, with the hint Upload this build to
  Comfy Developer Platform.

* fix(settings): use build naming and filter by workspace (Comfy-Org#1946)

* fix(settings): scope builds to their workspace and update naming

* test(e2e): use the renamed last-used build option

* fix(settings): keep requested and host builds in the scoped picker

Keep the host build visible when Hide Cloud is on, so opening settings
from a cloud build window still selects it and keeps its auto action.

Refresh the picker cache before resolving a requested build that is not
cached yet, so a deep link or a just-copied build is not rejected.

When the modal is opened for a specific build from the dashboard, scope
it to that build's workspace until the saved dashboard workspace
changes, so a pending or failed settings write cannot hide it.

Share the workspace membership check between the dashboard and the
main process, and scope the picker once per caller so the snapshot
builder forwards the scoped list and selection verbatim.

* fix(settings): use build naming in the Update and Snapshots tabs

Rename the remaining instance copy shown inside the settings modal:
the update undo hint, copy-and-update and release-update prompts, and
the snapshot delete, restore and import confirmations, in English and
Chinese.

* docs: delete redundant docs and trim README (Comfy-Org#1956)

* docs: delete TESTING.md and e2e/README.md

Most of both files restated package.json scripts, the Vitest and
Playwright configs, and the CI workflows, and the e2e spec inventory
had drifted (19 of 59 specs missing). Drop the README links to them.

* docs: delete the Comfy-Org#926 handoff note and trim README

Drop the README sections that restated package.json scripts, the
source tree, and the release workflow files.

* fix: rename installation heading to Install a New Build (Comfy-Org#1964)

* fix: use build terminology in installation labels (Comfy-Org#1965)

* fix: rename installation heading to Install a New Build

* fix: use build terminology in installation labels

* fix: update new build installation subtitle (Comfy-Org#1966)

* fix: keep the current page when closing What's New (DESK-175) (Comfy-Org#1970)

What's New was a value of activePanel, so opening it replaced the page
and closing it could only reset to 'comfy', which is the dashboard in a
window with no install. A performance test kept running with its page
gone from view.

Over a page, What's New now opens as a modal without changing
activePanel, so closing has nothing to restore. Over the live canvas it
still uses the 'announcement' key, because that is what brings the panel
view up above the canvas, and closing undoes only that.

The open path moves focus itself because setActivePanel no longer runs
there: the bell click leaves focus in the title bar, and Escape has to
reach the modal. Main decides what closing does because the renderer's
activePanel doesn't follow file-menu wizards, and resetting would have
dropped a wizard opened under the modal.

* test: split Vitest into node and renderer projects, and free renderer tests from happy-dom (Comfy-Org#1969)

* test: run main, preload, and shared tests in Node

The unit config ran everything under happy-dom unless a file opted out, so
151 main-process test files ran against a fake DOM that production never has.
Split it into a node project and a renderer project, and drop the 50
per-file node directives that split makes redundant.

Vitest's web transform for DOM environments is also what stopped vi.mock of
Node builtins from loading on Windows. agentRequirementsLaunch, pip, and
buildLaunchEnv now load there.

comfyContentScript and comfyTerminalContentScript evaluate scripts injected
into a page, so they stay on happy-dom through a file directive. csp and
localeCoverage read the filesystem, so they move to the node project.

* test: make renderer tests independent of happy-dom

These tests relied on things only a simulated DOM allows, which blocks moving
them to Vitest browser mode:

- vitest.setup.ts imported vue-i18n before a test's vi.mock could register.
  Install the plugin in beforeAll, after the test file is collected.
- Tests replaced window, which a real browser forbids. Add stubWindowApi,
  which stubs window.api and rejects keys ElectronApi doesn't declare.
- Drag and pointer tests passed plain objects as event data. Use a real
  DataTransfer and a real PointerEvent.
- useFirstUseChain's telemetry mock omitted a re-export that a real ES module
  link requires.

All 112 renderer test files (1,670 tests) pass under both happy-dom and real
Chromium with a throwaway browser-mode config. happy-dom stays the configured
environment for now. Switching is a separate change.

* test: run renderer tests in real Chromium with Vitest browser mode (Comfy-Org#1971)

* test: run renderer tests in real Chromium with Vitest browser mode

Renderer tests now run in headless Chromium through Vitest browser mode
instead of happy-dom, so they exercise real layout, events, focus, and
storage. happy-dom is removed.

- The renderer project becomes `browser`. It also takes the two tests
  that evaluate injected page scripts, which were the last happy-dom
  users. The scripts are plain strings, so they need no Node.
- Alias `vue` to the esm-bundler build in that project. The runtime-only
  build silently renders nothing for `template:` stubs.
- Drop the fake localStorage from the setup file. Each Vitest session has
  its own browser context, so parallel files stay isolated, and the setup
  file clears storage after each test for files sharing a session.
- Filter the one decodeEntities warning that Vue Test Utils string slots
  trigger. `onConsoleLog` is read from the root config, not per project.
- CI installs headless Chromium in the Test job only. Locally, run
  `pnpm run test:browser:install` once per Playwright version.

* fix(ci): patch Vitest browser advisories and pin Test to Ubuntu 24.04

Socket flagged critical advisories in @vitest/browser 4.0.18, which this
branch introduces: GHSA-g8mr-85jm-7xhm, GHSA-p63j-vcc4-9vmv, and
GHSA-2h32-95rg-cppp. Move vitest and @vitest/browser-playwright to 4.1.12,
which has the fixes for all three, and update ws to a patched version in
the lockfile because @vitest/browser depends on it.

ubuntu-latest now resolves to 26.04, where Playwright 1.58.2 refuses to
install Chromium. Pin only the job that needs a browser to ubuntu-24.04
rather than updating Playwright, which would also change the runner for
the E2E and lifecycle suites.

* test: run the node and browser projects one after the other

Vitest gives the browser project its own pool, so running both projects
together starts up to 16 workers instead of the 8 that happy-dom shared
with Node. On a CI runner that pushed import time from 123s to 375s and
made the node project time out while importing modules.

Give each project a sequence.groupOrder so the browser project starts
after the node project finishes. Capped to 4 cores locally, this cut
transform time from 62s to 22s and import time from 168s to 85s, and the
total run time did not get longer. Timeouts stay as they were, because
raising them would hide the overload.

* fix: finish Install a New Build copy in zh and leftover subtitle (Comfy-Org#1972)

Follow-up to Comfy-Org#1964, Comfy-Org#1965 and Comfy-Org#1966, which renamed these strings in
English only.

- zh: "新建实例" becomes "安装新构建" and the "environment" subtitle becomes
  "设置全新的 ComfyUI 安装。", using the 构建 and 安装 terms zh.json already uses.
- en and zh: newInstall.grandSubtitle no longer says "instance". No code
  references this key today, so nothing changes on screen.

* fix(ui): light takeovers with the spotlight from Mar's design (Comfy-Org#1973)

QA (Alexis) flagged that the install, add-existing and snapshot screens
don't match the Builds page: they read as an old purple gradient gone
black. Those screens layered a lighting band, a purple and teal wash, a
purple glow and two beams. Mar's Figma and prototype specify one soft
light from above with film grain, and have no beams or wash.

- Takeovers use Mar's background: film grain, the setup frame's and
  ambient layer's radial gradients, and the oklch(0.16 0.003 285) base.
- Benchmarks and Performance Tests share BrandBackground but sit beside
  Builds in the sidebar, so they use the exact Builds gradient. It now
  lives in one constant, so the two can't drift apart.
- Remove the beams, wash, glow and vignette, plus the anchors and assets
  that existed only for them.

* fix: name the snapshot screen Load Snapshot (Comfy-Org#1974)

From Alexis's retest: the screen opened by the Load Snapshot menu item was
titled "Restore From Snapshot", and its subtitle talked about recreating
a build.

- Title: "Restore From Snapshot" becomes "Load Snapshot", matching the
  menu items that open it.
- Subtitle: "Load a saved snapshot file to recreate that build here."
  becomes "Load a snapshot file to install a build."
- zh: 加载快照 and 加载快照文件以安装构建。, matching the existing 加载快照 menu
  items.

The build menu's "Restore Snapshot" restores into an existing build, a
different action, so it keeps its name.

* fix(ui): match Mar's dark tooltip bubble and show the Read more link (Comfy-Org#1975)

* fix(ui): show the Read more link in info tooltips under Void

The link was colored with --action, which Void sets to the foreground
color, the same color as the tooltip bubble's background, so it rendered
invisible and left what looked like extra height under the hint. Inherit
the bubble's text color and underline it instead.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>

* fix(ui): use Mar's dark tooltip bubble instead of the inverted one

Mar's designs (Figma New-Home, Atoms/Tooltip) use a dark bubble:
rgba(42,42,42,0.94) with a 10px backdrop blur, a 7% white border, an
8px radius, a 0 8px 12px shadow, 12px/16.2px medium text and no arrow.
Void had inverted tooltips to a light bubble. Point the Void tooltip
tokens at Mar's values, use them in the shared Tooltip, hide the arrow,
and give the title-bar tooltip popup the same colors and metrics.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>

---------

Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com>

* fix: confirm tile updates over the Builds page (Comfy-Org#1977)

Clicking Update on a build tile used to open the build manager on its
Update tab and fire the update from there, so the confirm appeared with
the manager behind it. QA asked for the confirm to show on its own over
the Builds page.

The Builds page now loads the build's update action for its current
channel and runs it through the same preflight the manager uses (busy
guard, stop warning, pickers, confirm, disk-space check), then shows
progress that returns to the Builds list. If no enabled update action is
found, it falls back to opening the manager on the Update tab.

The manager's preflight and progress setup move into
useDetailActionPreflight so both surfaces share one copy. The title-bar
pill and deep links keep opening the manager.

Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com>

* Revert "revert: keep Desktop platform redesign off the release branch (Comfy-Org#1892)"

This reverts commit b9e84d4.

* fix(lint): keep JSDoc in the published bridge contract (Comfy-Org#1985)

The bridge types package is the API contract the ComfyUI frontend builds
against. Comfy-Org#1936 deleted its JSDoc along with the repo's code comments, which
removed the docs from the published types and fails the bridge version
check on Comfy-Org#1976 without changing any type.

Restore the doc comments from main and give desktop/no-comments an
allowDocComments option. eslint.config.ts turns it on only for the files in
publishedApiSpecs, so line comments and plain block comments stay banned
there and everywhere else. AGENTS.md records the exception.

* test: fix tests that lie or cannot fail (Comfy-Org#1980)

Each test below either passed whatever the code did, or claimed something its body did not check. Every rewritten test was mutation-checked: break the line it guards and it fails.

- PanelApp: the install-update mismatch test asserted the absence of a test id that exists nowhere. It now seeds a second, known installation and asserts the instance picker is not opened. It fails when the installationId filter in useDeepLinkRouter is removed.
- snapshots: the staging test checked that history was empty in a fresh tmp dir that staging never touches. That check is dropped, and the title now says what the test proves.
- fetch: two titles said "no mirror retry" while the bodies assert a mirror retry. Retitled.
- r2Mirror: the collision test asserted that the collision happened. r2MirrorUrl now requires a "/" after the R2 base, and the test asserts that a lookalike prefix is not mirrored.
- agentUvReaper and delegate: the fake uv was a shell script, which macOS ps reports as "sh", so 4 tests failed on every macOS run. The fake is now a symlink named uv to sleep. A copied binary is SIGKILLed by macOS, which would have let the kill tests pass trivially.
- firebaseAuthIdentity: the hand-written verifiedLocalFirebaseAuth fake accepted any 127.* host, any protocol and any path. The test now uses the real module on a tmp config dir. The persistence-failure case writes under a regular file, and asserts that nothing was persisted.
- comfybuilder-models e2e: the stageBuildModels hook re-implemented staging and had drifted from the real task. The task body is now exported as runModelStagingTask, which returns staged, busy or aborted, and the hook calls it.
- quit-flow e2e: the title claimed tray-close mode, which settings strips on load. Retitled, and the always-true toBeTruthy is dropped.
- devhooks-smoke e2e: deleted. The first test had no expect, and every hook is asserted by downloads-shelf, update-pills and lifecycle-model-downloads.
- title-bar-hover-gate-comfy-window e2e: deleted. It repeated the same 5 tests line for line after launching live cloud.comfy.org.

* test(e2e): keep local macOS runs from taking OS focus (Comfy-Org#1979)

Extend the background run from Comfy-Org#1932 to macOS. A local macOS run now
loads the same -r preload as Windows, so windows show inactive and the
focus calls do nothing. On macOS the preload also sets the activation
policy to accessory before the app is ready. The test app then has no
Dock icon or menu bar and never becomes the frontmost app.

The shim is renamed to backgroundShim.cjs because it is no longer
Windows-only. @needs-focus now works on both platforms: a background
run drops those tests from macos and runs them in a new macos-focus
project (pnpm run test:e2e:macos:focus), as windows-focus does. No test
is tagged today. CI, lifecycle and E2E_FOREGROUND=1 keep real focus.

Checked on macOS by polling the frontmost app every ~200ms while the
suite ran, and reading the app type from lsappinfo. Electron was never
frontmost and was registered as a UIElement app.

---------

Co-authored-by: Alexis Rolland <alexisrolland@hotmail.com>
Co-authored-by: Claude <noreply@anthropic.com>
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.

1 participant