nautilus_okx/common/consts.rs
1// -------------------------------------------------------------------------------------------------
2// Copyright (C) 2015-2025 Nautech Systems Pty Ltd. All rights reserved.
3// https://nautechsystems.io
4//
5// Licensed under the GNU Lesser General Public License Version 3.0 (the "License");
6// You may not use this file except in compliance with the License.
7// You may obtain a copy of the License at https://www.gnu.org/licenses/lgpl-3.0.en.html
8//
9// Unless required by applicable law or agreed to in writing, software
10// distributed under the License is distributed on an "AS IS" BASIS,
11// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12// See the License for the specific language governing permissions and
13// limitations under the License.
14// -------------------------------------------------------------------------------------------------
15
16//! Core constants shared across the OKX adapter components.
17
18use std::sync::LazyLock;
19
20use ahash::AHashSet;
21use nautilus_model::{
22 enums::{OrderType, TimeInForce},
23 identifiers::Venue,
24};
25use ustr::Ustr;
26
27pub const OKX: &str = "OKX";
28pub static OKX_VENUE: LazyLock<Venue> = LazyLock::new(|| Venue::new(Ustr::from(OKX)));
29
30/// See <https://www.okx.com/docs-v5/en/#overview-broker-program> for further details.
31pub const OKX_NAUTILUS_BROKER_ID: &str = "a535cbe8d0c8BCDE";
32
33// Use the canonical host with www to avoid cross-domain redirects which may
34// strip authentication headers in some HTTP clients and middleboxes.
35pub const OKX_HTTP_URL: &str = "https://www.okx.com";
36pub const OKX_WS_PUBLIC_URL: &str = "wss://ws.okx.com:8443/ws/v5/public";
37pub const OKX_WS_PRIVATE_URL: &str = "wss://ws.okx.com:8443/ws/v5/private";
38pub const OKX_WS_BUSINESS_URL: &str = "wss://ws.okx.com:8443/ws/v5/business";
39pub const OKX_WS_DEMO_PUBLIC_URL: &str = "wss://wspap.okx.com:8443/ws/v5/public";
40pub const OKX_WS_DEMO_PRIVATE_URL: &str = "wss://wspap.okx.com:8443/ws/v5/private";
41pub const OKX_WS_DEMO_BUSINESS_URL: &str = "wss://wspap.okx.com:8443/ws/v5/business";
42
43pub const OKX_WS_TOPIC_DELIMITER: char = ':';
44
45/// OKX supported order time in force.
46///
47/// # Notes
48///
49/// - OKX implements IOC and FOK as order types rather than separate time-in-force parameters.
50/// - FOK is only supported with Limit orders (Market + FOK is not supported).
51/// - IOC with Market orders uses OptimalLimitIoc, with Limit orders uses Ioc.
52/// - GTD is supported via expire_time parameter.
53pub const OKX_SUPPORTED_TIME_IN_FORCE: &[TimeInForce] = &[
54 TimeInForce::Gtc, // Good Till Cancel (default)
55 TimeInForce::Ioc, // Immediate or Cancel (mapped to OKXOrderType::Ioc or OptimalLimitIoc)
56 TimeInForce::Fok, // Fill or Kill (only with Limit orders, mapped to OKXOrderType::Fok)
57];
58
59/// OKX supported order types.
60///
61/// # Notes
62///
63/// - PostOnly is supported as a flag on limit orders.
64/// - Conditional orders (stop/trigger) are supported via algo orders.
65pub const OKX_SUPPORTED_ORDER_TYPES: &[OrderType] = &[
66 OrderType::Market,
67 OrderType::Limit,
68 OrderType::MarketToLimit, // Mapped to IOC when no price is specified
69 OrderType::StopMarket, // Supported via algo order API
70 OrderType::StopLimit, // Supported via algo order API
71 OrderType::MarketIfTouched, // Supported via algo order API
72 OrderType::LimitIfTouched, // Supported via algo order API
73];
74
75/// Conditional order types that require the OKX algo order API.
76pub const OKX_CONDITIONAL_ORDER_TYPES: &[OrderType] = &[
77 OrderType::StopMarket,
78 OrderType::StopLimit,
79 OrderType::MarketIfTouched,
80 OrderType::LimitIfTouched,
81];
82
83/// OKX error codes that should trigger retries.
84///
85/// Only retry on temporary network/system issues.
86///
87/// # References
88///
89/// Based on OKX API documentation: <https://www.okx.com/docs-v5/en/#error-codes>
90pub static OKX_RETRY_ERROR_CODES: LazyLock<AHashSet<&'static str>> = LazyLock::new(|| {
91 let mut codes = AHashSet::new();
92
93 // Temporary system errors
94 codes.insert("50001"); // Service temporarily unavailable
95 codes.insert("50004"); // API endpoint request timeout (does not mean that the request was successful or failed, please check the request result)
96 codes.insert("50005"); // API is offline or unavailable
97 codes.insert("50013"); // System busy, please try again later
98 codes.insert("50026"); // System error, please try again later
99
100 // Rate limit errors (temporary)
101 codes.insert("50011"); // Request too frequent
102 codes.insert("50113"); // API requests exceed the limit
103
104 // WebSocket connection issues (temporary)
105 codes.insert("60001"); // OK not received in time
106 codes.insert("60005"); // Connection closed as there was no data transmission in the last 30 seconds
107
108 codes
109});
110
111/// Determines if an OKX error code should trigger a retry.
112pub fn should_retry_error_code(error_code: &str) -> bool {
113 OKX_RETRY_ERROR_CODES.contains(error_code)
114}
115
116/// OKX error code returned when a post-only order would immediately take liquidity.
117pub const OKX_POST_ONLY_ERROR_CODE: &str = "51019";
118
119/// OKX cancel source code used when a post-only order is auto-cancelled for taking liquidity.
120pub const OKX_POST_ONLY_CANCEL_SOURCE: &str = "31";
121
122/// Human-readable reason used when a post-only order is auto-cancelled for taking liquidity.
123pub const OKX_POST_ONLY_CANCEL_REASON: &str = "POST_ONLY would take liquidity";
124
125/// Target currency literal for base currency.
126pub const OKX_TARGET_CCY_BASE: &str = "base_ccy";
127
128/// Target currency literal for quote currency.
129pub const OKX_TARGET_CCY_QUOTE: &str = "quote_ccy";