nautechsystems/nautilus_trader · error
No usable instruments for {instrument_type:?} family {family
Error message
No usable instruments for {instrument_type:?} family {family}, cannot initialize execution client What it means
Same as the per-type instrument check, but for a specific option family: `establish_session` requests instruments for `{instrument_type} family {family}` (e.g. OPTION for a specific underlying/expiry family) and bails when the response is empty. Without instruments in that family the execution client cannot initialize.
Source
Thrown at crates/adapters/okx/src/execution.rs:1376
);
self.http_client.cache_instruments(&instruments);
all_instruments.extend(instruments);
all_inst_id_codes.extend(inst_id_codes);
} else {
for family in &families {
let (instruments, inst_id_codes) = self
.http_client
.request_instruments(*instrument_type, Some(family.clone()))
.await
.with_context(|| {
format!(
"failed to request OKX instruments for {instrument_type:?} family {family}"
)
})?;
if instruments.is_empty() {
anyhow::bail!(
"No usable instruments for {instrument_type:?} family {family}, \
cannot initialize execution client"
);
}
log::debug!(
"Loaded {} {instrument_type:?} instruments for family {family}",
instruments.len()
);
self.http_client.cache_instruments(&instruments);
all_instruments.extend(instruments);
all_inst_id_codes.extend(inst_id_codes);
}
}
}
if all_instruments.is_empty() {View on GitHub (pinned to 18893faf8b)
Solutions
- Verify the family/underlying identifier format against OKX (check the exact instId family on the OKX instruments endpoint).
- Remove families with no active listings from the config or switch to a live underlying.
- Confirm the family exists via `/api/v5/public/instruments?instType=OPTION&uly=...` before configuring it.
- Check OKX announcements for delistings affecting the configured family.
Example fix
// before option_families = ["BTC-USD-20260931"] // nonexistent expiry -> empty // after option_families = ["BTC-USD"] // valid underlying family with active listings
Defensive patterns
Strategy: validation
Validate before calling
// confirm the option family exists before configuring
let url = format!("https://www.okx.com/api/v5/public/instruments?instType=OPTION&uly={family}");
let resp = reqwest::get(&url).await?.json::<serde_json::Value>().await?;
if resp["data"].as_array().map_or(true, |a| a.is_empty()) {
return Err(anyhow::anyhow!("family {family} has no OKX option instruments"));
} Prevention
- Validate family/underlying strings against OKX's exact format (e.g. BTC-USD).
- Remove delisted/expired families from config; monitor OKX delist announcements.
- Keep family config in sync with live OKX listings via periodic checks.
When it happens
Trigger: `connect` -> `establish_session` iterates configured option families and the family-scoped instruments request returns an empty list — e.g. a family/underlying string that does not match any OKX listing, a delisted underlying, or a typo in the family config.
Common situations: Typo in underlying (e.g. `BTC-USDT` vs `BTC-USD` family format); requesting an expired/delisted option family; region-restricted products returning empty results.
Understand the failure class
Background: EmptyResultError / "no results found": when an API or scraper succeeds but returns zero rows — this error's family across 9 libraries.
Related errors
- No usable instruments for {instrument_type:?}, cannot initia
- No instruments loaded for configured types {instrument_types
- option instruments require instrument_family (OKX instFamily
- instrument update lock poisoned
- option_summary_family_subs mutex poisoned
AI-assisted analysis of nautechsystems/nautilus_trader@18893faf8b (2026-09-08).
Data as JSON: /api/errors/91f058fc1dcb2fbf.
Report an issue: GitHub.