vllm-project/vllm · error · ValueError

method='custom_class' requires 'model' to contain the custom

Error message

method='custom_class' requires 'model' to contain the custom proposer module path (e.g., 'my_module.MyProposer').

What it means

For method='custom_class', the draft proposer is user-supplied Python: the 'model' field must carry an importable 'module.ClassName' path. Unlike other methods there is nothing to auto-fill, so if model is None the config is rejected rather than silently loading nothing.

Source

Thrown at vllm/config/speculative.py:791

                # DeepSeek DSpark can ship the weights inside the target checkpoint
                if self.target_model_config is None:
                    raise ValueError("target_model_config must be present for dspark")
                self.model = self.target_model_config.model
                if not self.quantization:
                    self.quantization = self.target_model_config.quantization
            elif self.method in ("ngram", "[ngram]"):
                self.model = "ngram"
            elif self.method == "ngram_gpu":
                self.model = "ngram_gpu"
            elif self.method == "suffix":
                self.model = "suffix"
            elif self.method == "extract_hidden_states":
                self.model = "extract_hidden_states"
            elif self.method == "custom_class":
                # method was set explicitly, but model should already contain the
                # custom module path. If not, this is a configuration error.
                if self.model is None:
                    raise ValueError(
                        "method='custom_class' requires 'model' to contain the "
                        "custom proposer module path (e.g., 'my_module.MyProposer')."
                    )
            else:
                raise ValueError(
                    "num_speculative_tokens was provided but without speculative model."
                )

        if self.method in ("ngram", "[ngram]"):
            self.method = "ngram"

        if self.method in ("ngram", "ngram_gpu"):
            # Set default values if not provided
            if self.prompt_lookup_min is None and self.prompt_lookup_max is None:
                # TODO(woosuk): Tune these values. They are arbitrarily chosen.
                self.prompt_lookup_min = 5
                self.prompt_lookup_max = 5
            elif self.prompt_lookup_min is None:

View on GitHub (pinned to c794754062)

Solutions

  1. Set model to the dotted path of your proposer class, e.g. model='my_plugin.proposers.MyProposer'
  2. Ensure the module is importable in the vLLM process (installed or on PYTHONPATH)
  3. Verify the class is a registered/compatible speculative proposer before launch

Example fix

# before
SpeculativeConfig(method='custom_class', num_speculative_tokens=3)

# after
SpeculativeConfig(method='custom_class', num_speculative_tokens=3, model='my_plugin.proposers.MyProposer')
Defensive patterns

Strategy: validation

Validate before calling

import importlib

def proposer_path_ok(path: str | None) -> bool:
    if not isinstance(path, str) or '.' not in path:
        return False
    mod, cls = path.rsplit('.', 1)
    try:
        return hasattr(importlib.import_module(mod), cls)
    except ImportError:
        return False

Type guard

def is_custom_class_path(v: object) -> bool:
    return isinstance(v, str) and '.' in v and v.rsplit('.', 1)[1].isidentifier()

Try / catch

null

Prevention

When it happens

Trigger: SpeculativeConfig(method='custom_class', num_speculative_tokens=3) with no model; passing the class object in another field instead of the dotted path string; typo in the method name leaving model unset.

Common situations: Migrating from ngram/MTP configs and forgetting that custom_class has no default proposer; assuming model only names HF checkpoints.

Related errors


AI-assisted analysis of vllm-project/vllm@c794754062 (2026-08-14). Data as JSON: /api/errors/8e0448823eee8314. Report an issue: GitHub.