{"record":{"id":"9fbdc6e8b87915b5","repo":"nautechsystems/nautilus_trader","slug":"invalid-currency1-topic-length","errorCode":null,"errorMessage":"Invalid currency1 topic length","messagePattern":"Invalid currency1 topic length","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"crates/adapters/blockchain/src/exchanges/parsing/uniswap_v4/initialize.rs","lineNumber":120,"sourceCode":"        .as_ref();\n    let pool_identifier = Ustr::from(&hex::encode_prefixed(pool_id_bytes));\n\n    let currency0 = Address::from_slice(\n        topics[2]\n            .as_ref()\n            .ok_or_else(|| anyhow::anyhow!(\"Missing currency0 topic\"))?\n            .as_ref()\n            .get(12..32)\n            .ok_or_else(|| anyhow::anyhow!(\"Invalid currency0 topic length\"))?,\n    );\n\n    let currency1 = Address::from_slice(\n        topics[3]\n            .as_ref()\n            .ok_or_else(|| anyhow::anyhow!(\"Missing currency1 topic\"))?\n            .as_ref()\n            .get(12..32)\n            .ok_or_else(|| anyhow::anyhow!(\"Invalid currency1 topic length\"))?,\n    );\n\n    if let Some(data) = log.data {\n        let data_bytes = data.as_ref();\n\n        // Validate minimum data length (5 fields × 32 bytes = 160 bytes)\n        if data_bytes.len() < 160 {\n            anyhow::bail!(\n                \"Initialize event data too short: expected at least 160 bytes, was {}\",\n                data_bytes.len()\n            );\n        }\n\n        let decoded = <InitializeEventData as SolType>::abi_decode(data_bytes)\n            .map_err(|e| anyhow::anyhow!(\"Failed to decode initialize event data: {e}\"))?;\n\n        let mut event = PoolCreatedEvent::new(\n            block_number,","sourceCodeStart":102,"sourceCodeEnd":138,"githubUrl":"https://github.com/nautechsystems/nautilus_trader/blob/18893faf8b356be3320add8de2f861b0b647cf06/crates/adapters/blockchain/src/exchanges/parsing/uniswap_v4/initialize.rs#L102-L138","documentation":"Thrown by `parse_initialize_event_hypersync` when `topics[3]` exists but is not a full 32-byte word, so slicing bytes 12..32 (the last 20 bytes holding the Ethereum address) is impossible. Solidity indexed address topics are always 32 bytes; a shorter value indicates malformed log data from the indexer.","triggerScenarios":"Calling `parse_initialize_event_hypersync` with a log whose `topics[3]` value contains fewer than 32 bytes. Occurs when HyperSync returns truncated/padded-differently topic values or a non-32-byte indexed parameter.","commonSituations":"Indexer data corruption or partial sync; querying logs from an event ABI where topic3 is not an address; mixing log formats from different HyperSync schema versions.","solutions":["Validate `log.topics[3].as_ref().len() == 32` before parsing and skip/re-fetch malformed logs.","Re-query HyperSync for the affected block/tx to rule out transient indexer truncation.","Confirm you are using the Uniswap V4 Initialize event ABI (address-typed hooks topic) matching the deployed contract.","Check the HyperSync client/schema version for topic encoding changes."],"exampleFix":"// before\nlet currency1 = Address::from_slice(topics[3].as_ref()?.as_ref().get(12..32).ok_or_else(|| anyhow::anyhow!(\"Invalid currency1 topic length\"))?);\n// after\nlet topic3 = topics[3].as_ref().ok_or_else(|| anyhow::anyhow!(\"Missing currency1 topic\"))?.as_ref();\nanyhow::ensure!(topic3.len() == 32, \"currency1 topic has {} bytes, expected 32\", topic3.len());\nlet currency1 = Address::from_slice(&topic3[12..32]);","handlingStrategy":"validation","validationCode":"fn topics_are_32_bytes(log: &HypersyncLog) -> bool {\n    log.topics.iter().all(|t| t.as_ref().map(|v| v.as_ref().len() == 32).unwrap_or(false))\n}","typeGuard":"fn valid_topic(t: &Option<HypersyncValue>) -> bool {\n    t.as_ref().map(|v| v.as_ref().len() == 32).unwrap_or(false)\n}","tryCatchPattern":"match parse_initialize_event_hypersync(&log) {\n    Ok(ev) => store(ev),\n    Err(e) if e.to_string().contains(\"topic length\") => { re_fetch_log(&log).await?; }\n    Err(e) => return Err(e),\n}","preventionTips":["Check every topic is exactly 32 bytes before address extraction","Re-fetch suspicious logs by block/tx to rule out indexer truncation","Pin the HyperSync client/schema version and test with known-good logs"],"tags":["blockchain","parsing","hypersync","event-decoding"],"backgroundTag":"invalid-argument-format","analyzedSha":"18893faf8b356be3320add8de2f861b0b647cf06","analyzedAt":"2026-09-08T20:49:34.690Z","contentChangedAt":"2026-09-08T20:49:34.690Z","schemaVersion":2},"datasetVersion":"2026-09-14T05:17:10.506Z"}