nautechsystems/nautilus_trader · error · anyhow::Error

Failed to read execution schema version

Error message

Failed to read execution schema version: {e}

What it means

This error wraps failure reading the installed schema version from execution_schema_version (`SELECT version ... WHERE component = 'evm_execution'`). The library throws it to distinguish version-lookup failures from DDL failures during migration.

Solutions

  1. Ensure execution_schema_version table exists with a smallint version column (create it in the same migration)
  2. Verify connectivity and SELECT privileges on execution_schema_version
  3. Compare the column type to i16 (SMALLINT); alter if it was created as INTEGER
  4. Re-run migrations in order so version tracking is initialized before it is read

Example fix

// before
.map_err(|e| anyhow::anyhow!("Failed to read execution schema version: {e}"))?;
// after
.map_err(|e| {
    tracing::error!(error = %e, "execution_schema_version read failed");
    anyhow::anyhow!("Failed to read execution schema version: {e}")
})?;
Defensive patterns

Strategy: try-catch

Validate before calling

let has_version_table = sqlx::query_scalar::<_, bool>(
    "SELECT to_regclass('execution_schema_version') IS NOT NULL"
).fetch_one(&pool).await?;
if !has_version_table { anyhow::bail!("execution_schema_version missing; initialize version tracking first"); }

Try / catch

match db.ensure_execution_transaction_schema().await {
    Ok(()) => (),
    Err(e) if e.to_string().contains("Failed to read execution schema version") => {
        init_execution_schema_version_table(&pool).await?;
        db.ensure_execution_transaction_schema().await?;
    }
    Err(e) => return Err(e),
}

Prevention

When it happens

Trigger: ensure_execution_transaction_schema runs and the execution_schema_version table is missing, the version column has an unexpected type (query_scalar expects i16), or the query fails due to connectivity/permissions.

Common situations: Partially applied earlier migration that created execution_transaction but not execution_schema_version; manual schema edits; smallint vs integer type mismatch in the version column.

Understand the failure class

Background: Record Not Found Errors: "not found", RecordNotFound, and "was not found" — what they mean and how to fix them — this error's family across 28 libraries.

Related errors


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

Appendix: source

Thrown at crates/adapters/blockchain/src/cache/database.rs:3596

                )),
                UNIQUE (intent_id, transition_key)
            )
            ",
        ] {
            sqlx::query(statement)
                .execute(&mut *transaction)
                .await
                .map_err(|e| {
                    anyhow::anyhow!("Failed to migrate execution_transaction table: {e}")
                })?;
        }

        let installed_version = sqlx::query_scalar::<_, i16>(
            "SELECT version FROM execution_schema_version WHERE component = 'evm_execution'",
        )
        .fetch_optional(&mut *transaction)
        .await
        .map_err(|e| anyhow::anyhow!("Failed to read execution schema version: {e}"))?;
        if let Some(installed_version) = installed_version
            && installed_version > EXECUTION_SCHEMA_VERSION
        {
            anyhow::bail!(
                "Execution schema version {} is newer than supported version {EXECUTION_SCHEMA_VERSION}",
                installed_version
            );
        }

        let unresolved_legacy = sqlx::query_scalar::<_, i64>(
            "
            SELECT COUNT(*)
            FROM execution_transaction
            WHERE status IN ('pending', 'included', 'reverted')
            ",
        )
        .fetch_one(&mut *transaction)
        .await

View on GitHub (pinned to 18893faf8b)