nautechsystems/nautilus_trader · error
Invalid data element not `QuoteTick`, was {data:?}
Error message
Invalid data element not `QuoteTick`, was {data:?} What it means
Inside `get_range_quotes`, each decoded record is mapped to `Data::Quote(quote)` or `None` (undefined bid/ask, skipped). Any other `Data` variant means the schema produced a record type that is not a quote tick, which is an invariant violation for this method, so it errors with the debug representation of the offending element.
Source
Thrown at crates/adapters/databento/src/historical.rs:427
let price_precision = self.resolve_cached_price_precision(
&instrument_id,
price_precision_arg,
&mut precision_cache,
)?;
let (data, _) = decode_record(
&record,
instrument_id,
price_precision,
None,
false, // Don't include trades
true,
)?;
match data {
Some(Data::Quote(quote)) => result.push(quote),
None => {} // Skip records with undefined bid/ask prices
_ => anyhow::bail!("Invalid data element not `QuoteTick`, was {data:?}"),
}
Ok(())
};
match dbn_schema {
dbn::Schema::Mbp1 => {
while let Some(msg) = decoder.decode_record::<dbn::Mbp1Msg>().await? {
process_record(dbn::RecordRef::from(msg))?;
}
}
dbn::Schema::Tbbo => {
while let Some(msg) = decoder.decode_record::<dbn::TbboMsg>().await? {
process_record(dbn::RecordRef::from(msg))?;
}
}
dbn::Schema::Cmbp1 => {
while let Some(msg) = decoder.decode_record::<dbn::Cmbp1Msg>().await? {
process_record(dbn::RecordRef::from(msg))?;View on GitHub (pinned to 18893faf8b)
Solutions
- Check the printed `data:?` variant to see which record type leaked in; adjust the requested schema to one that yields only quotes.
- If the schema legitimately emits non-quote records, handle that variant explicitly instead of erroring.
- Upgrade/patch the adapter if this is a decode mismatch bug between schema handling and `Data` conversion.
- Filter records client-side: if you control record iteration, skip known non-quote record types before conversion.
Example fix
// before
_ => anyhow::bail!("Invalid data element not `QuoteTick`, was {data:?}"),
// after
_ => { log::debug!("skipping non-quote element {data:?}"); Ok(()) } Defensive patterns
Strategy: try-catch
Type guard
fn is_quote(data: &Data) -> Option<&QuoteTick> { match data { Data::Quote(q) => Some(q), _ => None } } Try / catch
match get_range_quotes(params).await {
Ok(quotes) => quotes,
Err(e) if e.to_string().contains("Invalid data element not `QuoteTick`") => {
log::error!("non-quote record leaked: {e}"); Vec::new()
}
Err(e) => return Err(e),
} Prevention
- Keep the requested schema restricted to pure quote-producing schemas.
- Check the debug output in the message to identify which Data variant leaked.
- Report persistent occurrences as an adapter bug.
When it happens
Trigger: A record from a quote-capable schema decodes into a non-quote `Data` variant — e.g. cmbp-1/tcbbo streams yielding trade-implied records that map to a non-Quote variant, or an internal decode mismatch between the schema allow-list and `process_record`'s conversion.
Common situations: Mixed/multi-asset responses where some records are not quotes; adapter bug after a schema allow-list change; feeding cbbo/cmbp schemas whose records decode to trade ticks under certain conditions.
Related errors
- Missing required price for `{field_name}`
- Invalid negative quantity: {value}
- Missing required timestamp for `{field_name}`
- Invalid negative multiplier: {v}
- Failed to decode instrument {instrument_id}: {e}
AI-assisted analysis of nautechsystems/nautilus_trader@18893faf8b (2026-09-08).
Data as JSON: /api/errors/3bc285a9087f1efd.
Report an issue: GitHub.