Turns out the vuedraggable import has side effects that break other
test cases. This is awful and requires further investigation, but for
now, the import is performed at execution time
This pull request updates event handling in the selection toolbox
components to ensure that mouse wheel events are properly forwarded to
the canvas, improving interaction consistency across the UI.
**Event handling improvements:**
* Changed the wheel event handler in `SelectionToolbox.vue` to use
`canvasInteractions.forwardEventToCanvas` instead of
`canvasInteractions.handleWheel`, ensuring wheel events are consistently
forwarded to the canvas.
* Added the wheel event handler to the `MoreOptions.vue` popover,
forwarding wheel events to the canvas for submenu interactions.
**Code organization updates:**
* Imported `useCanvasInteractions` in `MoreOptions.vue` to access the
new event forwarding method.
* Instantiated `canvasInteractions` in `MoreOptions.vue` for use in
event handling.## Summary
https://github.com/user-attachments/assets/46046086-35e8-4cd1-a11a-365705beb9cd
┆Issue is synchronized with this [Notion
page](https://www.notion.so/PR-5781-Wheel-Selection-Toolbox-and-Popover-27a6d73d3650812c9c4fe8440ff7dd1d)
by [Unito](https://www.unito.io)
## Refactor conflict detection system and move to manager extension
### Description
This PR refactors the conflict detection system, moving it from the
global composables to the manager extension folder for better code
organization. Additionally, it improves test type safety and adds
comprehensive test coverage for utility functions.
### Main Changes
#### 📦 Code Organization
- **Moved conflict detection to manager extension** - Relocated all
conflict detection related composables, stores, and utilities from
global scope to `/workbench/extensions/manager/` for better modularity
(https://github.com/Comfy-Org/ComfyUI_frontend/pull/5722)
- **Moved from** `src/composables/useConflictDetection.ts` **to**
`src/workbench/extensions/manager/composables/useConflictDetection.ts`
- Moved related stores and composables to maintain cohesive module
structure
#### ♻️ Refactoring
- **Extracted utility functions** - Split conflict detection logic into
separate utility modules:
- `conflictUtils.ts` - Conflict consolidation and summary generation
- `systemCompatibility.ts` - OS and accelerator compatibility checking
- `versionUtil.ts` - Version compatibility checking
- **Removed duplicate state management** - Cleaned up redundant state
and unused functions
- **Improved naming conventions** - Renamed functions for better clarity
- **Removed unused system environment code** - Cleaned up deprecated
code
#### 🔧 Test Improvements
- **Fixed TypeScript errors** in all test files - removed all `any` type
usage
- **Added comprehensive test coverage**:
- `conflictUtils.test.ts` - 299 lines of tests for conflict utilities
- `systemCompatibility.test.ts` - 270 lines of tests for compatibility
checking
- `versionUtil.test.ts` - 342 lines of tests for version utilities
- **Updated mock objects** to match actual implementations
- **Aligned with backend changes** - Updated SystemStats structure to
include `pytorch_version`, `embedded_python`,
`required_frontend_version`
#### 🐛 Bug Fixes
- **Fixed OS detection bug** - Resolved issue where 'darwin' was
incorrectly matched as 'Windows' due to containing 'win' substring
- **Fixed import paths** - Updated all import paths after moving to
manager extension
- **Fixed unused exports** - Removed all unused function exports
- **Fixed lint errors** - Resolved all ESLint and Prettier issues
### File Structure Changes
```
Before:
src/
├── composables/
│ └── useConflictDetection.ts (1374 lines)
└── types/
After:
src/
├── utils/
│ ├── conflictUtils.ts (114 lines)
│ ├── systemCompatibility.ts (125 lines)
│ └── versionUtil.ts (enhanced)
└── workbench/extensions/manager/
├── composables/
│ ├── useConflictDetection.ts (758 lines)
│ └── [other composables]
└── stores/
└── conflictDetectionStore.ts
```
### Testing
All tests pass successfully:
- ✅ **155 test files passed**
- ✅ **2209 tests passed**
- ⏩ 19 skipped (intentionally skipped subgraph-related tests)
### Impact
- **Better code organization** - Manager-specific code is now properly
isolated
- **Improved maintainability** - Smaller, focused utility functions are
easier to test and maintain
- **Enhanced type safety** - No more `any` types in tests
- **Comprehensive test coverage** - All utility functions are thoroughly
tested
### Commits in this PR
1. OS detection bug fix and refactor
2. Remove unused system environment code
3. Improve function naming
4. Refactor conflict detection
5. Remove duplicate state and unused functions
6. Fix unused function exports
7. Move manager features to workbench extension folder
8. Fix import paths
9. Rename systemCompatibility file
10. Improve test type safety
11. Apply ESLint and Prettier fixes
## Screenshots (if applicable)
[screen-capture.webm](https://github.com/user-attachments/assets/b4595604-3761-4d98-ae8e-5693cd0c95bd)
┆Issue is synchronized with this [Notion
page](https://www.notion.so/PR-5436-Manager-refactor-conflict-detect-2686d73d36508186ba06f57dae3656e5)
by [Unito](https://www.unito.io)
---------
Co-authored-by: Claude <noreply@anthropic.com>
## Summary
Fixed Vue node output restoration by consolidating state management
through the node output store.
## Changes
- **What**: Refactored node output cleanup and restoration logic in
`ChangeTracker` and `ComfyApp` to use centralized store methods
- **Breaking**: Removed direct manipulation of `app.nodeOutputs` in
favor of store-managed state
## Review Focus
State synchronization between `app.nodeOutputs` and `nodeOutputs.value`
during restore/reset operations, ensuring Vue reactivity is maintained.
┆Issue is synchronized with this [Notion
page](https://www.notion.so/PR-5788-fix-restoring-outputs-in-Vue-nodes-persisting-node-outputs-when-switching-between-workfl-27a6d73d365081b39411fed7479d8ac5)
by [Unito](https://www.unito.io)
## Summary
Split tailwind utils out to a shared package within the monorepo.
## Changes
- Creates `@comfyorg/tailwind-utils` package
- Does not require export, publishing, etc
- Uses `export` to ensure this change does not impact other PRs (many
imports to update)
- If we _want_ to update all imports, there are two commits ready to be
re-applied
- e.g. `git revert 80960c2a82c0d1ac06eee1bb83ac333216b2b376`
## Review Focus
- Is this pattern desirable?
- Should we just include this in a broader design-system split? I kind
of vote yes, but also it's a good small, first step.
┆Issue is synchronized with this [Notion
page](https://www.notion.so/PR-5777-Split-Tailwind-utility-functions-out-to-a-shared-package-2796d73d3650815f976fc73b4fb86ef3)
by [Unito](https://www.unito.io)
## Summary
Added mute state support to Vue nodes with visual feedback and keyboard
shortcut functionality.
## Changes
- **What**: Implemented mute state (mode 2) for Vue nodes with opacity
styling and `Ctrl+M` hotkey support
## Review Focus
Visual consistency between bypass and mute states, and keyboard shortcut
conflict detection with existing hotkeys.
## Test Coverage
- Single node mute/unmute with `Ctrl+M` hotkey
- Multi-selection mute/unmute operations
- Visual state verification with opacity changes
## Related
- https://github.com/Comfy-Org/ComfyUI_frontend/pull/5715
┆Issue is synchronized with this [Notion
page](https://www.notion.so/PR-5770-Add-muted-state-to-Vue-nodes-2796d73d36508143b3edfbcb782de7c1)
by [Unito](https://www.unito.io)
## Summary
UseNewMenu has been defaulted to Top in the app for over a year;
Playwright’s test default lagged behind. This PR aligns the test default
with reality and keeps legacy specs stable.
## Changes
- tests(e2e): default to 'Top' via fixture; specs that previously relied
on the old implicit default now explicitly set 'Comfy.UseNewMenu' to
'Disabled'.
- docs(browser-tests): remove outdated README note suggesting tests set
'Top' manually.
## Review Focus
- Intentional uses of 'Top' and 'Bottom' remain unchanged.
- Confirm ComfyPage default remains 'Top' (see
browser_tests/fixtures/ComfyPage.ts).
## Screenshots (if applicable)
N/A
┆Issue is synchronized with this [Notion
page](https://www.notion.so/PR-5746-test-e2e-align-test-default-menu-to-Top-make-legacy-specs-explicit-2786d73d365081218d06c1346f3ae18e)
by [Unito](https://www.unito.io)
---------
Co-authored-by: github-actions <github-actions@github.com>
## Summary
I want to take a more general look at `comfyApp.graph.onTrigger` but
this is the cleanest fix I could come up with for #5694.
I will explore simplifying onTrigger in a separate PR.
## Changes
1. Create a `node:slot-errors:changed` trigger.
2. Trigger it if we find any of the node slots have errors.
3. Check each node to see if there is any error present.
4. Add an error class if there are.
## Screenshots (if applicable)
Working error states!
<img width="1049" height="987" alt="Screenshot 2025-09-23 at 8 40 04 PM"
src="https://github.com/user-attachments/assets/30e13283-129c-4d9c-b342-e7037582998a"
/>
┆Issue is synchronized with this [Notion
page](https://www.notion.so/PR-5758-fix-properly-show-error-states-2786d73d365081cbbf62c314c7f5f380)
by [Unito](https://www.unito.io)
---------
Co-authored-by: Alexander Brown <drjkl@comfy.org>
## Summary
This PR fixes a flaky test in the load audio widget spec that was
causing intermittent failures in CI.
## Problem
The test was attempting to trigger a file chooser event before the
widget's upload button was fully rendered and ready for interaction,
leading to race conditions.
## Solution
Added an explicit wait for the widget element to be visible before
triggering the file chooser, ensuring the DOM is ready for interaction.
## Changes
- Added `waitFor` to verify widget visibility before file upload
- Ensures proper synchronization between DOM updates and test actions
## Test plan
- [x] Browser tests pass locally
- [x] Typecheck passes
- [ ] CI tests pass
🤖 Generated with [Claude Code](https://claude.ai/code)
┆Issue is synchronized with this [Notion
page](https://www.notion.so/PR-5755-bugfix-Stabilize-flaky-load-audio-widget-test-2786d73d365081cebaefdc6470333c5d)
by [Unito](https://www.unito.io)
---------
Co-authored-by: Claude <noreply@anthropic.com>