nautechsystems/nautilus_trader · error
invalid Derive `expired` filter: {e}
Error message
invalid Derive `expired` filter: {e} What it means
The `expired` load filter for DeriveInstrumentProvider must parse as a Rust bool (true/false). resolve_expired_filter parses the filter string and wraps any parse failure in this error. Lowercase `true`/`false` are valid; other spellings are not.
Source
Thrown at crates/adapters/derive/src/providers.rs:306
anyhow::ensure!(
!currencies.is_empty(),
"DeriveInstrumentProvider requires at least one currency",
);
let expired = resolve_expired_filter(default_expired, filters)?;
Ok((currencies, expired))
}
fn resolve_expired_filter(
default_expired: bool,
filters: Option<&HashMap<String, String>>,
) -> anyhow::Result<bool> {
filters
.and_then(|map| map.get("expired"))
.map(|value| value.parse::<bool>())
.transpose()
.map_err(|e| anyhow::anyhow!("invalid Derive `expired` filter: {e}"))
.map(|value| value.unwrap_or(default_expired))
}
fn split_currencies(value: &str) -> Vec<String> {
normalize_currencies(value.split(',').map(ToOwned::to_owned).collect())
}
fn normalize_currencies(currencies: Vec<String>) -> Vec<String> {
let mut currencies: Vec<_> = currencies
.into_iter()
.map(|currency| currency.trim().to_string())
.filter(|currency| !currency.is_empty())
.collect();
currencies.sort();
currencies.dedup();
currencies
}
View on GitHub (pinned to 18893faf8b)
Solutions
- Use exactly "true" or "false" (lowercase) for the expired filter
- Normalize the filter value with .to_lowercase() before passing it
- Convert numeric/bool config values to canonical bool strings at config load time
Example fix
// before
filters.insert("expired".into(), "True".into());
// after
filters.insert("expired".into(), "true".into()); Defensive patterns
Strategy: validation
Validate before calling
let expired = value.to_lowercase();
assert!(expired == "true" || expired == "false", "expired filter must be 'true' or 'false', got {value}"); Type guard
fn parse_expired(v: &str) -> Option<bool> { match v.to_lowercase().as_str() { "true" => Some(true), "false" => Some(false), _ => None } } Try / catch
match provider.load_ids(Some(&filters)).await { Err(e) if e.to_string().contains("invalid Derive `expired` filter") => fix_and_retry(filters), r => r } Prevention
- Normalize boolean filter strings to lowercase before passing to adapters
- Avoid 0/1 or Python-style True/False in string filter maps
- Centralize filter construction in a typed helper that produces canonical bool strings
When it happens
Trigger: Passing filters like {"expired": "True"}, {"expired": "1"}, or {"expired": "yes"} to load_ids/load_all — str::parse::<bool>() only accepts "true" or "false".
Common situations: Using Python-style booleans (`True`) in a string filter map; numeric flags from config files; copy-pasted filter values from other adapters that accept 0/1.
Understand the failure class
Background: "Invalid ... format", "must be in format X", "does not look like a ..." — invalid argument format errors across CLI tools and libraries — this error's family across 17 libraries.
Related errors
- Unknown position currency '{pos_ccy}' for instrument {instru
- Invalid timeframe for `BarSpecification`, was {timeframe}
- Gamma {scope} filter '{key}' must be true or false, was '{va
- Gamma {scope} filter '{key}' must contain non-empty comma-se
- Gamma {scope} filter '{key}' cannot be empty
AI-assisted analysis of nautechsystems/nautilus_trader@18893faf8b (2026-09-08).
Data as JSON: /api/errors/e52be84ba590f7e5.
Report an issue: GitHub.