nautechsystems/nautilus_trader · error

Invalid mid price for Cache::price

Error message

Invalid mid price for Cache::price

What it means

Cache::price with PriceType::Mid computes mid = (ask + bid) / 2 from the latest QuoteTick and builds a Price at bid precision + 1. The expect panics when the resulting decimal cannot be converted to a Price — typically a negative, non-finite, or out-of-range mid value produced by malformed quote data.

Source

Thrown at crates/common/src/cache/mod.rs:7599

    /// the maximum fixed precision.
    #[must_use]
    pub fn price(&self, instrument_id: &InstrumentId, price_type: PriceType) -> Option<Price> {
        match price_type {
            PriceType::Bid => self
                .quotes
                .get(instrument_id)
                .and_then(|quotes| quotes.front().map(|quote| quote.bid_price)),
            PriceType::Ask => self
                .quotes
                .get(instrument_id)
                .and_then(|quotes| quotes.front().map(|quote| quote.ask_price)),
            PriceType::Mid => self.quotes.get(instrument_id).and_then(|quotes| {
                quotes.front().map(|quote| {
                    let mid = (quote.ask_price.as_decimal() + quote.bid_price.as_decimal())
                        / Decimal::TWO;

                    Price::from_decimal_dp(mid, quote.bid_price.precision + 1)
                        .expect("Invalid mid price for Cache::price")
                })
            }),
            PriceType::Last => self
                .trades
                .get(instrument_id)
                .and_then(|trades| trades.front().map(|trade| trade.price)),
            PriceType::Mark => self
                .mark_prices
                .get(instrument_id)
                .and_then(|marks| marks.front().map(|mark| mark.value)),
        }
    }

    /// Gets all quotes for the `instrument_id`.
    #[must_use]
    pub fn quotes(&self, instrument_id: &InstrumentId) -> Option<Vec<QuoteTick>> {
        self.quotes
            .get(instrument_id)

View on GitHub (pinned to 18893faf8b)

Solutions

  1. Validate the latest QuoteTick (positive, finite ask/bid) before requesting the mid price
  2. Use Cache::try-style access or fetch the quote yourself and compute the mid with error handling
  3. Purge or repair corrupt quotes from the cache for that instrument_id
  4. Check the data source/adapter producing malformed quotes

Example fix

// before
let mid = cache.price(&instrument_id, PriceType::Mid).unwrap();
// after
if let Some(quote) = cache.quote_tick(&instrument_id) {
    if quote.bid_price.as_f64() > 0.0 && quote.ask_price.as_f64() > 0.0 {
        let mid = cache.price(&instrument_id, PriceType::Mid).unwrap();
    }
}
Defensive patterns

Strategy: type-guard

Validate before calling

fn has_valid_quote(cache: &Cache, id: &InstrumentId) -> bool {
    cache.quotes.get(id)
        .and_then(|q| q.front())
        .map(|q| q.bid_price.as_f64() > 0.0 && q.ask_price.as_f64() > 0.0
              && q.ask_price >= q.bid_price)
        .unwrap_or(false)
}

Type guard

fn valid_quote(q: &QuoteTick) -> bool {
    q.bid_price.as_f64() > 0.0 && q.ask_price.as_f64() > 0.0
}

Try / catch

// Cannot catch the panic; guard the input quote instead
if has_valid_quote(&cache, &instrument_id) {
    let mid = cache.price(&instrument_id, PriceType::Mid).unwrap();
} else {
    eprintln!("no valid quote for {instrument_id}; skip mid price");
}

Prevention

When it happens

Trigger: Calling cache.price(instrument_id, PriceType::Mid) when the top-of-book QuoteTick has invalid prices (e.g. ask or bid missing/zero/corrupt) such that the computed mid cannot form a valid Price.

Common situations: Feed handlers publishing placeholder quotes (0/0) during market close or before open; stale or corrupt quote data in the cache; instruments whose precision handling differs from expected.

Understand the failure class

Background: "Must be a positive integer", "Invalid value", "Unsupported": the invalid-argument-value error family, when a library rejects the value you pass — this error's family across 35 libraries.

Related errors


AI-assisted analysis of nautechsystems/nautilus_trader@18893faf8b (2026-09-08). Data as JSON: /api/errors/8b451b09f1e241b4. Report an issue: GitHub.