ccxt_exchanges/okx/
builder.rs1use super::{Okx, OkxOptions};
7use ccxt_core::types::default_type::{DefaultSubType, DefaultType};
8use ccxt_core::{ExchangeConfig, Result};
9use serde_json::Value;
10use std::collections::HashMap;
11
12#[derive(Debug, Clone)]
32pub struct OkxBuilder {
33 config: ExchangeConfig,
35 options: OkxOptions,
37}
38
39impl Default for OkxBuilder {
40 fn default() -> Self {
41 Self::new()
42 }
43}
44
45impl OkxBuilder {
46 pub fn new() -> Self {
56 Self {
57 config: ExchangeConfig {
58 id: "okx".to_string(),
59 name: "OKX".to_string(),
60 ..Default::default()
61 },
62 options: OkxOptions::default(),
63 }
64 }
65
66 pub fn api_key(mut self, key: impl Into<String>) -> Self {
72 self.config.api_key = Some(key.into());
73 self
74 }
75
76 pub fn secret(mut self, secret: impl Into<String>) -> Self {
82 self.config.secret = Some(secret.into());
83 self
84 }
85
86 pub fn passphrase(mut self, passphrase: impl Into<String>) -> Self {
94 self.config.password = Some(passphrase.into());
95 self
96 }
97
98 pub fn sandbox(mut self, enabled: bool) -> Self {
107 self.config.sandbox = enabled;
108 self.options.testnet = enabled;
109 self
110 }
111
112 pub fn account_mode(mut self, mode: impl Into<String>) -> Self {
120 self.options.account_mode = mode.into();
121 self
122 }
123
124 pub fn default_type(mut self, default_type: impl Into<DefaultType>) -> Self {
145 self.options.default_type = default_type.into();
146 self
147 }
148
149 pub fn default_sub_type(mut self, sub_type: DefaultSubType) -> Self {
174 self.options.default_sub_type = Some(sub_type);
175 self
176 }
177
178 pub fn timeout(mut self, seconds: u64) -> Self {
184 self.config.timeout = seconds;
185 self
186 }
187
188 pub fn enable_rate_limit(mut self, enabled: bool) -> Self {
194 self.config.enable_rate_limit = enabled;
195 self
196 }
197
198 pub fn proxy(mut self, proxy: impl Into<String>) -> Self {
204 self.config.proxy = Some(proxy.into());
205 self
206 }
207
208 pub fn verbose(mut self, enabled: bool) -> Self {
214 self.config.verbose = enabled;
215 self
216 }
217
218 pub fn option(mut self, key: impl Into<String>, value: Value) -> Self {
225 self.config.options.insert(key.into(), value);
226 self
227 }
228
229 pub fn options(mut self, options: HashMap<String, Value>) -> Self {
235 self.config.options.extend(options);
236 self
237 }
238
239 #[cfg(test)]
241 pub fn get_config(&self) -> &ExchangeConfig {
242 &self.config
243 }
244
245 #[cfg(test)]
247 pub fn get_options(&self) -> &OkxOptions {
248 &self.options
249 }
250
251 pub fn build(self) -> Result<Okx> {
261 Okx::new_with_options(self.config, self.options)
262 }
263}
264
265#[cfg(test)]
266mod tests {
267 use super::*;
268
269 #[test]
270 fn test_builder_default() {
271 let builder = OkxBuilder::new();
272 assert_eq!(builder.config.id, "okx");
273 assert_eq!(builder.config.name, "OKX");
274 assert!(!builder.config.sandbox);
275 assert_eq!(builder.options.account_mode, "cash");
276 }
277
278 #[test]
279 fn test_builder_api_key() {
280 let builder = OkxBuilder::new().api_key("test-key");
281 assert_eq!(builder.config.api_key, Some("test-key".to_string()));
282 }
283
284 #[test]
285 fn test_builder_secret() {
286 let builder = OkxBuilder::new().secret("test-secret");
287 assert_eq!(builder.config.secret, Some("test-secret".to_string()));
288 }
289
290 #[test]
291 fn test_builder_passphrase() {
292 let builder = OkxBuilder::new().passphrase("test-passphrase");
293 assert_eq!(builder.config.password, Some("test-passphrase".to_string()));
294 }
295
296 #[test]
297 fn test_builder_sandbox() {
298 let builder = OkxBuilder::new().sandbox(true);
299 assert!(builder.config.sandbox);
300 assert!(builder.options.testnet);
301 }
302
303 #[test]
304 fn test_builder_account_mode() {
305 let builder = OkxBuilder::new().account_mode("cross");
306 assert_eq!(builder.options.account_mode, "cross");
307 }
308
309 #[test]
310 fn test_builder_default_type() {
311 let builder = OkxBuilder::new().default_type(DefaultType::Swap);
312 assert_eq!(builder.options.default_type, DefaultType::Swap);
313 }
314
315 #[test]
316 fn test_builder_default_type_from_string() {
317 let builder = OkxBuilder::new().default_type("futures");
318 assert_eq!(builder.options.default_type, DefaultType::Futures);
319 }
320
321 #[test]
322 fn test_builder_default_sub_type() {
323 let builder = OkxBuilder::new().default_sub_type(DefaultSubType::Inverse);
324 assert_eq!(
325 builder.options.default_sub_type,
326 Some(DefaultSubType::Inverse)
327 );
328 }
329
330 #[test]
331 fn test_builder_default_type_and_sub_type() {
332 let builder = OkxBuilder::new()
333 .default_type(DefaultType::Swap)
334 .default_sub_type(DefaultSubType::Linear);
335 assert_eq!(builder.options.default_type, DefaultType::Swap);
336 assert_eq!(
337 builder.options.default_sub_type,
338 Some(DefaultSubType::Linear)
339 );
340 }
341
342 #[test]
343 fn test_builder_timeout() {
344 let builder = OkxBuilder::new().timeout(60);
345 assert_eq!(builder.config.timeout, 60);
346 }
347
348 #[test]
349 fn test_builder_chaining() {
350 let builder = OkxBuilder::new()
351 .api_key("key")
352 .secret("secret")
353 .passphrase("pass")
354 .sandbox(true)
355 .timeout(30)
356 .account_mode("isolated");
357
358 assert_eq!(builder.config.api_key, Some("key".to_string()));
359 assert_eq!(builder.config.secret, Some("secret".to_string()));
360 assert_eq!(builder.config.password, Some("pass".to_string()));
361 assert!(builder.config.sandbox);
362 assert_eq!(builder.config.timeout, 30);
363 assert_eq!(builder.options.account_mode, "isolated");
364 }
365
366 #[test]
367 fn test_builder_build() {
368 let result = OkxBuilder::new().build();
369 assert!(result.is_ok());
370
371 let okx = result.unwrap();
372 assert_eq!(okx.id(), "okx");
373 assert_eq!(okx.name(), "OKX");
374 }
375
376 #[test]
377 fn test_builder_build_with_credentials() {
378 let result = OkxBuilder::new()
379 .api_key("test-key")
380 .secret("test-secret")
381 .passphrase("test-passphrase")
382 .build();
383
384 assert!(result.is_ok());
385 }
386
387 #[test]
388 fn test_builder_enable_rate_limit() {
389 let builder = OkxBuilder::new().enable_rate_limit(false);
390 assert!(!builder.config.enable_rate_limit);
391 }
392
393 #[test]
394 fn test_builder_proxy() {
395 let builder = OkxBuilder::new().proxy("http://proxy.example.com:8080");
396 assert_eq!(
397 builder.config.proxy,
398 Some("http://proxy.example.com:8080".to_string())
399 );
400 }
401
402 #[test]
403 fn test_builder_verbose() {
404 let builder = OkxBuilder::new().verbose(true);
405 assert!(builder.config.verbose);
406 }
407}