[diffusion] feat: support diffusers backend - run any model supported by diffusers (#14112)
This commit is contained in:
committed by
GitHub
parent
84d13c54bb
commit
7be1a8c70c
@@ -143,13 +143,98 @@ def _sanitize_for_logging(obj: Any, key_hint: str | None = None) -> Any:
|
||||
return "<unserializable>"
|
||||
|
||||
|
||||
class ExecutionMode(str, Enum):
|
||||
"""
|
||||
Enumeration for different pipeline modes.
|
||||
|
||||
Inherits from str to allow string comparison for backward compatibility.
|
||||
"""
|
||||
|
||||
INFERENCE = "inference"
|
||||
|
||||
@classmethod
|
||||
def from_string(cls, value: str) -> "ExecutionMode":
|
||||
"""Convert string to ExecutionMode enum."""
|
||||
try:
|
||||
return cls(value.lower())
|
||||
except ValueError:
|
||||
raise ValueError(
|
||||
f"Invalid mode: {value}. Must be one of: {', '.join([m.value for m in cls])}"
|
||||
) from None
|
||||
|
||||
@classmethod
|
||||
def choices(cls) -> list[str]:
|
||||
"""Get all available choices as strings for argparse."""
|
||||
return [mode.value for mode in cls]
|
||||
|
||||
|
||||
class WorkloadType(str, Enum):
|
||||
"""
|
||||
Enumeration for different workload types.
|
||||
|
||||
Inherits from str to allow string comparison for backward compatibility.
|
||||
"""
|
||||
|
||||
I2V = "i2v" # Image to Video
|
||||
T2V = "t2v" # Text to Video
|
||||
T2I = "t2i" # Text to Image
|
||||
I2I = "i2i" # Image to Image
|
||||
|
||||
@classmethod
|
||||
def from_string(cls, value: str) -> "WorkloadType":
|
||||
"""Convert string to WorkloadType enum."""
|
||||
try:
|
||||
return cls(value.lower())
|
||||
except ValueError:
|
||||
raise ValueError(
|
||||
f"Invalid workload type: {value}. Must be one of: {', '.join([m.value for m in cls])}"
|
||||
) from None
|
||||
|
||||
@classmethod
|
||||
def choices(cls) -> list[str]:
|
||||
"""Get all available choices as strings for argparse."""
|
||||
return [workload.value for workload in cls]
|
||||
|
||||
|
||||
class Backend(str, Enum):
|
||||
"""
|
||||
Enumeration for different model backends.
|
||||
- AUTO: Automatically select backend (prefer sglang native, fallback to diffusers)
|
||||
- SGLANG: Use sglang's native optimized implementation
|
||||
- DIFFUSERS: Use vanilla diffusers pipeline (supports all diffusers models)
|
||||
"""
|
||||
|
||||
AUTO = "auto"
|
||||
SGLANG = "sglang"
|
||||
DIFFUSERS = "diffusers"
|
||||
|
||||
@classmethod
|
||||
def from_string(cls, value: str) -> "Backend":
|
||||
"""Convert string to Backend enum."""
|
||||
try:
|
||||
return cls(value.lower())
|
||||
except ValueError:
|
||||
raise ValueError(
|
||||
f"Invalid backend: {value}. Must be one of: {', '.join([m.value for m in cls])}"
|
||||
) from None
|
||||
|
||||
@classmethod
|
||||
def choices(cls) -> list[str]:
|
||||
"""Get all available choices as strings for argparse."""
|
||||
return [backend.value for backend in cls]
|
||||
|
||||
|
||||
@dataclasses.dataclass
|
||||
class ServerArgs:
|
||||
# Model and path configuration (for convenience)
|
||||
model_path: str
|
||||
|
||||
# Model backend (sglang native or diffusers)
|
||||
backend: Backend = Backend.AUTO
|
||||
|
||||
# Attention
|
||||
attention_backend: str = None
|
||||
diffusers_attention_backend: str = None # for diffusers backend only
|
||||
|
||||
# Distributed executor backend
|
||||
nccl_port: Optional[int] = None
|
||||
@@ -355,6 +440,13 @@ class ServerArgs:
|
||||
choices=[e.name.lower() for e in AttentionBackendEnum] + ["fa3", "fa4"],
|
||||
help="The attention backend to use. If not specified, the backend is automatically selected based on hardware and installed packages.",
|
||||
)
|
||||
parser.add_argument(
|
||||
"--diffusers-attention-backend",
|
||||
type=str,
|
||||
default=None,
|
||||
help="Attention backend for diffusers pipelines (e.g., flash, _flash_3_hub, sage, xformers). "
|
||||
"See: https://huggingface.co/docs/diffusers/main/en/optimization/attention_backends",
|
||||
)
|
||||
|
||||
# HuggingFace specific parameters
|
||||
parser.add_argument(
|
||||
@@ -601,6 +693,14 @@ class ServerArgs:
|
||||
default=ServerArgs.log_level,
|
||||
help="The logging level of all loggers.",
|
||||
)
|
||||
parser.add_argument(
|
||||
"--backend",
|
||||
type=str,
|
||||
choices=Backend.choices(),
|
||||
default=ServerArgs.backend.value,
|
||||
help="The model backend to use. 'auto' prefers sglang native and falls back to diffusers. "
|
||||
"'sglang' uses native optimized implementation. 'diffusers' uses vanilla diffusers pipeline.",
|
||||
)
|
||||
return parser
|
||||
|
||||
def url(self):
|
||||
@@ -718,6 +818,16 @@ class ServerArgs:
|
||||
|
||||
@classmethod
|
||||
def from_kwargs(cls, **kwargs: Any) -> "ServerArgs":
|
||||
# Convert mode string to enum if necessary
|
||||
if "mode" in kwargs and isinstance(kwargs["mode"], str):
|
||||
kwargs["mode"] = ExecutionMode.from_string(kwargs["mode"])
|
||||
# Convert workload_type string to enum if necessary
|
||||
if "workload_type" in kwargs and isinstance(kwargs["workload_type"], str):
|
||||
kwargs["workload_type"] = WorkloadType.from_string(kwargs["workload_type"])
|
||||
# Convert backend string to enum if necessary
|
||||
if "backend" in kwargs and isinstance(kwargs["backend"], str):
|
||||
kwargs["backend"] = Backend.from_string(kwargs["backend"])
|
||||
|
||||
kwargs["pipeline_config"] = PipelineConfig.from_kwargs(kwargs)
|
||||
return cls(**kwargs)
|
||||
|
||||
|
||||
Reference in New Issue
Block a user