quickwit-oss/quickwit · error

failed to convert value

Error message

failed to convert value `{env_var_value}` read from environment variable `{env_var_key}` to type `{}`: {error:?}

What it means

quickwit-config resolves configuration values from environment variables. `resolve_optional` parses the raw string of an env var into the target type T; if `str::parse` fails, this error is thrown, reporting the value, variable name, target type, and the parse error.

Solutions

  1. Inspect the env var named in the message and print its raw value (`printenv {env_var_key}`), then set it to a value valid for the type shown (u64/u32, ByteSize like `20MB`, duration like `30s`, bool like `true`).
  2. Watch for stray whitespace, BOM, or quotes: `export QW_X=$(tr -d '"\'' <<< "$QW_X")` or re-export the value cleanly.
  3. If the value was intended as a literal default and not an override, unset the env var (`unset {env_var_key}`) so the config file/default is used.
  4. Check docs for the expected format of that setting — unit suffixes (MB, MiB, s, ms) are required for size/duration types.

Example fix

// before
export QW_SEARCHER_FAST_FIELD_CACHE_CAPACITY="1 GB"
// after (ByteSize accepts compact form, no space)
export QW_SEARCHER_FAST_FIELD_CACHE_CAPACITY="1GB"
Defensive patterns

Strategy: validation

Validate before calling

function validateEnvVar(key, type) {
  const raw = process.env[key];
  if (raw === undefined) return true;
  switch (type) {
    case 'u64': case 'usize': {
      const n = Number(raw);
      return Number.isInteger(n) && n >= 0;
    }
    case 'bool': return raw === 'true' || raw === 'false';
    case 'bytesize': return /^\d+(B|KB|MB|GB|TB|KiB|MiB|GiB)$/i.test(raw);
    case 'duration': return /^\d+(ms|s|m|h|d)$/.test(raw);
    default: return raw.length > 0;
  }
}
// validateEnvVar('QW_GRPC_MAX_MESSAGE_SIZE', 'bytesize')

Type guard

const isPositiveInt = (s) => /^\d+$/.test(s.trim());

Prevention

When it happens

Trigger: Setting an environment variable that a config value resolves from (via qw env-var interpolation of QW_ prefixed variables) with a value that cannot parse into the declared Rust type, e.g. QW_LISTENER_HTTP_PORT="http" for a u16, or QW_GRPC_MAX_MESSAGE_SIZE="twenty-megabytes" for a ByteSize.

Common situations: Typos or whitespace in env var values; passing human-friendly strings where numbers/durations/sizes are expected; shell exporting quoted values that include quotes; wrong variable name mapping to the wrong type; changed unit formats across Quickwit versions.

Understand the failure class

Background: "is not a valid" / "Invalid ... value" environment variable errors: how libraries validate env vars and what to do when they reject yours — this error's family across 48 libraries.

Related errors


AI-assisted analysis of quickwit-oss/quickwit@a39730c5cd (2026-09-08). Data as JSON: /api/errors/2db230579a9f12c8. Report an issue: GitHub.

Appendix: source

Thrown at quickwit/quickwit-config/src/config_value.rs:85

        env_vars: &HashMap<String, String>,
    ) -> anyhow::Result<Option<T>> {
        // QW env vars take precedence over the config file values.
        if E > QW_NONE
            && let Some(env_var_key) = QW_ENV_VARS.get(&E)
            && let Some(env_var_value) = env_vars.get(*env_var_key).filter(|val| {
                if val.is_empty() {
                    warn!(
                        "environment variable `{}` is set but value is empty",
                        *env_var_key
                    );
                    false
                } else {
                    true
                }
            })
        {
            let value = env_var_value.parse::<T>().map_err(|error| {
                anyhow::anyhow!(
                    "failed to convert value `{env_var_value}` read from environment variable \
                     `{env_var_key}` to type `{}`: {error:?}",
                    any::type_name::<T>(),
                )
            })?;
            return Ok(Some(value));
        }
        Ok(self.provided.or(self.default))
    }

    pub(crate) fn resolve(self, env_vars: &HashMap<String, String>) -> anyhow::Result<T> {
        self.resolve_optional(env_vars)?.context(
            "failed to resolve field value: no value was provided via environment variable or \
             config file, and the field has no default",
        )
    }
}

View on GitHub (pinned to a39730c5cd)