nautechsystems/nautilus_trader · error

load_strategy not implemented for PostgreSQL cache adapter:

Error message

load_strategy not implemented for PostgreSQL cache adapter: {strategy_id}

What it means

Unimplemented trait method in the PostgreSQL cache adapter: strategy state loading is not implemented, so load_strategy always bails with the requested strategy_id (rather than panicking via todo!()).

Source

Thrown at crates/infrastructure/src/sql/cache.rs:883

        tokio::spawn(async move {
            let result = DatabaseQueries::load_position(&pool, &position_id).await;
            if let Err(e) = tx.send(result) {
                log::error!("Failed to send position {position_id}: {e:?}");
            }
        });
        rx.recv()?
    }

    fn load_actor(&self, actor_id: &ActorId) -> anyhow::Result<AHashMap<String, Bytes>> {
        anyhow::bail!("load_actor not implemented for PostgreSQL cache adapter: {actor_id}")
    }

    fn delete_actor(&self, _actor_id: &ActorId) -> anyhow::Result<()> {
        todo!()
    }

    fn load_strategy(&self, strategy_id: &StrategyId) -> anyhow::Result<AHashMap<String, Bytes>> {
        anyhow::bail!("load_strategy not implemented for PostgreSQL cache adapter: {strategy_id}")
    }

    fn delete_strategy(&self, _strategy_id: &StrategyId) -> anyhow::Result<()> {
        todo!()
    }

    fn delete_order(&self, client_order_id: &ClientOrderId) -> anyhow::Result<()> {
        anyhow::bail!(
            "delete_order not implemented for PostgreSQL cache adapter: {client_order_id}"
        )
    }

    fn delete_position(&self, position_id: &PositionId) -> anyhow::Result<()> {
        anyhow::bail!("delete_position not implemented for PostgreSQL cache adapter: {position_id}")
    }

    fn delete_account_event(&self, account_id: &AccountId, event_id: &str) -> anyhow::Result<()> {
        anyhow::bail!(

View on GitHub (pinned to 18893faf8b)

Solutions

  1. Use the Redis cache adapter for strategy state persistence
  2. Disable strategy load_state when using the PostgreSQL adapter
  3. Implement load_strategy in sql/cache.rs (persist strategy state like other string-blob entities)

Example fix

// before
let state = cache_db.load_strategy(&strategy_id)?; // bails on Postgres
// after
match cache_db.load_strategy(&strategy_id) {
    Ok(state) => state,
    Err(e) if e.to_string().contains("not implemented") => { log::warn!("strategy state unavailable with SQL adapter"); Default::default() }
    Err(e) => return Err(e),
}
Defensive patterns

Strategy: fallback

Validate before calling

if is_postgres_cache(&cache_db) { /* skip strategy state load */ }

Type guard

fn is_postgres_cache(db: &dyn CacheDatabase) -> bool { db.as_any().downcast_ref::<PostgresCache>().is_some() }

Try / catch

match cache_db.load_strategy(&strategy_id) {
    Ok(state) => state,
    Err(e) if e.to_string().contains("not implemented") => { log::warn!("no persisted strategy state with SQL adapter"); AHashMap::new() }
    Err(e) => return Err(e),
}

Prevention

When it happens

Trigger: Loading strategy state (StrategyId) from a PostgreSQL cache database at strategy start with load_state enabled; restore tooling calling load_strategy on the SQL adapter.

Common situations: Switching deployments from Redis cache to PostgreSQL; expecting strategy checkpoint/restore to work across restarts with the SQL adapter.

Related errors


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