fix(samplers): report validation failures without backtrace

Sampler capability gates raised plain ValueError when schedulers_fallback is
disabled, so the API middleware and the gradio call wrapper printed a full
backtrace for an expected outcome. Add errors.ValidationError, raise it from
the gates, and report it message-only in errors.display; the UI error box and
the API error response already carry the message.
This commit is contained in:
CalamitousFelicitousness
2026-06-10 01:27:38 +01:00
parent e783981f3d
commit 47aa9a2c93
3 changed files with 16 additions and 9 deletions
+7
View File
@@ -10,6 +10,10 @@ install_traceback()
already_displayed = {}
class ValidationError(ValueError):
"""Expected validation failure: display() reports the message without a traceback."""
def install(suppress=None):
if suppress is None:
suppress = []
@@ -23,6 +27,9 @@ def display(e: Exception, task: str, suppress=None):
suppress = []
if isinstance(e, ErrorLimiterAbort):
return
if isinstance(e, ValidationError):
log.error(f"{task or 'error'}: {e}")
return
log.error(f"{task or 'error'}: {type(e).__name__}")
"""
trace = traceback.format_exc()
+4 -4
View File
@@ -1,6 +1,6 @@
import os
import copy
from modules import shared
from modules import shared, errors
from modules.logger import log
@@ -108,7 +108,7 @@ def create_sampler(name, model, scheduler_overrides=None):
if config is None or config.constructor is None:
if debug or not shared.opts.schedulers_fallback:
raise ValueError(f'Sampler: name="{name}" unknown')
raise errors.ValidationError(f'Sampler: name="{name}" unknown')
return restore_default(model, name)
from modules import sd_samplers_diffusers
@@ -129,13 +129,13 @@ def create_sampler(name, model, scheduler_overrides=None):
elif (model is not None) and (is_flow and not requires_flow):
log.error(f'Sampler: "{sampler.name}" cls={sampler.sampler.__class__.__name__} pipe={model.__class__.__name__} type={pred_type} model requires sampler with discrete prediction')
if debug or not shared.opts.schedulers_fallback:
raise ValueError(f'Sampler: name="{sampler.name}" cls={sampler.sampler.__class__.__name__} type={pred_type} model requires sampler with discrete prediction')
raise errors.ValidationError(f'Sampler: name="{sampler.name}" cls={sampler.sampler.__class__.__name__} type={pred_type} model requires sampler with discrete prediction')
else:
return restore_default(model, name)
elif (model is not None) and (not is_flow and requires_flow):
log.error(f'Sampler: "{sampler.name}" cls={sampler.sampler.__class__.__name__} pipe={model.__class__.__name__} type={pred_type} model requires sampler with flow prediction')
if debug or not shared.opts.schedulers_fallback:
raise ValueError(f'Sampler: name="{sampler.name}" cls={sampler.sampler.__class__.__name__} type={pred_type} model requires sampler with flow prediction')
raise errors.ValidationError(f'Sampler: name="{sampler.name}" cls={sampler.sampler.__class__.__name__} type={pred_type} model requires sampler with flow prediction')
else:
return restore_default(model, name)
+5 -5
View File
@@ -450,7 +450,7 @@ class DiffusionSampler:
sigma_applied = True
if not sigma_applied:
if debug or not shared.opts.schedulers_fallback:
raise ValueError(f'Sampler: name="{name}" does not support sigma="{sched_sigma}"')
raise errors.ValidationError(f'Sampler: name="{name}" does not support sigma="{sched_sigma}"')
else:
log.warning(f'Sampler: name="{name}" does not support sigma="{sched_sigma}", using default schedule')
else:
@@ -520,7 +520,7 @@ class DiffusionSampler:
if debug:
errors.display(e, 'Samplers')
if debug or not shared.opts.schedulers_fallback:
raise
raise errors.ValidationError(f'Sampler: name="{name}" {e}') from e
self.sampler = None
return
@@ -529,7 +529,7 @@ class DiffusionSampler:
cls_source = inspect.getsource(constructor)
if '"flow_prediction"' not in cls_source and "'flow_prediction'" not in cls_source:
if debug or not shared.opts.schedulers_fallback:
raise ValueError(f'Sampler: name="{name}" does not appear to support flow_prediction')
raise errors.ValidationError(f'Sampler: name="{name}" does not appear to support flow_prediction')
else:
log.warning(f'Sampler: name="{name}" does not support flow_prediction')
self.sampler = None
@@ -549,7 +549,7 @@ class DiffusionSampler:
default_accept_sigmas = (model is not None) and hasattr(model.default_scheduler, 'set_timesteps') and "sigmas" in set(inspect.signature(model.default_scheduler.set_timesteps).parameters.keys())
if default_accept_sigmas and not accept_sigmas:
if debug or not shared.opts.schedulers_fallback:
raise ValueError(f'Sampler: name="{name}" does not accept sigmas')
raise errors.ValidationError(f'Sampler: name="{name}" does not accept sigmas')
else:
log.warning(f'Sampler: name="{name}" does not accept sigmas')
self.sampler = None
@@ -559,7 +559,7 @@ class DiffusionSampler:
if default_accept_scale_noise and not accept_scale_noise:
log.warning(f'Sampler: name="{name}" does not implement scale noise')
if debug or not shared.opts.schedulers_fallback:
raise ValueError(f'Sampler: name="{name}" does not implement scale noise')
raise errors.ValidationError(f'Sampler: name="{name}" does not implement scale noise')
else:
log.warning(f'Sampler: name="{name}" does not implement scale noise')
self.sampler = None