sgl-project/sglang · error · ValueError
invalid Rust extension build mode {mode!r}; expected auto, n
Error message
invalid Rust extension build mode {mode!r}; expected auto, never, or force What it means
load_rust_extension(mode=...) only accepts 'auto', 'never', or 'force'. Any other mode string raises this ValueError; when mode is None the value comes from the SGLANG_RUST_BUILD_MODE env var. 'auto' uses bundled or cached builds, 'never' forbids invoking Cargo, 'force' rebuilds from source and replaces the cache entry.
Source
Thrown at python/sglang/srt/rust_extensions/loader.py:88
cache_dir: Path | None = None,
workspace: Path | None = None,
) -> ModuleType:
"""Import a PyO3 extension, compiling it locally when permitted and needed.
The crate is discovered from the workspace under ``rust/``: the one whose
Cargo manifest declares ``[package.metadata.sglang] python-module`` equal
to ``python_module`` (the same metadata setup.py uses for wheel builds), so
new crates need no registration here.
``auto`` prefers a module bundled in the installed wheel, then a cached
local build, and finally Cargo. ``never`` permits the first two but never
invokes Cargo. ``force`` rebuilds from source and replaces the cache entry.
``mode`` defaults to ``SGLANG_RUST_BUILD_MODE``.
"""
if mode is None:
mode = envs.SGLANG_RUST_BUILD_MODE.get()
if mode not in ("auto", "never", "force"):
raise ValueError(
f"invalid Rust extension build mode {mode!r}; expected auto, never, or force"
)
if mode != "force":
module = _import_bundled_extension(python_module)
if module is not None:
return module
elif python_module in sys.modules:
raise RuntimeError(
f"cannot force-build {python_module} after it has been imported; "
"start a new Python process"
)
if workspace is None:
workspace = _RUST_WORKSPACE
crate = _discover_crate(workspace, python_module)
context = _build_context(crate)
cache_root = _cache_root(cache_dir)View on GitHub (pinned to 0132848349)
Solutions
- Set mode (or SGLANG_RUST_BUILD_MODE) to exactly auto, never, or force
- If you wanted rebuild-on-every-call semantics, that is 'force'
- Unset the env var to fall back to the default behavior instead of an invalid literal
Example fix
# before SGLANG_RUST_BUILD_MODE=always python -m ... # after SGLANG_RUST_BUILD_MODE=force python -m ...
Defensive patterns
Strategy: validation
Validate before calling
assert mode in {"auto", "never", "force"}, f"bad build mode {mode!r}" Type guard
def is_valid_build_mode(mode: str) -> bool:
return mode in {"auto", "never", "force"} Prevention
- Use an enum or constant set for build-mode values instead of free-form strings
- Validate SGLANG_RUST_BUILD_MODE at app startup, not at first extension load
When it happens
Trigger: Passing mode="always", "True", or "" to load_rust_extension; setting SGLANG_RUST_BUILD_MODE to anything other than auto/never/force and calling the loader without an explicit mode.
Common situations: Copy-pasting build-mode values from other tools (e.g. 'always' instead of 'force'); typos in CI env vars; docs or examples referencing a removed mode name.
Related errors
- {crate.python_module} is not bundled or cached, and Rust ext
- v_cache must be provided
- q can only be None when only_qv=True
- q must be provided unless qv is provided with only_qv=True
- name must be provided
AI-assisted analysis of sgl-project/sglang@0132848349 (2026-08-28).
Data as JSON: /api/errors/b759d904b88269bc.
Report an issue: GitHub.