vllm-project/vllm · critical

server info value must serialize

Error message

server info value must serialize

What it means

A panic (expect) in ServerInfoSnapshot::from_config: serde_json::to_value(config) must succeed when serializing the frontend Config for the /server info endpoints. Config derives Serialize, so this failing means a Config field holds data serde_json cannot represent — an internal invariant break, not user error in the normal path.

Source

Thrown at rust/src/server/src/server_info.rs:32

pub(crate) enum ServerInfoConfigFormat {
    Text,
    Json,
}

/// Snapshot returned by `/server_info`.
#[derive(Debug, Clone)]
pub(crate) struct ServerInfoSnapshot {
    vllm_config_text: String,
    vllm_config_json: Value,
    vllm_env: BTreeMap<String, String>,
    system_env: BTreeMap<String, String>,
}

impl ServerInfoSnapshot {
    /// Capture the runtime configuration fields available to the Rust frontend.
    pub(crate) fn from_config(config: &Config) -> Self {
        let vllm_config_json =
            serde_json::to_value(config).expect("server info value must serialize");

        Self {
            vllm_config_text: render_config_text(&vllm_config_json),
            vllm_config_json,
            vllm_env: collect_vllm_env(),
            system_env: collect_system_env(),
        }
    }

    pub(crate) fn response(&self, config_format: ServerInfoConfigFormat) -> Value {
        let vllm_config = match config_format {
            ServerInfoConfigFormat::Text => Value::String(self.vllm_config_text.clone()),
            ServerInfoConfigFormat::Json => self.vllm_config_json.clone(),
        };

        json!({
            "vllm_config": vllm_config,
            "vllm_env": self.vllm_env.clone(),

View on GitHub (pinned to c794754062)

Solutions

  1. If running a patched build: audit recently added Config fields for types serde_json cannot serialize (non-string map keys without custom serde) and add #[serde(with = ...)] or convert keys to String.
  2. Check that the Serialize derive covers enum variants you added (no untagged variants with conflicting shapes).
  3. On stock builds, report the panic with the Config dump — it indicates a bug in the server.

Example fix

// before
pub struct Config { pub extra: HashMap<u32, String>, .. }  // serde_json: key must be a string

// after
pub struct Config {
    #[serde(with = "serde_json::map_tuple_keys")]
    pub extra: HashMap<u32, String>,
    ..
}
Defensive patterns

Strategy: try-catch

Validate before calling

// if you build custom Config types, prove serializability in a test:
#[test]
fn config_serializes() {
    let cfg = test_config();
    assert!(serde_json::to_value(&cfg).is_ok());
}

Try / catch

let snapshot = std::panic::catch_unwind(|| {
    ServerInfoSnapshot::from_config(&config)
});
// a panic here is an internal invariant break — capture it in a crash handler that logs the Config's Debug form.

Prevention

When it happens

Trigger: A Config field (possibly added by a new feature or non-default transport-mode variant) containing a value that cannot map to JSON — e.g. a map with non-string keys serialized without a helper, or untagged enum data that hits an unserializable state. Fires during snapshot construction at startup or on config reload.

Common situations: Building a custom/patched frontend that adds a Config field with a map key type serde_json rejects; version skew between config producer and serializer; essentially never seen on stock builds.

Related errors


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