{"record":{"id":"5feb5b0016916659","repo":"nautechsystems/nautilus_trader","slug":"binance-spot-market-data-mode-sbe-requires-ed25519","errorCode":null,"errorMessage":"Binance Spot market data mode SBE requires Ed25519 API credentials. Set the appropriate env vars for your environment, or provide api_key/api_secret in the data client config","messagePattern":"Binance Spot market data mode SBE requires Ed25519 API credentials\\. Set the appropriate env vars for your environment, or provide api_key/api_secret in the data client config","errorType":"validation","errorClass":"anyhow::Error","httpStatus":null,"severity":"error","filePath":"crates/adapters/binance/src/spot/data.rs","lineNumber":1493,"sourceCode":"        Ok(())\n    }\n\n    fn dispose(&mut self) -> anyhow::Result<()> {\n        log::debug!(\"Disposing {id}\", id = self.client_id);\n        self.stop()\n    }\n\n    async fn connect(&mut self) -> anyhow::Result<()> {\n        if self.is_connected() && self.session_tasks.is_open() && self.command_tasks.is_open() {\n            return Ok(());\n        }\n\n        register_binance_custom_data();\n\n        if self.spot_market_data_mode == BinanceSpotMarketDataMode::Sbe\n            && !self.ws_client.has_credentials()\n        {\n            anyhow::bail!(\n                \"Binance Spot market data mode SBE requires Ed25519 API credentials. \\\n                 Set the appropriate env vars for your environment, \\\n                 or provide api_key/api_secret in the data client config\"\n            );\n        }\n\n        self.prepare_task_groups().await?;\n        let ws_client = self.ws_client.clone();\n        let setup_guard =\n            TaskGroupGuard::new(&[&self.session_tasks, &self.command_tasks], move || {\n                ws_client.begin_shutdown();\n            });\n\n        Self::refresh_instrument_catalog(\n            &self.http_client,\n            &self.config.instrument_provider,\n            self.config.us,\n            &self.instruments,","sourceCodeStart":1475,"sourceCodeEnd":1511,"githubUrl":"https://github.com/nautechsystems/nautilus_trader/blob/18893faf8b356be3320add8de2f861b0b647cf06/crates/adapters/binance/src/spot/data.rs#L1475-L1511","documentation":"Binance Spot SBE (Simple Binary Encoding) market data streams require authenticated Ed25519-signed websocket connections. The data client refuses to `connect()` in SBE mode when the underlying websocket client holds no API credentials (`has_credentials()` is false), preventing a doomed connection attempt. Regular JSON market data is public, but SBE requires the key/secret pair.","triggerScenarios":"Configuring `spot_market_data_mode = Sbe` on the Binance Spot data client while neither the config provides `api_key`/`api_secret` nor the environment exposes the expected credential env vars, then calling `connect()`.","commonSituations":"Running locally where env vars (e.g. BINANCE_API_KEY / BINANCE_API_SECRET) are unset because credentials live only in production secrets; switching market data mode to SBE for lower-latency binary feeds without updating the config; container deployments where env vars were not forwarded.","solutions":["Provide `api_key` and `api_secret` (Ed25519 keypair credentials) in the data client config","Export the Binance Ed25519 API credentials as environment variables for your environment","Verify the credentials are Ed25519 type, not HMAC, as SBE requires Ed25519","If SBE authentication is not needed, switch `spot_market_data_mode` back to the default JSON mode","Check that the process environment actually receives the vars (docker --env-file, k8s secret mounting)"],"exampleFix":"// before\nDataClientConfig { spot_market_data_mode: Sbe, /* no credentials */ }\n// after\nDataClientConfig {\n    spot_market_data_mode: Sbe,\n    api_key: Some(env::var(\"BINANCE_API_KEY\")?),\n    api_secret: Some(env::var(\"BINANCE_API_SECRET\")?),\n}","handlingStrategy":"validation","validationCode":"fn validate_sbe_credentials(config: &DataClientConfig, env: &Env) -> Result<(), String> {\n    if config.spot_market_data_mode == BinanceSpotMarketDataMode::Sbe {\n        let has_cfg = config.api_key.is_some() && config.api_secret.is_some();\n        let has_env = env::var(\"BINANCE_API_KEY\").is_ok() && env::var(\"BINANCE_API_SECRET\").is_ok();\n        if !has_cfg && !has_env {\n            return Err(\"SBE mode requires Ed25519 api_key/api_secret (config or env)\".into());\n        }\n    }\n    Ok()\n}","typeGuard":"fn has_credentials(c: &DataClientConfig) -> bool {\n    c.api_key.as_deref().map_or(false, |k| !k.is_empty())\n        && c.api_secret.as_deref().map_or(false, |s| !s.is_empty())\n}","tryCatchPattern":"match data_client.connect().await {\n    Err(e) if e.to_string().contains(\"requires Ed25519 API credentials\") => {\n        eprintln!(\"SBE auth misconfigured: {e:#}\");\n        // fall back to JSON mode or abort startup\n    }\n    other => other?,\n}","preventionTips":["Always set Binance Ed25519 API credentials in env or config before enabling SBE mode","Verify key type is Ed25519 (not HMAC) when creating API keys on Binance","Forward credential env vars into containers/k8s pods explicitly","Prefer JSON market data mode when authenticated market data is not needed"],"tags":["rust","authentication","credentials","binance","config"],"backgroundTag":"missing-credentials","analyzedSha":"18893faf8b356be3320add8de2f861b0b647cf06","analyzedAt":"2026-09-08T20:49:34.690Z","contentChangedAt":"2026-09-08T20:49:34.690Z","schemaVersion":2},"datasetVersion":"2026-09-23T08:17:48.524Z"}