FuelLabs/fuel-core · error
relayer database height({relayer_db_height}) is less than ta
Error message
relayer database height({relayer_db_height}) is less than target height({target_da_height}) What it means
rollback_relayer_to rewinds the relayer (DA) database to a target DA block height. Its height is Optional, but if Some(height) is strictly below target_da_height the rollback aborts: the relayer DB would need to move forward, which rollback never does. The relayer DB must first catch up to (or past) the target before it can be trimmed back.
Source
Thrown at crates/fuel-core/src/combined_database.rs:620
target_da_height: DaBlockHeight,
shutdown_listener: &mut S,
) -> anyhow::Result<()>
where
S: ShutdownListener,
{
while !shutdown_listener.is_cancelled() {
let relayer_db_height = self.relayer().latest_height_from_metadata()?;
let relayer_db_rolled_back =
is_equal_or_none(relayer_db_height, target_da_height);
if relayer_db_rolled_back {
break;
}
if let Some(relayer_db_height) = relayer_db_height
&& relayer_db_height < target_da_height
{
return Err(anyhow::anyhow!(
"relayer database height({relayer_db_height}) \
is less than target height({target_da_height})"
));
}
if let Some(relayer_db_height) = relayer_db_height
&& relayer_db_height > target_da_height
{
self.relayer().rollback_last_block()?;
}
}
if shutdown_listener.is_cancelled() {
return Err(anyhow::anyhow!(
"Stop the rollback due to shutdown signal received"
));
}
View on GitHub (pinned to b9d4d170da)
Solutions
- Let the relayer sync forward from the DA layer until its height >= target_da_height, then retry the rollback.
- Derive target_da_height from the relayer DB's own current height rather than from chain state.
- If relayer history is disposable, wipe the relayer DB and let it re-sync.
Defensive patterns
Strategy: validation
Validate before calling
if let Some(relayer_height) = db.relayer().latest_height_from_metadata()? {
if target_da_height > relayer_height {
anyhow::bail!("relayer at {} is behind target {}; sync the relayer first", relayer_height, target_da_height);
}
}
db.rollback_relayer_to(target_da_height, &mut shutdown)?; Try / catch
match db.rollback_relayer_to(target_da_height, &mut shutdown) {
Ok(()) => Ok(()),
Err(e) if e.to_string().contains("relayer database height") => {
// relayer must move forward first: this is a sync problem, not a rollback problem
anyhow::bail!("sync relayer to >= {} before rollback: {}", target_da_height, e)
}
Err(e) => Err(e),
} Prevention
- Compute the DA rollback target from the relayer DB's own height, not from chain state.
- Keep the relayer running and healthy so its DB tracks the DA layer.
- A relayer DB behind its target can be wiped and re-synced if history is disposable.
When it happens
Trigger: Calling rollback_relayer_to with a DA height above the relayer database's recorded height — relayer lagging behind DA layer, or a target computed from chain/consensus metadata that the relayer DB has not reached.
Common situations: Relayer temporarily disabled or falling behind the DA layer; restoring the relayer DB from an old snapshot; passing an on-chain-derived DA height without validating relayer progress.
Related errors
- on-chain database doesn't have height
- off-chain database doesn't have height
- on-chain database height({on_chain_height}) is less than tar
- off-chain database height({off_chain_height}) is less than t
- gas-price database height({gas_price_chain_height}) is less
AI-assisted analysis of FuelLabs/fuel-core@b9d4d170da (2026-08-16).
Data as JSON: /api/errors/520a4bb744727877.
Report an issue: GitHub.