nautechsystems/nautilus_trader · error

Initialize event data too short: expected at least 160 bytes

Error message

Initialize event data too short: expected at least 160 bytes, was {data_bytes_len}

What it means

parse_initialize_event_hypersync validates that the Initialize event data carries at least 5 words (160 bytes): sqrtPriceX96, tick, protocolFee, lpFee, and the reserved/extra word layout. Shorter data cannot be decoded as InitializeEventData, so the parser bails with the actual length in the message.

Source

Thrown at crates/adapters/blockchain/src/exchanges/parsing/uniswap_v4/initialize.rs:128

            .get(12..32)
            .ok_or_else(|| anyhow::anyhow!("Invalid currency0 topic length"))?,
    );

    let currency1 = Address::from_slice(
        topics[3]
            .as_ref()
            .ok_or_else(|| anyhow::anyhow!("Missing currency1 topic"))?
            .as_ref()
            .get(12..32)
            .ok_or_else(|| anyhow::anyhow!("Invalid currency1 topic length"))?,
    );

    if let Some(data) = log.data {
        let data_bytes = data.as_ref();

        // Validate minimum data length (5 fields × 32 bytes = 160 bytes)
        if data_bytes.len() < 160 {
            anyhow::bail!(
                "Initialize event data too short: expected at least 160 bytes, was {}",
                data_bytes.len()
            );
        }

        let decoded = <InitializeEventData as SolType>::abi_decode(data_bytes)
            .map_err(|e| anyhow::anyhow!("Failed to decode initialize event data: {e}"))?;

        let mut event = PoolCreatedEvent::new(
            block_number,
            currency0,
            currency1,
            pool_manager_address, // V4 pools are managed by PoolManager
            PoolIdentifier::PoolId(pool_identifier), // Pool ID (bytes32 as hex string)
            Some(decoded.fee.to::<u32>()),
            Some(i32::try_from(decoded.tick_spacing)? as u32),
        );

View on GitHub (pinned to 18893faf8b)

Solutions

  1. Check the V4 contract revision on the target chain and use InitializeEventData bindings matching that deployed version
  2. Verify data length >= 160 in the caller before invoking the parser and skip shorter logs
  3. Filter by exact V4 Initialize topic0 to exclude foreign events
  4. Compare the failing log's data hex against the expected 5-word layout

Example fix

// before
if data_bytes.len() < 160 {
    anyhow::bail!("Initialize event data too short: expected at least 160 bytes, was {}", data_bytes.len());
}
// after
if data_bytes.len() < 160 {
    tracing::debug!(len = data_bytes.len(), "skipping short v4 initialize log");
    return Ok(None); // or continue
}
Defensive patterns

Strategy: validation

Validate before calling

fn has_v4_initialize_data(log: &HypersyncLog) -> bool {
    log.data.as_ref().map(|d| d.as_ref().len() >= 160).unwrap_or(false)
}
if !has_v4_initialize_topics(&log) || !has_v4_initialize_data(&log) { skip_or_log(); }

Try / catch

match parse_initialize_event_hypersync(&log, &dex) {
    Ok(ev) => handle(ev),
    Err(e) => { tracing::warn!(%e, "short v4 initialize log skipped"); Ok(None) }
}

Prevention

When it happens

Trigger: Calling parse_initialize_event_hypersync with a V4 Initialize-like log whose data is under 160 bytes — an older V4 contract revision with fewer fields (e.g. before lpFee/protocolFee were added), a non-V4 event sharing the topic0, or truncated hypersync data.

Common situations: Indexing chains deployed with an earlier Uniswap V4 revision whose Initialize data layout omits newer fee fields; broad topic filters catching foreign events; provider truncation on old blocks.

Understand the failure class

Background: payload too large / request exceeds maximum size: why libraries cap bytes and how to fix oversize payloads — this error's family across 50 libraries.

Related errors


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