Commit Graph
312 Commits
Author SHA1 Message Date
Dariusz L 41f0f6c7b4 Use shared global notification container across custom nodes
Add SHARED_CONTAINER_ID constant so the toast container is no longer namespaced per-node.

This allows different custom nodes or projects to stack notifications in one container.
2026-06-30 01:27:52 +02:00
Dariusz L 24db5ed54c refactor: centralize notification handling into shared utility 2026-06-30 01:08:11 +02:00
Dariusz L 54f861a02e feat: add aria2 daemon start/stop control and install migration
- Add /aria2/start and /aria2/stop API endpoints for explicit daemon lifecycle control
- Track aria2 daemon state (managed/running/version/active_transfers) in get_aria2_status
- Implement idle auto-stop timer (5 minutes) with aria2_auto_stop_daemon setting
- Add start_aria2_daemon() and stop_aria2_daemon() helpers in core/downloader.py
- Migrate legacy release-* install directories to normalized versioned paths
- Normalize aria2 version strings (strip release-/v prefixes) in installer metadata
- Update aria2 archive extraction to extract-to-temp then copy into canonical dir
- Add frontend daemon controls: status display, stop button, auto-stop toggle
2026-06-30 00:03:08 +02:00
Dariusz L 8b15500ce4 Add automatic aria2 binary installation support
- New core/aria2_installer.py module downloads the latest aria2c release
  from GitHub for Windows, macOS, and Linux with safe path extraction.
- New POST /model_resolver/aria2/install endpoint triggers installation
  and saves the resolved aria2c_path plus download_backend=aria2.
- Options UI adds an Install aria2 button, hides aria2-specific fields
  when another backend is selected, and updates status on completion.
- Includes .gitignore entry for tools/aria2/ so installed binaries are
  not committed.
2026-06-29 21:55:27 +02:00
Dariusz L 5f1b53e41c Add option to show/hide auto-download capable models in missing browser 2026-06-29 20:54:54 +02:00
Dariusz L 378f82cb25 feat: identify auto-download-capable missing models; add workflow schema inference and badge UI
- Extend dynamic widget category hints to capture choice source (static/hybrid/folder_paths)
- Infer workflow schema model candidates from output category hints when widget values match known presets
- Surface auto_download_capable and auto_download_candidate flags in missing model data
- Merge these flags on duplicate missing model entries
- Add cloud-download badge UI with tooltip explaining auto-download context
- Update huggingface author index metadata timestamp
2026-06-29 20:34:03 +02:00
Dariusz L f780e6507b feat: preserve search state and resolution aliases across workflow transitions
- Propagate missing_search_key through resolution queue and download
  resolution paths so cache lookups remain consistent after workflow
  re-analysis or active searches.
- Set preserveSearchCacheAcrossNextWorkflowSync before reloading
  workflow data following batch queue/resolve operations.
- Remember applied resolu tions (rememberAppliedResolvedSelections)
  after both queue and direct downloads so alias tracking is not lost.
- getMissingSearchKey now short-circuits on missing_search_key and
  search_key fields instead of always deriving from node identity,
  fixing spurious cache misses.
- Guard settleInactiveSearchProgress so non-active workflow states
  only update the cache when the active workflow hosts a matching
  background search job.
- After workflow analysis, call applyResolvedSelectionAliases
  so analysis data reflects user selections.
- When switching workflows, clone and merge the previous workflow
  search-result cache and migrate background search jobs that are
  still running, so active searches are not interrupted or dropped.
2026-06-28 04:04:45 +02:00
Dariusz L 59e874c17f feat: improve CivitAI download support with session tokens and proper headers
- Add __init__.py: support civitai.red domain and session token cookies
- Add core/downloader.py: build_download_headers for consistent User-Agent,
  Accept, and CivitAI-specific Referer/Origin headers across download backends
- Resolve CivitAI API redirects before handing URLs to aria2
- Strip sensitive URL parameters from download logs
- Forward civitai_session_token from the frontend to the downloader
2026-06-28 03:42:41 +02:00
Dariusz L c79e217a42 feat: support grouped download progress for multiple active downloads
- Add getActiveDownloadEntriesForMissing to find all active downloads
  targeting the same missing model entry.
- Refactor resolve_download_methods.js to extract status labels,
  progress markup builders, and snapshot helpers.
- Render multiple concurrent downloads in a grouped progress list
  when more than one download is active for the same missing model.
- Update attachDownloadActionHandlers to resolve downloadId from
  dataset attributes so grouped controls target the right download.
- Add CSS for grouped download progress items in the missing models UI.
- Refresh huggingface-author-index.json timestamp.
2026-06-27 23:51:43 +02:00
Dariusz L aa91d1410c feat: add aria2 download backend with pause/resume support
Integrates aria2c as an alternative download backend alongside the built-in
Python downloader. Adds settings for selecting the backend and configuring
the aria2c executable path, plus a status check button in the options panel.

Backend changes:
- core/downloader.py: aria2 daemon lifecycle, JSON-RPC client, pause/resume
  state machine, and transfer tracking
- core/settings.py: download_backend normalization and aria2c_path setting
- __init__.py: new API routes for pause, resume, and aria2 status checks

Frontend changes:
- options_methods.js: backend selector, aria2c path input, check button,
  and local storage persistence
- resolve_download_methods.js: pause/resume handlers, pending status
  transitions, and progress rendering for aria2 downloads
- queue_methods.js: queue panel pause/resume buttons, backend badge, and
  debounced panel updates
- search_panel.js: actionsHtml support for composite action buttons
2026-06-27 23:39:31 +02:00
Dariusz L e151f9b4c1 fix: normalize download category token before color lookup
Apply normalizeDownloadCategory to the category token before checking
color mappings, preventing unknown-category tokens from falling through
to the default class. Also add clip_gguf to the clip color mapping.
2026-06-27 22:25:55 +02:00
Dariusz L 5571035e23 Replace resolved badge with check icon in missing model rows
- Switch missing model row layout from grid to flex
- Add circleCheckBig SVG icon to icon_utils
- Replace green 'Resolved' text pill with inline checkmark icon
- Update CSS with resolved icon and model details wrapper styles
2026-06-27 22:21:21 +02:00
Dariusz L 4ac05c0228 Make missing-model list header sticky during scroll
Move the .mr-missing-list-head element inside the scrollable .mr-missing-list
container and apply position: sticky so the column headers remain visible when
the list overflows. Adjust grid layout and row alignment rules to support the
new structure.
2026-06-27 20:52:45 +02:00
Dariusz L b73cdb0f40 feat: improve category resolution and missing models browser
- Expand preferred categories to include clip_vision, ipadapter, sams, ultralytics
- Add clip_gguf alias for text_encoders in both backend and frontend
- Add explicit diffusion_models/text_encoders mappings in CATEGORY_MAP
- Refactor get_model_roots to skip custom_nodes/configs, use template key
  aliases, accept new folder keys from known categories, and normalize
  ultralytics paths (yolo/bbox, yolo/segm, yolo -> parent)
- Pass missing object through resolve_download_methods and search_panel
  so category selection can use widget hints
- Refactor frontend download target resolution:
  - getMissingSupportedDownloadCategories respects widget/type hints
  - getNodeTypeDownloadCategory splits exact-node map and adds
    normalizeNodeCategoryToken / getNodeTypeDownloadCategoryFromTokens
    for GGUF and future node families
  - getSourceResultDownloadCategory and _sourceSupportLevel accept
    missing for unified logic
- Prioritize dynamic widget category hints in workflow analyzer and
  include category_hints/folder_key_hints on all model refs
- Add folder count badges and path normalization in missing browser
  (normalizeMissingFolderRootPath handles category suffixes / bbox/segm)
2026-06-27 19:36:47 +02:00
Dariusz L e53d9f2a0b feat: generalize remote metadata lookup across CivitAI, CivArchive, and HuggingFace
Replace CivitAI-only search with a multi-source metadata resolution route using
SHA256 exact-match validation, dead-link filtering, and live download URL
probing. Unify sidecar metadata saving across all remote sources. Add
force-refresh support, local metadata import with preview detection, and
frontend source-aware UI controls.
2026-06-27 03:25:31 +02:00
Dariusz L 3cd302d4ee feat: implement local-only model info fetching and refactor model info dialog
- Add local_only endpoint mode: returns basic file info (filename, size, path,
  location, sha256) without querying CivitAI or computing file hashes
- Validate provided sha256/hash inputs (must be 64-char hex) and fall back to
  empty string when invalid
- Refactor monolithic info response builder into build_info_response() helper
  used across all result paths (local, CivitAI success, CivitAI fallback,
  not-found), reducing duplication
- Add get_model_info_for_file(local_only=True) early return in CivitAI source
  that builds a minimal local-only result without hash lookup
- Split frontend fetchModelInfoForDialog into:
  - fetchLocalModelInfoForDialog: opens dialog with local data immediately,
    marks civitai_checked=false
  - fetchCivitaiModelInfoForDialog: async CivitAI lookup triggered by user
- Add 'Fetch with CivitAI' button in info dialog when local file exists but
  CivitAI has not been checked yet
- Infer model_type from category in both backend and frontend to reduce
  reliance on upstream data shape
- Fix sidecar metadata condition (was skipping save when path already existed)
- Add cursor/disabled styles for info dialog CivitAI link button
2026-06-26 22:16:44 +02:00
Dariusz L 4e576cbd56 feat: add SHA256 hash calculation with cancellation, progress tracking, and remote size probing 2026-06-26 21:51:55 +02:00
Dariusz L af31075cb1 style: tighten padding in model details panel and sidebar
Reduce excessive padding in .mr-model-details-side, .mr-model-details-panel, and .mr-model-details-side to make the layout more compact and consistent with the updated modal spacing.
2026-06-26 03:22:34 +02:00
Dariusz L e386808dd4 feat: add CivitAI link, file matching, and mirror selection to model details
Add a direct "View on CivitAI" action button when a model has CivitAI IDs,
auto-detect the matched file via hash/URL/filename, surface the preferred
mirror, and render file entries as collapsible details with summary badges.
Normalize CSS formatting (rgba spacing, rule separators) for consistency.
2026-06-26 01:44:15 +02:00
Dariusz L c7d6b27fb0 feat: add search cancellation API and harden CivArchive source resolution
Add a /model_resolver/search-cancel/{progress_id} endpoint with a
SearchCancelled exception so in-flight source searches abort cleanly on
batch cancel. Track sourceProgressIds alongside sourceControllers so the
frontend can cancel backend progress polls. Rework CivArchive extraction
with robust __NEXT_DATA__ parsing, hash-page file resolution, model-link
scraping, confidence-based candidate filtering, and expanded type maps.
Add conftest.py for pytest path setup, update .gitignore for scratch/,
and refresh huggingface-author-index.json.
2026-06-26 00:55:38 +02:00
Dariusz L d49ae0becc refactor: centralize API calls through ResolverManagerDialog.fetchJson
Replace scattered api.fetchApi(...) + response.ok + response.json() boilerplate
across all web/modules with a unified this.fetchJson() helper defined on the
base dialog class.

Changes:
- dialog.fetchJson(url, options, context) handles headers, status checks, and
  JSON parsing in one place
- Extracts server-side error messages (errData.error) for better UX
- Optional silent flag suppresses notifications for background/refresh requests
- All callers simplified: async return, shorter bodies, consistent error handling
- BOM removed from workflow_update_methods.js and tabs_loaded_methods.js
2026-06-25 02:01:18 +02:00
Dariusz L 8f890f6992 refactor: centralize path utilities in core/path_utils
Extract repeated path normalization and identity logic from __init__.py,
core/resolver.py, core/downloader.py, and core/scanner.py into a shared
core/path_utils module. Also add a loading state to the local model picker
so it waits for models to load before rendering options.
2026-06-25 01:23:20 +02:00
Dariusz L 2fe2092dfc refactor: centralize API helpers, extract shared UI utilities, simplify dropdown positioning 2026-06-25 00:59:06 +02:00
Dariusz L 91549dbc9b refactor: delegate download cancellation, reorder workflowId, remove unused copy/filter helpers 2026-06-25 00:39:23 +02:00
Dariusz L c0a4398911 refactor: deduplicate download logic into executeDownloadRequest
Extract shared download orchestration from downloadModel and downloadFromSearch
into a single executeDownloadRequest method to eliminate ~125 lines of duplication.
2026-06-25 00:30:25 +02:00
Dariusz L 0b98054536 refactor: consolidate duplicated credential checks and local match fetch logic 2026-06-24 23:54:18 +02:00
Dariusz L dcac1b7c8a refactor: consolidate shared utilities and relocate view-specific settings logic
- Moved formatting helpers (formatBytes, formatDuration, getDownloadEtaText,
  formatDownloadProgressMeta) and getLocalMatchDisplayInfo from
  resolve_download_methods.js and missing_browser_methods.js into
  render_format_methods.js for shared reuse.
- Relocated settings-related methods (getStoredTokens,
  applyFrontendLoggingPreference, loadSettingsFromServer) and their
  log_system imports from download_target_methods.js into
  options_methods.js, where they are actually consumed by the options UI.
- Simplified missing_browser_methods.js to use
  getLocalMatchDisplayInfo instead of inline local-match code.
2026-06-24 23:42:34 +02:00
Dariusz L 9d3f18f288 refactor: consolidate refreshMissingListRow into shared method
Remove duplicated refreshMissingListRowForMissing and
refreshMissingListRowLocalMatch implementations, replacing them
with a single refreshMissingListRow method in missingBrowserMethods.
Also strip unnecessary BOM from imports.
2026-06-24 23:34:33 +02:00
Dariusz L fb8a65758b refactor: centralize context-menu attribute and element helpers
Replace scattered inline encodeURIComponent(JSON.stringify(...)) and
manual oncontextmenu/dataset assignments with unified helpers added to
renderFormatMethods:

  - encodeContextMenuModel(context): safe JSON serialization for data-model
  - getContextMenuAttrs(context, tooltip): HTML attribute string for
    template literals (used in 5 files)
  - getContextMenuProps(context, tooltip): props object for imperative
    element assignment (used in missingBrowserMethods)
  - setContextMenuElement(element, context, tooltip): sets or clears
    data-model, data-tooltip, and oncontextmenu on a DOM element

Reduces duplication across 5 modules, adds try/catch around JSON
serialization, and removes 14 lines of repeated oncontextmenu wiring.
2026-06-24 23:19:02 +02:00
Dariusz L b5d10fa5cc refactor: extract floating tree picker positioning into shared tree_picker.js
Create createFloatingTreePicker() utility to replace duplicated inline
floating positioning logic in download_target_methods.js and
missing_browser_methods.js. The factory handles portalization, duplicate
removal, viewport-aware positioning (open above/below), scroll container
height calculation, and scroll/resize listener lifecycle management,
reducing ~175 lines of duplicated code.
2026-06-24 23:04:50 +02:00
Dariusz L d3c7ace464 feat: add folder browser context menu and local model deduplication
- Add right-click 'Open Folder' context menu to folder browser rows and
  root group headers, with left-click guards to prevent context actions on
  non-primary clicks
- Deduplicate local model entries before filtering using path-based identity
  and category ranking to prefer the active download category
2026-06-24 22:57:56 +02:00
Dariusz L 26cca55fee feat: add right-click context menu to local model folder browser
- Introduce --mr-z-context-menu-popup z-index variable and shift existing
  z-indices up by one so context menu popups layer correctly above
  other UI elements.
- Update resolver-main.css and resolver-shell.css context-menu rules to
  use the new popup z-index with a fallback.
- Add joinLocalModelPath, buildLocalFolderContext, buildLocalModelContext,
  and getLocalPathContextAttrs helpers to missing_browser_methods.js.
- Wire folder and model entries in the local browser to include encoded
  JSON context attributes so right-click opens the model/folder context
  menu with the correct open-folder and model actions.
2026-06-24 22:44:51 +02:00
Dariusz L f4f07ccb0a completion: add local model browser with category-aware filtering and download target synchronization 2026-06-24 22:30:31 +02:00
Dariusz L 46b1e155b6 feat: remember and normalize downloaded subfolder paths for reuse in download targets 2026-06-24 22:12:06 +02:00
Dariusz L 5445dd4ac0 feat: implement local hash matching via metadata sidecar files
Backend adds SHA256 normalization, metadata sidecar lookup, and hash fields across source modules. Frontend handles local_hash_matches in search responses and missing browser.
2026-06-24 21:59:10 +02:00
Dariusz L 8867058312 feat: improve download folder selection UX with category tooltips and dynamic widget category hints
- core/workflow_analyzer.py: add dynamic widget category hint extraction via threaded cache and sentinel-prefix matching; get_model_widget_category_hints now returns all inferred categories including dynamic ones, improving model folder detection for workflows with encoded category metadata.
- web: add ? help icon with context-aware tooltip to download folder selector explaining why a category was auto-selected (preserved manual choice, node type hint, workflow-detected category, default fallback, or best available). Tooltip refreshes live as the user changes the folder selection.
- web/css/resolver-main.css: style the new category help badge.
- metadata/huggingface-author-index.json: update index entry.
2026-06-24 21:01:21 +02:00
Dariusz L c5c3490210 feat: add auto-refresh of ComfyUI model catalog after Apply 2026-06-24 19:22:55 +02:00
Dariusz L 8c0168ab76 feat: skip model analysis for empty or non-model workflows
Add early-return optimizations so both backend and frontend avoid unnecessary
URL extraction and disk scanning when a workflow has no nodes or contains
no potential model references.

Also tighten API input validation by rejecting non-object workflow_json.
2026-06-24 03:46:50 +02:00
Dariusz L a01be11e27 feat(info-dialog): improve model info dialog layout and UX
- Add Escape key handler to close the info dialog, with proper cleanup
- Extract reusable renderInfoFieldLabel() helper to reduce code duplication
- Add dedicated SVG icons (file, fileText, hash, box, hardDrive, bookType) for field labels
- Adjust dialog sizing to calc(100vh - 16px) with 92vw max width
- Refactor CSS into .mr-info-field-label / .mr-info-label-icon / .mr-info-label-text
- Improve trained-words row layout with flex styling
2026-06-23 21:15:22 +02:00
Dariusz L b292411b93 feat: enhance model info image preview with CivitAI badge, metadata fields, and linked resources
- Add CivitAI badge overlay on example images with icon and direct link
- Extract denoise, scheduler, and cfgScale from metadata in civitai.py
- Support additionalResources alongside resources in both parser paths
- Redesign resource display with clickable links, version badges, and type/weight pills
- Drop prompt tags section and getInfoImagePromptTags; focus preview on generation data and resources
- Include full metadata rows and resources in copy-to-clipboard output
- Add matching CSS for badge, resource layout, and interactive states
2026-06-23 20:48:08 +02:00
Dariusz L 16a32de8de feat: improve model info dialog with clickable location, wider layout, and refined styling 2026-06-23 20:28:48 +02:00
Dariusz L 093b6d33a7 feat: enrich model info dialog with location, size, tags, and trained words from metadata 2026-06-23 19:47:49 +02:00
Dariusz L ee7d59546c feat(folder-browser): show create path message and update model index
- Update HuggingFace author index metadata (file count, repo entries)
- Style empty folder browser state with grid layout and monospace path display
- When a non-existent subfolder is typed, inform user the path will be created during download
2026-06-23 19:01:35 +02:00
Dariusz L 1cfc0beeb6 refactor: replace inline dropdown display toggling with reusable floating positioning helpers
Switch download target dropdowns from absolute-positioned elements clipped by
scroll containers to body-ported fixed-position lists managed by
downloadTargetMethods. Adds showDropdownList, hideDropdownList,
portalDropdownList, positionFloatingDropdownList, and related helpers so the
UI can keep dropdowns visible and correctly placed near their anchors.
2026-06-23 06:22:57 +02:00
Dariusz L 762363d7ef refactor: replace inline dropdown hide logic with reusable outside-dismiss helpers
Add bindDropdownOutsideDismiss and pointer-guard utilities to downloadTargetMethods,
then use them in resolveDownloadMethods to remove duplicated hide-on-blur and
setTimeout-based hide patterns. This centralizes dropdown dismissal behavior and
handles pointer/mouse/touch events consistently across dropdown lists.
2026-06-23 05:02:59 +02:00
Dariusz L f94abe1489 feat(folder-browser): improve expand/collapse interaction and row styling
Make expandable folder rows clearly distinguishable and allow clicking the
left-side toggle zone to expand/collapse folders instead of selecting them.

- Add is-expandable class and data-state-key to expandable rows
- Extract toggleFolderBrowserState helper for reuse
- Extract isFolderBrowserToggleZoneClick to detect toggle-zone clicks
- Adjust toggle button width/positioning via CSS for expandable rows
- Apply box-sizing: border-box to folder browser toggle
2026-06-23 04:48:05 +02:00
Dariusz L baa8849fa4 fix: improve floating subfolder list positioning and scroll behavior
- Remove fixed max-height constraints from folder browser scroll container
- Calculate available height dynamically based on viewport space
- Account for container chrome (borders, padding) and child elements when setting scroll max-height
- Use clampNumber for popup positioning to keep it within viewport bounds
- Ignore scroll events originating from within the list to prevent jittery repositioning
- Add box-sizing: border-box to folder browser for consistent sizing
2026-06-23 04:42:00 +02:00
Dariusz L c08eabc465 Simplify download folder browser by removing manual path rows and preserving scroll position
- Remove 'Use model root' and 'Use typed folder' manual rows from the folder browser
- Remove category badge and folder browser header elements
- Add nested scroll element detection for scroll delta handling
- Preserve scroll position when re-rendering the folder browser on toggle
2026-06-23 04:28:41 +02:00
Dariusz L f2cd4cde30 feat: replace flat subfolder list with floating folder browser for download targets
Refactor populateSubfolderOptions into renderDownloadFolderBrowser to show a
persistent floating panel with an expandable folder tree grouped by base
directory. Includes live preview of the selected target path, manual
typed-folder rows, and window/viewport-aware positioning. Prevents duplicate
portal mounts and cleans up resize/scroll bindings on hide.
2026-06-23 04:16:38 +02:00
Dariusz L d8124d03da feat: add live backend search progress tracking
Frontend now polls a new backend endpoint (/model_resolver/search-progress/{progress_id})
to display real-time, per-source progress messages and percentages during model searches,
replacing static 'Searching...' indicators with granular status updates.
2026-06-23 02:23:45 +02:00