{"record":{"id":"5bad8b535a690fa8","repo":"nautechsystems/nautilus_trader","slug":"failed-to-load-currency-e","errorCode":null,"errorMessage":"Failed to load currency: {e}","messagePattern":"Failed to load currency: (.+?)","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"crates/infrastructure/src/sql/queries.rs","lineNumber":142,"sourceCode":"        sqlx::query_as::<_, CurrencyRow>(\"SELECT * FROM currency ORDER BY id ASC\")\n            .fetch_all(pool)\n            .await\n            .map(|rows| rows.into_iter().map(|row| row.0).collect())\n            .map_err(|e| anyhow::anyhow!(\"Failed to load currencies: {e}\"))\n    }\n\n    /// Loads a single `Currency` entry by `code` via the provided `pool`.\n    ///\n    /// # Errors\n    ///\n    /// Returns an error if the SELECT operation fails.\n    pub async fn load_currency(pool: &PgPool, code: &str) -> anyhow::Result<Option<Currency>> {\n        sqlx::query_as::<_, CurrencyRow>(\"SELECT * FROM currency WHERE id = $1\")\n            .bind(code)\n            .fetch_optional(pool)\n            .await\n            .map(|currency| currency.map(|row| row.0))\n            .map_err(|e| anyhow::anyhow!(\"Failed to load currency: {e}\"))\n    }\n\n    /// Inserts or updates an `InstrumentAny` entry via the provided `pool`.\n    ///\n    /// # Errors\n    ///\n    /// Returns an error if the INSERT or UPDATE operation fails.\n    pub async fn add_instrument(\n        pool: &PgPool,\n        kind: &str,\n        instrument: Box<dyn Instrument>,\n    ) -> anyhow::Result<()> {\n        sqlx::query(r#\"\n            INSERT INTO \"instrument\" (\n                id, kind, raw_symbol, base_currency, underlying, quote_currency, settlement_currency, isin, asset_class, exchange,\n                strategy_type, multiplier, option_kind, is_inverse, strike_price, activation_ns, expiration_ns, price_precision, size_precision,\n                price_increment, size_increment, maker_fee, taker_fee, margin_init, margin_maint, lot_size, max_quantity, min_quantity, max_notional,\n                min_notional, max_price, min_price, ts_init, ts_event, created_at, updated_at","sourceCodeStart":124,"sourceCodeEnd":160,"githubUrl":"https://github.com/nautechsystems/nautilus_trader/blob/18893faf8b356be3320add8de2f861b0b647cf06/crates/infrastructure/src/sql/queries.rs#L124-L160","documentation":"`DatabaseQueries::load_currency` runs `SELECT * FROM currency WHERE id = $1` and returns Ok(None) when no row matches — a missing currency is not an error. This anyhow error is raised only on execution or row-decoding failure: connection loss, missing table (migrations not applied), or a stored row that can't decode into CurrencyRow.","triggerScenarios":"Calling `DatabaseQueries::load_currency(pool, code)` when the connection fails, the `currency` table doesn't exist, or the row's `currency_type` (or other column) can't decode — e.g. an enum value written by a different version.","commonSituations":"Fresh database without migrations; version skew between the process that wrote the currency row and the reader; transient connection loss during a lookup.","solutions":["Run migrations so the `currency` table exists with matching enum types.","If the inner error is a decode failure, align versions or re-write the offending row with the current binary.","Verify pool connectivity and privileges.","Handle the Option<Currency> None case separately — absent rows are not this error."],"exampleFix":null,"handlingStrategy":"try-catch","validationCode":"let exists: bool = sqlx::query_scalar(\n    \"SELECT EXISTS (SELECT 1 FROM information_schema.tables WHERE table_name = 'currency')\",\n).fetch_one(pool).await?;\nif !exists {\n    return Err(anyhow::anyhow!(\"'currency' table missing — run migrations\"));\n}","typeGuard":null,"tryCatchPattern":"match DatabaseQueries::load_currency(&pool, code).await {\n    Ok(None) => {\n        tracing::debug!(\"currency {code} not cached\");\n    }\n    Err(e) if e.to_string().contains(\"relation \\\"currency\\\" does not exist\") => {\n        return Err(anyhow::anyhow!(\"cache schema missing — run migrations: {e}\"));\n    }\n    result => result?,\n}","preventionTips":["Run migrations before querying the cache database.","Remember a missing row returns Ok(None) — reserve error handling for real query/decode failures.","Keep versions aligned so stored rows always decode with the reading binary.","Check pool connectivity on startup to catch transient failures early."],"tags":["postgres","sqlx","database","select","currency"],"backgroundTag":"database-query-failed","analyzedSha":"18893faf8b356be3320add8de2f861b0b647cf06","analyzedAt":"2026-09-08T20:49:34.690Z","contentChangedAt":"2026-09-08T20:49:34.690Z","schemaVersion":2},"datasetVersion":"2026-09-14T05:17:10.506Z"}