mirror of
https://github.com/willmiao/ComfyUI-Lora-Manager.git
synced 2026-10-03 08:45:31 -03:00
fix(downloads): route unknown checkpoint baseModels to diffusion models by default
CivitAI labels new DiT architectures (MiniMax H3, future Flux/Wan/Qwen variants) as model.type "Checkpoint" with plain "Model" file entries, so the DIFFUSION_MODEL_BASE_MODELS allowlist could never keep up and such downloads were mis-routed to the checkpoint roots (e.g. model 2877206 / version 3374439). The set of true full-checkpoint families is closed, so the baseModel fallback is inverted: 1. file type UNet/Diffusion Model -> unet (unchanged) 2. baseModel in DIFFUSION_MODEL_BASE_MODELS (now incl. MiniMax H3) -> unet 3. baseModel in new CHECKPOINT_BASE_MODELS (SD 1.x/2.x/3.x, SDXL, Pony, Illustrious, NoobAI) -> checkpoint 4. unknown/empty baseModel -> new unknown_base_model_routing setting, defaulting to diffusion models The setting is exposed under Settings > Downloads, validated in SettingsManager, and threaded into both the download manager and the download routing endpoint so they keep agreeing.
This commit is contained in:
@@ -96,10 +96,15 @@ class DownloadRoutingHandler:
|
||||
}
|
||||
)
|
||||
|
||||
from ...services.settings_manager import get_settings_manager
|
||||
|
||||
is_diffusion = is_diffusion_model_download(
|
||||
model_type,
|
||||
file_types=(str(t) for t in file_types),
|
||||
base_model=base_model,
|
||||
unknown_base_model_default=get_settings_manager().get(
|
||||
"unknown_base_model_routing", "diffusion_model"
|
||||
),
|
||||
)
|
||||
return web.json_response(
|
||||
{
|
||||
|
||||
@@ -1670,6 +1670,9 @@ class DownloadManager:
|
||||
model_type,
|
||||
file_types=(f.get("type", "") for f in version_info.get("files", [])),
|
||||
base_model=base_model_value,
|
||||
unknown_base_model_default=get_settings_manager().get(
|
||||
"unknown_base_model_routing", "diffusion_model"
|
||||
),
|
||||
)
|
||||
|
||||
# Existence check after the metadata fetch (#1058):
|
||||
|
||||
@@ -13,6 +13,7 @@ import logging
|
||||
from typing import Iterable, Optional
|
||||
|
||||
from ..utils.constants import (
|
||||
CHECKPOINT_BASE_MODELS,
|
||||
CIVITAI_FILE_TYPE_TO_OTHER_SUB_TYPE,
|
||||
CIVITAI_TYPE_TO_OTHER_SUB_TYPE,
|
||||
DIFFUSION_MODEL_BASE_MODELS,
|
||||
@@ -24,17 +25,27 @@ logger = logging.getLogger(__name__)
|
||||
# model (loaded via UNETLoader in ComfyUI) rather than a full checkpoint.
|
||||
DIFFUSION_FILE_TYPES = frozenset({"UNet", "Diffusion Model"})
|
||||
|
||||
# Allowed values for the "unknown_base_model_routing" setting / the
|
||||
# unknown_base_model_default parameter below.
|
||||
ROUTING_DIFFUSION_MODEL = "diffusion_model"
|
||||
ROUTING_CHECKPOINT = "checkpoint"
|
||||
|
||||
|
||||
def is_diffusion_model_download(
|
||||
model_type: str,
|
||||
file_types: Iterable[str] = (),
|
||||
base_model: str = "",
|
||||
unknown_base_model_default: str = ROUTING_DIFFUSION_MODEL,
|
||||
) -> bool:
|
||||
"""Return True when a download should be routed to the unet roots.
|
||||
|
||||
Only applies to downloads initiated from the checkpoint library.
|
||||
Priority: (1) any file has type "UNet" or "Diffusion Model" (the more
|
||||
direct signal from CivitAI), (2) baseModel is a known diffusion model.
|
||||
direct signal from CivitAI), (2) baseModel is a known diffusion model,
|
||||
(3) baseModel is a known full checkpoint -> not diffusion, (4) unknown
|
||||
or empty baseModel -> the ``unknown_base_model_default`` setting, which
|
||||
defaults to diffusion because the set of true checkpoint families is
|
||||
closed while new DiT base models appear all the time.
|
||||
"""
|
||||
if model_type != "checkpoint":
|
||||
return False
|
||||
@@ -54,7 +65,16 @@ def is_diffusion_model_download(
|
||||
)
|
||||
return True
|
||||
|
||||
return False
|
||||
if base_model in CHECKPOINT_BASE_MODELS:
|
||||
return False
|
||||
|
||||
is_diffusion = unknown_base_model_default != ROUTING_CHECKPOINT
|
||||
logger.info(
|
||||
"baseModel '%s' is unknown, routing to %s folder (unknown_base_model_routing)",
|
||||
base_model,
|
||||
"unet" if is_diffusion else "checkpoint",
|
||||
)
|
||||
return is_diffusion
|
||||
|
||||
|
||||
def resolve_other_download_sub_type(
|
||||
|
||||
@@ -130,6 +130,9 @@ DEFAULT_SETTINGS: Dict[str, Any] = {
|
||||
"metadata_refresh_skip_paths": [],
|
||||
"skip_previously_downloaded_model_versions": False,
|
||||
"download_skip_base_models": [],
|
||||
# Routing target for checkpoint downloads whose baseModel is neither a
|
||||
# known diffusion model nor a known full checkpoint (CHECKPOINT_BASE_MODELS).
|
||||
"unknown_base_model_routing": "diffusion_model",
|
||||
"backup_auto_enabled": True,
|
||||
"backup_retention_count": 5,
|
||||
"use_new_license_icons": True,
|
||||
@@ -1628,6 +1631,16 @@ class SettingsManager:
|
||||
return normalized
|
||||
return "alongside"
|
||||
|
||||
@staticmethod
|
||||
def _normalize_unknown_base_model_routing(value: Any) -> str:
|
||||
"""Return a valid unknown-base-model routing target, falling back to ``diffusion_model``."""
|
||||
|
||||
if isinstance(value, str):
|
||||
normalized = value.strip().lower()
|
||||
if normalized in ("diffusion_model", "checkpoint"):
|
||||
return normalized
|
||||
return "diffusion_model"
|
||||
|
||||
def _refresh_sidecar_storage_config(self) -> None:
|
||||
"""Rebuild dependent config state after sidecar storage settings change."""
|
||||
|
||||
@@ -1840,6 +1853,8 @@ class SettingsManager:
|
||||
self._migrate_recipes_directory(current_recipes_dir, target_recipes_dir)
|
||||
elif key == "sidecar_storage_mode":
|
||||
value = self._normalize_sidecar_storage_mode(value)
|
||||
elif key == "unknown_base_model_routing":
|
||||
value = self._normalize_unknown_base_model_routing(value)
|
||||
elif key == "sidecar_storage_path":
|
||||
value = self._normalize_recipes_path_value(value)
|
||||
self.settings[key] = value
|
||||
|
||||
@@ -371,6 +371,7 @@ DIFFUSION_MODEL_BASE_MODELS = frozenset(
|
||||
# Other diffusion models
|
||||
"Ernie",
|
||||
"Ernie Turbo",
|
||||
"MiniMax H3",
|
||||
"Nucleus",
|
||||
"Qwen",
|
||||
"ZImageBase",
|
||||
@@ -380,6 +381,39 @@ DIFFUSION_MODEL_BASE_MODELS = frozenset(
|
||||
]
|
||||
)
|
||||
|
||||
# baseModel values from CivitAI that are true full checkpoints (loaded via
|
||||
# CheckpointLoaderSimple in ComfyUI). New DiT families appear on CivitAI all
|
||||
# the time, so download routing inverts the fallback: anything NOT in this
|
||||
# closed set (and not a known diffusion model) is treated as a diffusion
|
||||
# model by default (see py/services/download_routing.py).
|
||||
# "Pony V7" is deliberately excluded: it is not an SDXL-derivative full
|
||||
# checkpoint, so it follows the unknown-base-model default (diffusion).
|
||||
CHECKPOINT_BASE_MODELS = frozenset(
|
||||
[
|
||||
# Stable Diffusion 1.x
|
||||
"SD 1.4",
|
||||
"SD 1.5",
|
||||
"SD 1.5 LCM",
|
||||
"SD 1.5 Hyper",
|
||||
# Stable Diffusion 2.x
|
||||
"SD 2.0",
|
||||
"SD 2.1",
|
||||
# Stable Diffusion 3.x
|
||||
"SD 3",
|
||||
"SD 3.5",
|
||||
"SD 3.5 Medium",
|
||||
"SD 3.5 Large",
|
||||
"SD 3.5 Large Turbo",
|
||||
# SDXL and its full-checkpoint derivatives
|
||||
"SDXL 1.0",
|
||||
"SDXL Lightning",
|
||||
"SDXL Hyper",
|
||||
"Pony",
|
||||
"Illustrious",
|
||||
"NoobAI",
|
||||
]
|
||||
)
|
||||
|
||||
# Supported baseModel values for download exclusion settings.
|
||||
# Keep this aligned with static/js/utils/constants.js, excluding the generic "Other" value.
|
||||
SUPPORTED_DOWNLOAD_SKIP_BASE_MODELS = frozenset(
|
||||
|
||||
Reference in New Issue
Block a user