nautechsystems/nautilus_trader · error
Replacement scan cursor timestamp is negative
Error message
Replacement scan cursor timestamp is negative
What it means
Data-integrity check when loading the replacement scan cursor: the stored cursor row's timestamp column decoded to a negative value, which cannot be a valid Unix timestamp, so the cursor is rejected as corrupt.
Source
Thrown at crates/adapters/blockchain/src/cache/database.rs:6220
.bind(chain_id)
.bind(wallet_address)
.bind(nonce)
.fetch_optional(&self.pool)
.await
.context("failed to load replacement scan cursor")?;
row.map(
|(number, hash, parent_hash, timestamp, base_fee, stored_digest)| {
anyhow::ensure!(
stored_digest == manifest_digest,
"Replacement scan manifest identity changed"
);
Ok(ExecutionVerifiedHeader {
number: u64::try_from(number)
.context("Replacement scan cursor number is negative")?,
hash,
parent_hash,
timestamp: u64::try_from(timestamp)
.context("Replacement scan cursor timestamp is negative")?,
base_fee_per_gas: base_fee
.map(|value| {
value.parse::<u128>().map_err(|_| {
anyhow::anyhow!("Replacement scan cursor base fee is invalid")
})
})
.transpose()?,
})
},
)
.transpose()
}
pub(crate) async fn record_execution_replacement_scan(
&self,
scan: &ExecutionReplacementScan<'_>,
) -> anyhow::Result<()> {
anyhow::ensure!(View on GitHub (pinned to 18893faf8b)
Solutions
- Inspect and fix or delete the row with the negative timestamp
- Fix or re-run the writer that produced the negative timestamp
- Re-record the replacement scan so a valid header is stored
Defensive patterns
Strategy: validation
Validate before calling
let ts: i64 = /* loaded timestamp */;
if ts < 0 {
// corrupt row: purge and re-record the scan
} Type guard
fn valid_timestamp(ts: i64) -> bool { ts >= 0 } Try / catch
match db.load_execution_replacement_cursor(..).await {
Err(e) if e.to_string().contains("cursor timestamp is negative") => {
// delete corrupted row and re-run record_execution_replacement_scan
}
other => other,
} Prevention
- Write timestamps only from trusted clock sources
- Add CHECK (timestamp >= 0) constraints
- Detect-and-rescan rather than trusting legacy rows after tooling changes
When it happens
Trigger: load_execution_replacement_cursor reads a row whose execution_verified_finalized_header.timestamp is negative and calls u64::try_from(timestamp).
Common situations: Corrupted or hand-edited rows; clock skew bugs in the writer producing negative values; schema/type confusion from external tooling.
Understand the failure class
Background: "value must be between 0 and 1" / "out of range" / "must not be negative" errors: fixing range-validation failures across open-source libraries — this error's family across 42 libraries.
Related errors
- Finalized header base fee is invalid
- Canonical nonce overflow
- Replacement scan cursor number is negative
- Replacement scan cursor base fee is invalid
- Stored execution payload has a truncated envelope header
AI-assisted analysis of nautechsystems/nautilus_trader@18893faf8b (2026-09-08).
Data as JSON: /api/errors/d6b74ee4a5efc07a.
Report an issue: GitHub.