{"record":{"id":"c6d48dfd9088af07","repo":"nautechsystems/nautilus_trader","slug":"vega-pricing-timeout-exceeds-the-nanosecond-range","errorCode":null,"errorMessage":"vega pricing timeout exceeds the nanosecond range","messagePattern":"vega pricing timeout exceeds the nanosecond range","errorType":"panic","errorClass":null,"httpStatus":null,"severity":"error","filePath":"crates/data/src/aggregation.rs","lineNumber":2421,"sourceCode":"        if self\n            .clock\n            .borrow()\n            .timer_names()\n            .contains(&self.vega_pricing_timeout_timer_name.as_str())\n        {\n            return;\n        }\n\n        let Some(aggregator_weak) = self.aggregator_weak.clone() else {\n            return;\n        };\n        let callback = TimeEventCallback::RustLocal(Rc::new(move |_event: TimeEvent| {\n            if let Some(agg) = aggregator_weak.upgrade() {\n                agg.borrow_mut().clear_vega_pricing_timeout();\n            }\n        }));\n        let timeout = DurationNanos::try_from_secs(self.vega_pricing_timeout_seconds)\n            .expect(\"vega pricing timeout exceeds the nanosecond range\");\n        let alert_time = self.clock.borrow().timestamp_ns() + timeout;\n\n        self.clock\n            .borrow_mut()\n            .set_time_alert_ns(\n                &self.vega_pricing_timeout_timer_name,\n                alert_time,\n                Some(callback),\n                Some(true),\n            )\n            .expect(\"Failed to set spread quote vega pricing timeout\");\n    }\n\n    fn create_futures_spread_prices(&self) -> (f64, f64) {\n        let mut raw_ask = 0.0_f64;\n        let mut raw_bid = 0.0_f64;\n\n        for i in 0..self.leg_ids.len() {","sourceCodeStart":2403,"sourceCodeEnd":2439,"githubUrl":"https://github.com/nautechsystems/nautilus_trader/blob/18893faf8b356be3320add8de2f861b0b647cf06/crates/data/src/aggregation.rs#L2403-L2439","documentation":"The vega pricing timeout is configured in seconds and converted to nanoseconds with `DurationNanos::try_from_secs`, which fails when the second value exceeds u64 nanosecond range (i.e. > ~584 years, or a negative/huge f64-derived value). The `.expect` then panics.","triggerScenarios":"Setting `vega_pricing_timeout_seconds` to an absurd value (NaN, huge float, u64-seconds overflow) in the spread aggregator configuration before the timeout timer is armed.","commonSituations":"Config parsed from JSON/TOML where the timeout is in milliseconds but assigned to a seconds field multiplied incorrectly; sentinel values like f64::MAX used as 'no timeout'; unit confusion between seconds/millis in adapter config.","solutions":["Set a sane timeout in seconds (e.g. 1–60) for `vega_pricing_timeout_seconds`","Fix unit conversion at config load: if the source value is milliseconds, divide by 1000 before assigning","Validate/limit the config value (reject NaN, negative, or > some bound) before constructing the aggregator"],"exampleFix":"// before\nagg_config.vega_pricing_timeout_seconds = timeout_ms * 1000.0; // wrong direction, can overflow\n// after\nagg_config.vega_pricing_timeout_seconds = timeout_ms / 1000.0;\nassert!(agg_config.vega_pricing_timeout_seconds.is_finite()\n    && (0.0..=3600.0).contains(&agg_config.vega_pricing_timeout_seconds));","handlingStrategy":"validation","validationCode":"// Rust: validate timeout seconds before arming\nlet t = config.vega_pricing_timeout_seconds;\nassert!(t.is_finite() && t > 0.0 && t <= 3600.0, \"invalid vega pricing timeout: {t}\");","typeGuard":"fn valid_timeout_secs(t: f64) -> Option<f64> { t.is_finite().then(|| t).filter(|v| *v > 0.0 && *v <= 3600.0) }","tryCatchPattern":"let result = std::panic::catch_unwind(|| agg.arm_vega_pricing_timeout());","preventionTips":["Keep timeouts in a bounded sane range (seconds, not millis)","Fix ms-vs-s conversion direction at config load","Reject NaN/negative/sentinel timeout values in config validation"],"tags":["rust","panic","duration","config","overflow"],"backgroundTag":"value-out-of-range","analyzedSha":"18893faf8b356be3320add8de2f861b0b647cf06","analyzedAt":"2026-09-08T20:49:34.690Z","contentChangedAt":"2026-09-08T20:49:34.690Z","schemaVersion":2},"datasetVersion":"2026-09-14T00:17:10.932Z"}