nautechsystems/nautilus_trader · error

InstrumentId symbol is empty

Error message

InstrumentId symbol is empty

What it means

When converting an InstrumentId to a Bybit symbol, the adapter checks that the symbol component is non-empty. An InstrumentId with an empty symbol cannot map to a venue symbol, so the request is aborted.

Source

Thrown at crates/adapters/bybit/src/http/client.rs:4725

                    );
                };
                return self
                    .generate_spot_position_reports_from_wallet(account_id, instrument_id)
                    .await;
            } else {
                // Return empty vector when SPOT position reports are disabled
                return Ok(Vec::new());
            }
        }

        let ts_init = self.generate_ts_init();
        let mut reports = Vec::new();

        // Build query parameters based on whether a specific instrument is requested
        let symbol = if let Some(id) = instrument_id {
            let symbol_str = id.symbol.as_str();
            if symbol_str.is_empty() {
                anyhow::bail!("InstrumentId symbol is empty");
            }
            let bybit_symbol = BybitSymbol::new(symbol_str)?;
            Some(bybit_symbol.raw_symbol().to_string())
        } else {
            None
        };

        // For LINEAR category, the API requires either symbol OR settleCoin
        // When querying all positions (no symbol), we must iterate through settle coins
        if product_type == BybitProductType::Linear && symbol.is_none() {
            // Query positions for each known settle coin with pagination
            for settle_coin in ["USDT", "USDC"] {
                let mut cursor: Option<String> = None;

                loop {
                    let params = BybitPositionListParams {
                        category: product_type,
                        symbol: None,

View on GitHub (pinned to 18893faf8b)

Solutions

  1. Validate the symbol is non-empty before constructing the InstrumentId
  2. Trim and normalize venue symbols when building InstrumentIds
  3. Pass None instead of an empty-symbol InstrumentId when no specific instrument is intended

Example fix

// before
let id = InstrumentId::from(format!("@{}", venue).as_str()); // empty symbol
// after
anyhow::ensure!(!symbol.is_empty(), "symbol required");
let id = InstrumentId::from(format!("{symbol}@{venue").as_str());
Defensive patterns

Strategy: validation

Validate before calling

anyhow::ensure!(!instrument_id.symbol.as_str().is_empty(), "instrument symbol must be non-empty");
let bybit_symbol = BybitSymbol::new(instrument_id.symbol.as_str())?;

Type guard

fn has_symbol(id: &InstrumentId) -> bool { !id.symbol.as_str().is_empty() }

Prevention

When it happens

Trigger: Passing an InstrumentId whose symbol part is an empty string (e.g. parsed from "@BYBIT.SPOT"-style or malformed input) into an instruments/positions query that expects Some(instrument_id).

Common situations: Programmatically constructed InstrumentIds where the symbol was built from an empty or untrimmed string; parsing venue metadata that returned blank symbols.

Understand the failure class

Background: "must not be empty", "cannot be empty" — required-field validation errors across open-source libraries — this error's family across 41 libraries.

Related errors


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