Skip to main content

binance_sdk/sub_account/rest_api/apis/
managed_sub_account_api.rs

1/*
2 * Sub Account REST API
3 *
4 * Create and manage sub-accounts, control permissions, and transfer assets via the Sub Account API.
5 *
6 * The version of the OpenAPI document: 1.0.0
7 *
8 *
9 * NOTE: This class is auto generated by OpenAPI Generator (https://openapi-generator.tech).
10 * https://openapi-generator.tech
11 * Do not edit the class manually.
12 */
13
14#![allow(unused_imports)]
15use async_trait::async_trait;
16use derive_builder::Builder;
17use reqwest;
18use rust_decimal::prelude::*;
19use serde::{Deserialize, Serialize};
20use serde_json::{Value, json};
21use std::collections::BTreeMap;
22
23use crate::common::{
24    config::ConfigurationRestApi,
25    models::{ParamBuildError, RestApiResponse},
26    utils::send_request,
27};
28use crate::sub_account::rest_api::models;
29
30const HAS_TIME_UNIT: bool = false;
31
32#[async_trait]
33pub trait ManagedSubAccountApi: Send + Sync {
34    async fn deposit_assets_into_the_managed_sub_account(
35        &self,
36        params: DepositAssetsIntoTheManagedSubAccountParams,
37    ) -> anyhow::Result<RestApiResponse<models::DepositAssetsIntoTheManagedSubAccountResponse>>;
38    async fn get_managed_sub_account_deposit_address(
39        &self,
40        params: GetManagedSubAccountDepositAddressParams,
41    ) -> anyhow::Result<RestApiResponse<models::GetManagedSubAccountDepositAddressResponse>>;
42    async fn query_managed_sub_account_asset_details(
43        &self,
44        params: QueryManagedSubAccountAssetDetailsParams,
45    ) -> anyhow::Result<RestApiResponse<Vec<models::QueryManagedSubAccountAssetDetailsResponseInner>>>;
46    async fn query_managed_sub_account_futures_asset_details(
47        &self,
48        params: QueryManagedSubAccountFuturesAssetDetailsParams,
49    ) -> anyhow::Result<RestApiResponse<models::QueryManagedSubAccountFuturesAssetDetailsResponse>>;
50    async fn query_managed_sub_account_list(
51        &self,
52        params: QueryManagedSubAccountListParams,
53    ) -> anyhow::Result<RestApiResponse<models::QueryManagedSubAccountListResponse>>;
54    async fn query_managed_sub_account_margin_asset_details(
55        &self,
56        params: QueryManagedSubAccountMarginAssetDetailsParams,
57    ) -> anyhow::Result<RestApiResponse<models::QueryManagedSubAccountMarginAssetDetailsResponse>>;
58    async fn query_managed_sub_account_snapshot(
59        &self,
60        params: QueryManagedSubAccountSnapshotParams,
61    ) -> anyhow::Result<RestApiResponse<models::QueryManagedSubAccountSnapshotResponse>>;
62    async fn query_managed_sub_account_transfer_log_master_account_investor(
63        &self,
64        params: QueryManagedSubAccountTransferLogMasterAccountInvestorParams,
65    ) -> anyhow::Result<
66        RestApiResponse<models::QueryManagedSubAccountTransferLogMasterAccountInvestorResponse>,
67    >;
68    async fn query_managed_sub_account_transfer_log_master_account_trading(
69        &self,
70        params: QueryManagedSubAccountTransferLogMasterAccountTradingParams,
71    ) -> anyhow::Result<
72        RestApiResponse<models::QueryManagedSubAccountTransferLogMasterAccountTradingResponse>,
73    >;
74    async fn query_managed_sub_account_transfer_log_sub_account_trading(
75        &self,
76        params: QueryManagedSubAccountTransferLogSubAccountTradingParams,
77    ) -> anyhow::Result<
78        RestApiResponse<models::QueryManagedSubAccountTransferLogSubAccountTradingResponse>,
79    >;
80    async fn withdrawl_assets_from_the_managed_sub_account(
81        &self,
82        params: WithdrawlAssetsFromTheManagedSubAccountParams,
83    ) -> anyhow::Result<RestApiResponse<models::WithdrawlAssetsFromTheManagedSubAccountResponse>>;
84}
85
86#[derive(Debug, Clone)]
87pub struct ManagedSubAccountApiClient {
88    configuration: ConfigurationRestApi,
89}
90
91impl ManagedSubAccountApiClient {
92    pub fn new(configuration: ConfigurationRestApi) -> Self {
93        Self { configuration }
94    }
95}
96
97#[allow(non_camel_case_types)]
98#[derive(Debug, Clone, Serialize, Deserialize)]
99pub enum QueryManagedSubAccountSnapshotTypeEnum {
100    #[serde(rename = "SPOT")]
101    Spot,
102    #[serde(rename = "MARGIN")]
103    Margin,
104    #[serde(rename = "FUTURES")]
105    Futures,
106}
107
108impl QueryManagedSubAccountSnapshotTypeEnum {
109    #[must_use]
110    pub fn as_str(&self) -> &'static str {
111        match self {
112            Self::Spot => "SPOT",
113            Self::Margin => "MARGIN",
114            Self::Futures => "FUTURES",
115        }
116    }
117}
118
119impl std::str::FromStr for QueryManagedSubAccountSnapshotTypeEnum {
120    type Err = Box<dyn std::error::Error + Send + Sync>;
121
122    fn from_str(s: &str) -> Result<Self, Self::Err> {
123        match s {
124            "SPOT" => Ok(Self::Spot),
125            "MARGIN" => Ok(Self::Margin),
126            "FUTURES" => Ok(Self::Futures),
127            other => {
128                Err(format!("invalid QueryManagedSubAccountSnapshotTypeEnum: {}", other).into())
129            }
130        }
131    }
132}
133
134#[allow(non_camel_case_types)]
135#[derive(Debug, Clone, Serialize, Deserialize)]
136pub enum QueryManagedSubAccountTransferLogMasterAccountInvestorTransferFunctionAccountTypeEnum {
137    #[serde(rename = "SPOT")]
138    Spot,
139    #[serde(rename = "MARGIN")]
140    Margin,
141    #[serde(rename = "ISOLATED_MARGIN")]
142    IsolatedMargin,
143    #[serde(rename = "USDT_FUTURE")]
144    UsdtFuture,
145    #[serde(rename = "COIN_FUTURE")]
146    CoinFuture,
147}
148
149impl QueryManagedSubAccountTransferLogMasterAccountInvestorTransferFunctionAccountTypeEnum {
150    #[must_use]
151    pub fn as_str(&self) -> &'static str {
152        match self {
153            Self::Spot => "SPOT",
154            Self::Margin => "MARGIN",
155            Self::IsolatedMargin => "ISOLATED_MARGIN",
156            Self::UsdtFuture => "USDT_FUTURE",
157            Self::CoinFuture => "COIN_FUTURE",
158        }
159    }
160}
161
162impl std::str::FromStr
163    for QueryManagedSubAccountTransferLogMasterAccountInvestorTransferFunctionAccountTypeEnum
164{
165    type Err = Box<dyn std::error::Error + Send + Sync>;
166
167    fn from_str(s: &str) -> Result<Self, Self::Err> {
168        match s {
169            "SPOT" => Ok(Self::Spot),
170            "MARGIN" => Ok(Self::Margin),
171            "ISOLATED_MARGIN" => Ok(Self::IsolatedMargin),
172            "USDT_FUTURE" => Ok(Self::UsdtFuture),
173            "COIN_FUTURE" => Ok(Self::CoinFuture),
174            other  => Err(format!("invalid QueryManagedSubAccountTransferLogMasterAccountInvestorTransferFunctionAccountTypeEnum: {}", other).into()),
175        }
176    }
177}
178
179#[allow(non_camel_case_types)]
180#[derive(Debug, Clone, Serialize, Deserialize)]
181pub enum QueryManagedSubAccountTransferLogMasterAccountTradingTransferFunctionAccountTypeEnum {
182    #[serde(rename = "SPOT")]
183    Spot,
184    #[serde(rename = "MARGIN")]
185    Margin,
186    #[serde(rename = "ISOLATED_MARGIN")]
187    IsolatedMargin,
188    #[serde(rename = "USDT_FUTURE")]
189    UsdtFuture,
190    #[serde(rename = "COIN_FUTURE")]
191    CoinFuture,
192}
193
194impl QueryManagedSubAccountTransferLogMasterAccountTradingTransferFunctionAccountTypeEnum {
195    #[must_use]
196    pub fn as_str(&self) -> &'static str {
197        match self {
198            Self::Spot => "SPOT",
199            Self::Margin => "MARGIN",
200            Self::IsolatedMargin => "ISOLATED_MARGIN",
201            Self::UsdtFuture => "USDT_FUTURE",
202            Self::CoinFuture => "COIN_FUTURE",
203        }
204    }
205}
206
207impl std::str::FromStr
208    for QueryManagedSubAccountTransferLogMasterAccountTradingTransferFunctionAccountTypeEnum
209{
210    type Err = Box<dyn std::error::Error + Send + Sync>;
211
212    fn from_str(s: &str) -> Result<Self, Self::Err> {
213        match s {
214            "SPOT" => Ok(Self::Spot),
215            "MARGIN" => Ok(Self::Margin),
216            "ISOLATED_MARGIN" => Ok(Self::IsolatedMargin),
217            "USDT_FUTURE" => Ok(Self::UsdtFuture),
218            "COIN_FUTURE" => Ok(Self::CoinFuture),
219            other  => Err(format!("invalid QueryManagedSubAccountTransferLogMasterAccountTradingTransferFunctionAccountTypeEnum: {}", other).into()),
220        }
221    }
222}
223
224#[allow(non_camel_case_types)]
225#[derive(Debug, Clone, Serialize, Deserialize)]
226pub enum QueryManagedSubAccountTransferLogSubAccountTradingTransferFunctionAccountTypeEnum {
227    #[serde(rename = "SPOT")]
228    Spot,
229    #[serde(rename = "MARGIN")]
230    Margin,
231    #[serde(rename = "ISOLATED_MARGIN")]
232    IsolatedMargin,
233    #[serde(rename = "USDT_FUTURE")]
234    UsdtFuture,
235    #[serde(rename = "COIN_FUTURE")]
236    CoinFuture,
237}
238
239impl QueryManagedSubAccountTransferLogSubAccountTradingTransferFunctionAccountTypeEnum {
240    #[must_use]
241    pub fn as_str(&self) -> &'static str {
242        match self {
243            Self::Spot => "SPOT",
244            Self::Margin => "MARGIN",
245            Self::IsolatedMargin => "ISOLATED_MARGIN",
246            Self::UsdtFuture => "USDT_FUTURE",
247            Self::CoinFuture => "COIN_FUTURE",
248        }
249    }
250}
251
252impl std::str::FromStr
253    for QueryManagedSubAccountTransferLogSubAccountTradingTransferFunctionAccountTypeEnum
254{
255    type Err = Box<dyn std::error::Error + Send + Sync>;
256
257    fn from_str(s: &str) -> Result<Self, Self::Err> {
258        match s {
259            "SPOT" => Ok(Self::Spot),
260            "MARGIN" => Ok(Self::Margin),
261            "ISOLATED_MARGIN" => Ok(Self::IsolatedMargin),
262            "USDT_FUTURE" => Ok(Self::UsdtFuture),
263            "COIN_FUTURE" => Ok(Self::CoinFuture),
264            other  => Err(format!("invalid QueryManagedSubAccountTransferLogSubAccountTradingTransferFunctionAccountTypeEnum: {}", other).into()),
265        }
266    }
267}
268
269/// Request parameters for the [`deposit_assets_into_the_managed_sub_account`] operation.
270///
271/// This struct holds all of the inputs you can pass when calling
272/// [`deposit_assets_into_the_managed_sub_account`](#method.deposit_assets_into_the_managed_sub_account).
273#[derive(Clone, Debug, Builder, Deserialize)]
274#[builder(pattern = "owned", build_fn(error = "ParamBuildError"))]
275pub struct DepositAssetsIntoTheManagedSubAccountParams {
276    ///
277    /// The `to_email` parameter.
278    ///
279    /// This field is **required.
280    #[builder(setter(into))]
281    #[serde(rename = "toEmail")]
282    pub to_email: String,
283    ///
284    /// The `asset` parameter.
285    ///
286    /// This field is **required.
287    #[builder(setter(into))]
288    #[serde(rename = "asset")]
289    pub asset: String,
290    ///
291    /// The `amount` parameter.
292    ///
293    /// This field is **required.
294    #[builder(setter(into))]
295    #[serde(rename = "amount")]
296    pub amount: rust_decimal::Decimal,
297    ///
298    /// The `recv_window` parameter.
299    ///
300    /// This field is **optional.
301    #[builder(setter(into), default)]
302    #[serde(rename = "recvWindow", default)]
303    pub recv_window: Option<i64>,
304}
305
306impl DepositAssetsIntoTheManagedSubAccountParams {
307    /// Create a builder for [`deposit_assets_into_the_managed_sub_account`].
308    ///
309    /// Required parameters:
310    ///
311    /// * `to_email` — String
312    /// * `asset` — String
313    /// * `amount` — `rust_decimal::Decimal`
314    ///
315    #[must_use]
316    pub fn builder(
317        to_email: String,
318        asset: String,
319        amount: rust_decimal::Decimal,
320    ) -> DepositAssetsIntoTheManagedSubAccountParamsBuilder {
321        DepositAssetsIntoTheManagedSubAccountParamsBuilder::default()
322            .to_email(to_email)
323            .asset(asset)
324            .amount(amount)
325    }
326}
327/// Request parameters for the [`get_managed_sub_account_deposit_address`] operation.
328///
329/// This struct holds all of the inputs you can pass when calling
330/// [`get_managed_sub_account_deposit_address`](#method.get_managed_sub_account_deposit_address).
331#[derive(Clone, Debug, Builder, Deserialize)]
332#[builder(pattern = "owned", build_fn(error = "ParamBuildError"))]
333pub struct GetManagedSubAccountDepositAddressParams {
334    ///
335    /// The `email` parameter.
336    ///
337    /// This field is **required.
338    #[builder(setter(into))]
339    #[serde(rename = "email")]
340    pub email: String,
341    ///
342    /// The `coin` parameter.
343    ///
344    /// This field is **required.
345    #[builder(setter(into))]
346    #[serde(rename = "coin")]
347    pub coin: String,
348    /// networks can be found in `GET /sapi/v1/capital/deposit/address`
349    ///
350    /// This field is **optional.
351    #[builder(setter(into), default)]
352    #[serde(rename = "network", default)]
353    pub network: Option<String>,
354    ///
355    /// The `amount` parameter.
356    ///
357    /// This field is **optional.
358    #[builder(setter(into), default)]
359    #[serde(rename = "amount", default)]
360    pub amount: Option<rust_decimal::Decimal>,
361    ///
362    /// The `recv_window` parameter.
363    ///
364    /// This field is **optional.
365    #[builder(setter(into), default)]
366    #[serde(rename = "recvWindow", default)]
367    pub recv_window: Option<i64>,
368}
369
370impl GetManagedSubAccountDepositAddressParams {
371    /// Create a builder for [`get_managed_sub_account_deposit_address`].
372    ///
373    /// Required parameters:
374    ///
375    /// * `email` — String
376    /// * `coin` — String
377    ///
378    #[must_use]
379    pub fn builder(email: String, coin: String) -> GetManagedSubAccountDepositAddressParamsBuilder {
380        GetManagedSubAccountDepositAddressParamsBuilder::default()
381            .email(email)
382            .coin(coin)
383    }
384}
385/// Request parameters for the [`query_managed_sub_account_asset_details`] operation.
386///
387/// This struct holds all of the inputs you can pass when calling
388/// [`query_managed_sub_account_asset_details`](#method.query_managed_sub_account_asset_details).
389#[derive(Clone, Debug, Builder, Deserialize)]
390#[builder(pattern = "owned", build_fn(error = "ParamBuildError"))]
391pub struct QueryManagedSubAccountAssetDetailsParams {
392    ///
393    /// The `email` parameter.
394    ///
395    /// This field is **required.
396    #[builder(setter(into))]
397    #[serde(rename = "email")]
398    pub email: String,
399    ///
400    /// The `recv_window` parameter.
401    ///
402    /// This field is **optional.
403    #[builder(setter(into), default)]
404    #[serde(rename = "recvWindow", default)]
405    pub recv_window: Option<i64>,
406}
407
408impl QueryManagedSubAccountAssetDetailsParams {
409    /// Create a builder for [`query_managed_sub_account_asset_details`].
410    ///
411    /// Required parameters:
412    ///
413    /// * `email` — String
414    ///
415    #[must_use]
416    pub fn builder(email: String) -> QueryManagedSubAccountAssetDetailsParamsBuilder {
417        QueryManagedSubAccountAssetDetailsParamsBuilder::default().email(email)
418    }
419}
420/// Request parameters for the [`query_managed_sub_account_futures_asset_details`] operation.
421///
422/// This struct holds all of the inputs you can pass when calling
423/// [`query_managed_sub_account_futures_asset_details`](#method.query_managed_sub_account_futures_asset_details).
424#[derive(Clone, Debug, Builder, Deserialize)]
425#[builder(pattern = "owned", build_fn(error = "ParamBuildError"))]
426pub struct QueryManagedSubAccountFuturesAssetDetailsParams {
427    ///
428    /// The `email` parameter.
429    ///
430    /// This field is **required.
431    #[builder(setter(into))]
432    #[serde(rename = "email")]
433    pub email: String,
434    /// No input or input "`USDT_FUTURE`" to get UM Futures account details. Input "`COIN_FUTURE`" to get CM Futures account details.
435    ///
436    /// This field is **optional.
437    #[builder(setter(into), default)]
438    #[serde(rename = "accountType", default)]
439    pub account_type: Option<String>,
440}
441
442impl QueryManagedSubAccountFuturesAssetDetailsParams {
443    /// Create a builder for [`query_managed_sub_account_futures_asset_details`].
444    ///
445    /// Required parameters:
446    ///
447    /// * `email` — String
448    ///
449    #[must_use]
450    pub fn builder(email: String) -> QueryManagedSubAccountFuturesAssetDetailsParamsBuilder {
451        QueryManagedSubAccountFuturesAssetDetailsParamsBuilder::default().email(email)
452    }
453}
454/// Request parameters for the [`query_managed_sub_account_list`] operation.
455///
456/// This struct holds all of the inputs you can pass when calling
457/// [`query_managed_sub_account_list`](#method.query_managed_sub_account_list).
458#[derive(Clone, Debug, Builder, Deserialize, Default)]
459#[builder(pattern = "owned", build_fn(error = "ParamBuildError"))]
460pub struct QueryManagedSubAccountListParams {
461    ///
462    /// The `email` parameter.
463    ///
464    /// This field is **optional.
465    #[builder(setter(into), default)]
466    #[serde(rename = "email", default)]
467    pub email: Option<String>,
468    ///
469    /// The `page` parameter.
470    ///
471    /// This field is **optional.
472    #[builder(setter(into), default)]
473    #[serde(rename = "page", default)]
474    pub page: Option<i64>,
475    ///
476    /// The `limit` parameter.
477    ///
478    /// This field is **optional.
479    #[builder(setter(into), default)]
480    #[serde(rename = "limit", default)]
481    pub limit: Option<i64>,
482    ///
483    /// The `recv_window` parameter.
484    ///
485    /// This field is **optional.
486    #[builder(setter(into), default)]
487    #[serde(rename = "recvWindow", default)]
488    pub recv_window: Option<i64>,
489}
490
491impl QueryManagedSubAccountListParams {
492    /// Create a builder for [`query_managed_sub_account_list`].
493    ///
494    #[must_use]
495    pub fn builder() -> QueryManagedSubAccountListParamsBuilder {
496        QueryManagedSubAccountListParamsBuilder::default()
497    }
498}
499/// Request parameters for the [`query_managed_sub_account_margin_asset_details`] operation.
500///
501/// This struct holds all of the inputs you can pass when calling
502/// [`query_managed_sub_account_margin_asset_details`](#method.query_managed_sub_account_margin_asset_details).
503#[derive(Clone, Debug, Builder, Deserialize)]
504#[builder(pattern = "owned", build_fn(error = "ParamBuildError"))]
505pub struct QueryManagedSubAccountMarginAssetDetailsParams {
506    ///
507    /// The `email` parameter.
508    ///
509    /// This field is **required.
510    #[builder(setter(into))]
511    #[serde(rename = "email")]
512    pub email: String,
513    /// No input or input "MARGIN" to get Cross Margin account details. Input "`ISOLATED_MARGIN`" to get Isolated
514    /// Margin account details.
515    ///
516    /// This field is **optional.
517    #[builder(setter(into), default)]
518    #[serde(rename = "accountType", default)]
519    pub account_type: Option<String>,
520}
521
522impl QueryManagedSubAccountMarginAssetDetailsParams {
523    /// Create a builder for [`query_managed_sub_account_margin_asset_details`].
524    ///
525    /// Required parameters:
526    ///
527    /// * `email` — String
528    ///
529    #[must_use]
530    pub fn builder(email: String) -> QueryManagedSubAccountMarginAssetDetailsParamsBuilder {
531        QueryManagedSubAccountMarginAssetDetailsParamsBuilder::default().email(email)
532    }
533}
534/// Request parameters for the [`query_managed_sub_account_snapshot`] operation.
535///
536/// This struct holds all of the inputs you can pass when calling
537/// [`query_managed_sub_account_snapshot`](#method.query_managed_sub_account_snapshot).
538#[derive(Clone, Debug, Builder, Deserialize)]
539#[builder(pattern = "owned", build_fn(error = "ParamBuildError"))]
540pub struct QueryManagedSubAccountSnapshotParams {
541    ///
542    /// The `email` parameter.
543    ///
544    /// This field is **required.
545    #[builder(setter(into))]
546    #[serde(rename = "email")]
547    pub email: String,
548    ///
549    /// The `r#type` parameter.
550    ///
551    /// This field is **required.
552    #[builder(setter(into))]
553    #[serde(rename = "type")]
554    pub r#type: QueryManagedSubAccountSnapshotTypeEnum,
555    /// Query time range must be within 30 days and only supports data within the last month.
556    ///
557    /// This field is **optional.
558    #[builder(setter(into), default)]
559    #[serde(rename = "startTime", default)]
560    pub start_time: Option<i64>,
561    /// If both startTime and endTime are omitted, records from the last 7 days are returned by default.
562    ///
563    /// This field is **optional.
564    #[builder(setter(into), default)]
565    #[serde(rename = "endTime", default)]
566    pub end_time: Option<i64>,
567    ///
568    /// The `limit` parameter.
569    ///
570    /// This field is **optional.
571    #[builder(setter(into), default)]
572    #[serde(rename = "limit", default)]
573    pub limit: Option<i64>,
574    ///
575    /// The `recv_window` parameter.
576    ///
577    /// This field is **optional.
578    #[builder(setter(into), default)]
579    #[serde(rename = "recvWindow", default)]
580    pub recv_window: Option<i64>,
581}
582
583impl QueryManagedSubAccountSnapshotParams {
584    /// Create a builder for [`query_managed_sub_account_snapshot`].
585    ///
586    /// Required parameters:
587    ///
588    /// * `email` — String
589    /// * `r#type` — String
590    ///
591    #[must_use]
592    pub fn builder(
593        email: String,
594        r#type: QueryManagedSubAccountSnapshotTypeEnum,
595    ) -> QueryManagedSubAccountSnapshotParamsBuilder {
596        QueryManagedSubAccountSnapshotParamsBuilder::default()
597            .email(email)
598            .r#type(r#type)
599    }
600}
601/// Request parameters for the [`query_managed_sub_account_transfer_log_master_account_investor`] operation.
602///
603/// This struct holds all of the inputs you can pass when calling
604/// [`query_managed_sub_account_transfer_log_master_account_investor`](#method.query_managed_sub_account_transfer_log_master_account_investor).
605#[derive(Clone, Debug, Builder, Deserialize)]
606#[builder(pattern = "owned", build_fn(error = "ParamBuildError"))]
607pub struct QueryManagedSubAccountTransferLogMasterAccountInvestorParams {
608    ///
609    /// The `email` parameter.
610    ///
611    /// This field is **required.
612    #[builder(setter(into))]
613    #[serde(rename = "email")]
614    pub email: String,
615    /// Start Time
616    ///
617    /// This field is **required.
618    #[builder(setter(into))]
619    #[serde(rename = "startTime")]
620    pub start_time: i64,
621    /// End Time (The start time and end time interval cannot exceed half a year)
622    ///
623    /// This field is **required.
624    #[builder(setter(into))]
625    #[serde(rename = "endTime")]
626    pub end_time: i64,
627    /// Page
628    ///
629    /// This field is **required.
630    #[builder(setter(into))]
631    #[serde(rename = "page")]
632    pub page: i64,
633    ///
634    /// The `limit` parameter.
635    ///
636    /// This field is **required.
637    #[builder(setter(into))]
638    #[serde(rename = "limit")]
639    pub limit: i64,
640    /// Transfer Direction (FROM/TO)
641    ///
642    /// This field is **optional.
643    #[builder(setter(into), default)]
644    #[serde(rename = "transfers", default)]
645    pub transfers: Option<String>,
646    ///
647    /// The `transfer_function_account_type` parameter.
648    ///
649    /// This field is **optional.
650    #[builder(setter(into), default)]
651    #[serde(rename = "transferFunctionAccountType", default)]
652    pub transfer_function_account_type: Option<
653        QueryManagedSubAccountTransferLogMasterAccountInvestorTransferFunctionAccountTypeEnum,
654    >,
655}
656
657impl QueryManagedSubAccountTransferLogMasterAccountInvestorParams {
658    /// Create a builder for [`query_managed_sub_account_transfer_log_master_account_investor`].
659    ///
660    /// Required parameters:
661    ///
662    /// * `email` — String
663    /// * `start_time` — Start Time
664    /// * `end_time` — End Time (The start time and end time interval cannot exceed half a year)
665    /// * `page` — Page
666    /// * `limit` — i64
667    ///
668    #[must_use]
669    pub fn builder(
670        email: String,
671        start_time: i64,
672        end_time: i64,
673        page: i64,
674        limit: i64,
675    ) -> QueryManagedSubAccountTransferLogMasterAccountInvestorParamsBuilder {
676        QueryManagedSubAccountTransferLogMasterAccountInvestorParamsBuilder::default()
677            .email(email)
678            .start_time(start_time)
679            .end_time(end_time)
680            .page(page)
681            .limit(limit)
682    }
683}
684/// Request parameters for the [`query_managed_sub_account_transfer_log_master_account_trading`] operation.
685///
686/// This struct holds all of the inputs you can pass when calling
687/// [`query_managed_sub_account_transfer_log_master_account_trading`](#method.query_managed_sub_account_transfer_log_master_account_trading).
688#[derive(Clone, Debug, Builder, Deserialize)]
689#[builder(pattern = "owned", build_fn(error = "ParamBuildError"))]
690pub struct QueryManagedSubAccountTransferLogMasterAccountTradingParams {
691    ///
692    /// The `email` parameter.
693    ///
694    /// This field is **required.
695    #[builder(setter(into))]
696    #[serde(rename = "email")]
697    pub email: String,
698    /// Start Time
699    ///
700    /// This field is **required.
701    #[builder(setter(into))]
702    #[serde(rename = "startTime")]
703    pub start_time: i64,
704    /// End Time (The start time and end time interval cannot exceed half a year)
705    ///
706    /// This field is **required.
707    #[builder(setter(into))]
708    #[serde(rename = "endTime")]
709    pub end_time: i64,
710    ///
711    /// The `page` parameter.
712    ///
713    /// This field is **required.
714    #[builder(setter(into))]
715    #[serde(rename = "page")]
716    pub page: i64,
717    ///
718    /// The `limit` parameter.
719    ///
720    /// This field is **required.
721    #[builder(setter(into))]
722    #[serde(rename = "limit")]
723    pub limit: i64,
724    /// Transfer Direction (FROM/TO)
725    ///
726    /// This field is **optional.
727    #[builder(setter(into), default)]
728    #[serde(rename = "transfers", default)]
729    pub transfers: Option<String>,
730    ///
731    /// The `transfer_function_account_type` parameter.
732    ///
733    /// This field is **optional.
734    #[builder(setter(into), default)]
735    #[serde(rename = "transferFunctionAccountType", default)]
736    pub transfer_function_account_type: Option<
737        QueryManagedSubAccountTransferLogMasterAccountTradingTransferFunctionAccountTypeEnum,
738    >,
739}
740
741impl QueryManagedSubAccountTransferLogMasterAccountTradingParams {
742    /// Create a builder for [`query_managed_sub_account_transfer_log_master_account_trading`].
743    ///
744    /// Required parameters:
745    ///
746    /// * `email` — String
747    /// * `start_time` — Start Time
748    /// * `end_time` — End Time (The start time and end time interval cannot exceed half a year)
749    /// * `page` — i64
750    /// * `limit` — i64
751    ///
752    #[must_use]
753    pub fn builder(
754        email: String,
755        start_time: i64,
756        end_time: i64,
757        page: i64,
758        limit: i64,
759    ) -> QueryManagedSubAccountTransferLogMasterAccountTradingParamsBuilder {
760        QueryManagedSubAccountTransferLogMasterAccountTradingParamsBuilder::default()
761            .email(email)
762            .start_time(start_time)
763            .end_time(end_time)
764            .page(page)
765            .limit(limit)
766    }
767}
768/// Request parameters for the [`query_managed_sub_account_transfer_log_sub_account_trading`] operation.
769///
770/// This struct holds all of the inputs you can pass when calling
771/// [`query_managed_sub_account_transfer_log_sub_account_trading`](#method.query_managed_sub_account_transfer_log_sub_account_trading).
772#[derive(Clone, Debug, Builder, Deserialize)]
773#[builder(pattern = "owned", build_fn(error = "ParamBuildError"))]
774pub struct QueryManagedSubAccountTransferLogSubAccountTradingParams {
775    /// Start Time
776    ///
777    /// This field is **required.
778    #[builder(setter(into))]
779    #[serde(rename = "startTime")]
780    pub start_time: i64,
781    /// End Time (The start time and end time interval cannot exceed half a year)
782    ///
783    /// This field is **required.
784    #[builder(setter(into))]
785    #[serde(rename = "endTime")]
786    pub end_time: i64,
787    ///
788    /// The `page` parameter.
789    ///
790    /// This field is **required.
791    #[builder(setter(into))]
792    #[serde(rename = "page")]
793    pub page: i64,
794    ///
795    /// The `limit` parameter.
796    ///
797    /// This field is **required.
798    #[builder(setter(into))]
799    #[serde(rename = "limit")]
800    pub limit: i64,
801    /// Transfer Direction (from/to)
802    ///
803    /// This field is **optional.
804    #[builder(setter(into), default)]
805    #[serde(rename = "transfers", default)]
806    pub transfers: Option<String>,
807    ///
808    /// The `transfer_function_account_type` parameter.
809    ///
810    /// This field is **optional.
811    #[builder(setter(into), default)]
812    #[serde(rename = "transferFunctionAccountType", default)]
813    pub transfer_function_account_type:
814        Option<QueryManagedSubAccountTransferLogSubAccountTradingTransferFunctionAccountTypeEnum>,
815    ///
816    /// The `recv_window` parameter.
817    ///
818    /// This field is **optional.
819    #[builder(setter(into), default)]
820    #[serde(rename = "recvWindow", default)]
821    pub recv_window: Option<i64>,
822}
823
824impl QueryManagedSubAccountTransferLogSubAccountTradingParams {
825    /// Create a builder for [`query_managed_sub_account_transfer_log_sub_account_trading`].
826    ///
827    /// Required parameters:
828    ///
829    /// * `start_time` — Start Time
830    /// * `end_time` — End Time (The start time and end time interval cannot exceed half a year)
831    /// * `page` — i64
832    /// * `limit` — i64
833    ///
834    #[must_use]
835    pub fn builder(
836        start_time: i64,
837        end_time: i64,
838        page: i64,
839        limit: i64,
840    ) -> QueryManagedSubAccountTransferLogSubAccountTradingParamsBuilder {
841        QueryManagedSubAccountTransferLogSubAccountTradingParamsBuilder::default()
842            .start_time(start_time)
843            .end_time(end_time)
844            .page(page)
845            .limit(limit)
846    }
847}
848/// Request parameters for the [`withdrawl_assets_from_the_managed_sub_account`] operation.
849///
850/// This struct holds all of the inputs you can pass when calling
851/// [`withdrawl_assets_from_the_managed_sub_account`](#method.withdrawl_assets_from_the_managed_sub_account).
852#[derive(Clone, Debug, Builder, Deserialize)]
853#[builder(pattern = "owned", build_fn(error = "ParamBuildError"))]
854pub struct WithdrawlAssetsFromTheManagedSubAccountParams {
855    ///
856    /// The `from_email` parameter.
857    ///
858    /// This field is **required.
859    #[builder(setter(into))]
860    #[serde(rename = "fromEmail")]
861    pub from_email: String,
862    ///
863    /// The `asset` parameter.
864    ///
865    /// This field is **required.
866    #[builder(setter(into))]
867    #[serde(rename = "asset")]
868    pub asset: String,
869    ///
870    /// The `amount` parameter.
871    ///
872    /// This field is **required.
873    #[builder(setter(into))]
874    #[serde(rename = "amount")]
875    pub amount: rust_decimal::Decimal,
876    /// Withdrawal will happen automatically on the selected date (UTC 0). If no date is selected,
877    /// withdrawal takes effect immediately.
878    ///
879    /// This field is **optional.
880    #[builder(setter(into), default)]
881    #[serde(rename = "transferDate", default)]
882    pub transfer_date: Option<i64>,
883    ///
884    /// The `recv_window` parameter.
885    ///
886    /// This field is **optional.
887    #[builder(setter(into), default)]
888    #[serde(rename = "recvWindow", default)]
889    pub recv_window: Option<i64>,
890}
891
892impl WithdrawlAssetsFromTheManagedSubAccountParams {
893    /// Create a builder for [`withdrawl_assets_from_the_managed_sub_account`].
894    ///
895    /// Required parameters:
896    ///
897    /// * `from_email` — String
898    /// * `asset` — String
899    /// * `amount` — `rust_decimal::Decimal`
900    ///
901    #[must_use]
902    pub fn builder(
903        from_email: String,
904        asset: String,
905        amount: rust_decimal::Decimal,
906    ) -> WithdrawlAssetsFromTheManagedSubAccountParamsBuilder {
907        WithdrawlAssetsFromTheManagedSubAccountParamsBuilder::default()
908            .from_email(from_email)
909            .asset(asset)
910            .amount(amount)
911    }
912}
913
914#[async_trait]
915impl ManagedSubAccountApi for ManagedSubAccountApiClient {
916    async fn deposit_assets_into_the_managed_sub_account(
917        &self,
918        params: DepositAssetsIntoTheManagedSubAccountParams,
919    ) -> anyhow::Result<RestApiResponse<models::DepositAssetsIntoTheManagedSubAccountResponse>>
920    {
921        let DepositAssetsIntoTheManagedSubAccountParams {
922            to_email,
923            asset,
924            amount,
925            recv_window,
926        } = params;
927
928        let mut query_params = BTreeMap::new();
929        let body_params = BTreeMap::new();
930
931        query_params.insert("toEmail".to_string(), json!(to_email));
932
933        query_params.insert("asset".to_string(), json!(asset));
934
935        query_params.insert("amount".to_string(), json!(amount));
936
937        if let Some(rw) = recv_window {
938            query_params.insert("recvWindow".to_string(), json!(rw));
939        }
940
941        send_request::<models::DepositAssetsIntoTheManagedSubAccountResponse>(
942            &self.configuration,
943            "/sapi/v1/managed-subaccount/deposit",
944            reqwest::Method::POST,
945            query_params,
946            body_params,
947            if HAS_TIME_UNIT {
948                self.configuration.time_unit
949            } else {
950                None
951            },
952            true,
953        )
954        .await
955    }
956
957    async fn get_managed_sub_account_deposit_address(
958        &self,
959        params: GetManagedSubAccountDepositAddressParams,
960    ) -> anyhow::Result<RestApiResponse<models::GetManagedSubAccountDepositAddressResponse>> {
961        let GetManagedSubAccountDepositAddressParams {
962            email,
963            coin,
964            network,
965            amount,
966            recv_window,
967        } = params;
968
969        let mut query_params = BTreeMap::new();
970        let body_params = BTreeMap::new();
971
972        query_params.insert("email".to_string(), json!(email));
973
974        query_params.insert("coin".to_string(), json!(coin));
975
976        if let Some(rw) = network {
977            query_params.insert("network".to_string(), json!(rw));
978        }
979
980        if let Some(rw) = amount {
981            query_params.insert("amount".to_string(), json!(rw));
982        }
983
984        if let Some(rw) = recv_window {
985            query_params.insert("recvWindow".to_string(), json!(rw));
986        }
987
988        send_request::<models::GetManagedSubAccountDepositAddressResponse>(
989            &self.configuration,
990            "/sapi/v1/managed-subaccount/deposit/address",
991            reqwest::Method::GET,
992            query_params,
993            body_params,
994            if HAS_TIME_UNIT {
995                self.configuration.time_unit
996            } else {
997                None
998            },
999            true,
1000        )
1001        .await
1002    }
1003
1004    async fn query_managed_sub_account_asset_details(
1005        &self,
1006        params: QueryManagedSubAccountAssetDetailsParams,
1007    ) -> anyhow::Result<RestApiResponse<Vec<models::QueryManagedSubAccountAssetDetailsResponseInner>>>
1008    {
1009        let QueryManagedSubAccountAssetDetailsParams { email, recv_window } = params;
1010
1011        let mut query_params = BTreeMap::new();
1012        let body_params = BTreeMap::new();
1013
1014        query_params.insert("email".to_string(), json!(email));
1015
1016        if let Some(rw) = recv_window {
1017            query_params.insert("recvWindow".to_string(), json!(rw));
1018        }
1019
1020        send_request::<Vec<models::QueryManagedSubAccountAssetDetailsResponseInner>>(
1021            &self.configuration,
1022            "/sapi/v1/managed-subaccount/asset",
1023            reqwest::Method::GET,
1024            query_params,
1025            body_params,
1026            if HAS_TIME_UNIT {
1027                self.configuration.time_unit
1028            } else {
1029                None
1030            },
1031            true,
1032        )
1033        .await
1034    }
1035
1036    async fn query_managed_sub_account_futures_asset_details(
1037        &self,
1038        params: QueryManagedSubAccountFuturesAssetDetailsParams,
1039    ) -> anyhow::Result<RestApiResponse<models::QueryManagedSubAccountFuturesAssetDetailsResponse>>
1040    {
1041        let QueryManagedSubAccountFuturesAssetDetailsParams {
1042            email,
1043            account_type,
1044        } = params;
1045
1046        let mut query_params = BTreeMap::new();
1047        let body_params = BTreeMap::new();
1048
1049        query_params.insert("email".to_string(), json!(email));
1050
1051        if let Some(rw) = account_type {
1052            query_params.insert("accountType".to_string(), json!(rw));
1053        }
1054
1055        send_request::<models::QueryManagedSubAccountFuturesAssetDetailsResponse>(
1056            &self.configuration,
1057            "/sapi/v1/managed-subaccount/fetch-future-asset",
1058            reqwest::Method::GET,
1059            query_params,
1060            body_params,
1061            if HAS_TIME_UNIT {
1062                self.configuration.time_unit
1063            } else {
1064                None
1065            },
1066            true,
1067        )
1068        .await
1069    }
1070
1071    async fn query_managed_sub_account_list(
1072        &self,
1073        params: QueryManagedSubAccountListParams,
1074    ) -> anyhow::Result<RestApiResponse<models::QueryManagedSubAccountListResponse>> {
1075        let QueryManagedSubAccountListParams {
1076            email,
1077            page,
1078            limit,
1079            recv_window,
1080        } = params;
1081
1082        let mut query_params = BTreeMap::new();
1083        let body_params = BTreeMap::new();
1084
1085        if let Some(rw) = email {
1086            query_params.insert("email".to_string(), json!(rw));
1087        }
1088
1089        if let Some(rw) = page {
1090            query_params.insert("page".to_string(), json!(rw));
1091        }
1092
1093        if let Some(rw) = limit {
1094            query_params.insert("limit".to_string(), json!(rw));
1095        }
1096
1097        if let Some(rw) = recv_window {
1098            query_params.insert("recvWindow".to_string(), json!(rw));
1099        }
1100
1101        send_request::<models::QueryManagedSubAccountListResponse>(
1102            &self.configuration,
1103            "/sapi/v1/managed-subaccount/info",
1104            reqwest::Method::GET,
1105            query_params,
1106            body_params,
1107            if HAS_TIME_UNIT {
1108                self.configuration.time_unit
1109            } else {
1110                None
1111            },
1112            true,
1113        )
1114        .await
1115    }
1116
1117    async fn query_managed_sub_account_margin_asset_details(
1118        &self,
1119        params: QueryManagedSubAccountMarginAssetDetailsParams,
1120    ) -> anyhow::Result<RestApiResponse<models::QueryManagedSubAccountMarginAssetDetailsResponse>>
1121    {
1122        let QueryManagedSubAccountMarginAssetDetailsParams {
1123            email,
1124            account_type,
1125        } = params;
1126
1127        let mut query_params = BTreeMap::new();
1128        let body_params = BTreeMap::new();
1129
1130        query_params.insert("email".to_string(), json!(email));
1131
1132        if let Some(rw) = account_type {
1133            query_params.insert("accountType".to_string(), json!(rw));
1134        }
1135
1136        send_request::<models::QueryManagedSubAccountMarginAssetDetailsResponse>(
1137            &self.configuration,
1138            "/sapi/v1/managed-subaccount/marginAsset",
1139            reqwest::Method::GET,
1140            query_params,
1141            body_params,
1142            if HAS_TIME_UNIT {
1143                self.configuration.time_unit
1144            } else {
1145                None
1146            },
1147            true,
1148        )
1149        .await
1150    }
1151
1152    async fn query_managed_sub_account_snapshot(
1153        &self,
1154        params: QueryManagedSubAccountSnapshotParams,
1155    ) -> anyhow::Result<RestApiResponse<models::QueryManagedSubAccountSnapshotResponse>> {
1156        let QueryManagedSubAccountSnapshotParams {
1157            email,
1158            r#type,
1159            start_time,
1160            end_time,
1161            limit,
1162            recv_window,
1163        } = params;
1164
1165        let mut query_params = BTreeMap::new();
1166        let body_params = BTreeMap::new();
1167
1168        query_params.insert("email".to_string(), json!(email));
1169
1170        query_params.insert("type".to_string(), json!(r#type));
1171
1172        if let Some(rw) = start_time {
1173            query_params.insert("startTime".to_string(), json!(rw));
1174        }
1175
1176        if let Some(rw) = end_time {
1177            query_params.insert("endTime".to_string(), json!(rw));
1178        }
1179
1180        if let Some(rw) = limit {
1181            query_params.insert("limit".to_string(), json!(rw));
1182        }
1183
1184        if let Some(rw) = recv_window {
1185            query_params.insert("recvWindow".to_string(), json!(rw));
1186        }
1187
1188        send_request::<models::QueryManagedSubAccountSnapshotResponse>(
1189            &self.configuration,
1190            "/sapi/v1/managed-subaccount/accountSnapshot",
1191            reqwest::Method::GET,
1192            query_params,
1193            body_params,
1194            if HAS_TIME_UNIT {
1195                self.configuration.time_unit
1196            } else {
1197                None
1198            },
1199            true,
1200        )
1201        .await
1202    }
1203
1204    async fn query_managed_sub_account_transfer_log_master_account_investor(
1205        &self,
1206        params: QueryManagedSubAccountTransferLogMasterAccountInvestorParams,
1207    ) -> anyhow::Result<
1208        RestApiResponse<models::QueryManagedSubAccountTransferLogMasterAccountInvestorResponse>,
1209    > {
1210        let QueryManagedSubAccountTransferLogMasterAccountInvestorParams {
1211            email,
1212            start_time,
1213            end_time,
1214            page,
1215            limit,
1216            transfers,
1217            transfer_function_account_type,
1218        } = params;
1219
1220        let mut query_params = BTreeMap::new();
1221        let body_params = BTreeMap::new();
1222
1223        query_params.insert("email".to_string(), json!(email));
1224
1225        query_params.insert("startTime".to_string(), json!(start_time));
1226
1227        query_params.insert("endTime".to_string(), json!(end_time));
1228
1229        query_params.insert("page".to_string(), json!(page));
1230
1231        query_params.insert("limit".to_string(), json!(limit));
1232
1233        if let Some(rw) = transfers {
1234            query_params.insert("transfers".to_string(), json!(rw));
1235        }
1236
1237        if let Some(rw) = transfer_function_account_type {
1238            query_params.insert("transferFunctionAccountType".to_string(), json!(rw));
1239        }
1240
1241        send_request::<models::QueryManagedSubAccountTransferLogMasterAccountInvestorResponse>(
1242            &self.configuration,
1243            "/sapi/v1/managed-subaccount/queryTransLogForInvestor",
1244            reqwest::Method::GET,
1245            query_params,
1246            body_params,
1247            if HAS_TIME_UNIT {
1248                self.configuration.time_unit
1249            } else {
1250                None
1251            },
1252            true,
1253        )
1254        .await
1255    }
1256
1257    async fn query_managed_sub_account_transfer_log_master_account_trading(
1258        &self,
1259        params: QueryManagedSubAccountTransferLogMasterAccountTradingParams,
1260    ) -> anyhow::Result<
1261        RestApiResponse<models::QueryManagedSubAccountTransferLogMasterAccountTradingResponse>,
1262    > {
1263        let QueryManagedSubAccountTransferLogMasterAccountTradingParams {
1264            email,
1265            start_time,
1266            end_time,
1267            page,
1268            limit,
1269            transfers,
1270            transfer_function_account_type,
1271        } = params;
1272
1273        let mut query_params = BTreeMap::new();
1274        let body_params = BTreeMap::new();
1275
1276        query_params.insert("email".to_string(), json!(email));
1277
1278        query_params.insert("startTime".to_string(), json!(start_time));
1279
1280        query_params.insert("endTime".to_string(), json!(end_time));
1281
1282        query_params.insert("page".to_string(), json!(page));
1283
1284        query_params.insert("limit".to_string(), json!(limit));
1285
1286        if let Some(rw) = transfers {
1287            query_params.insert("transfers".to_string(), json!(rw));
1288        }
1289
1290        if let Some(rw) = transfer_function_account_type {
1291            query_params.insert("transferFunctionAccountType".to_string(), json!(rw));
1292        }
1293
1294        send_request::<models::QueryManagedSubAccountTransferLogMasterAccountTradingResponse>(
1295            &self.configuration,
1296            "/sapi/v1/managed-subaccount/queryTransLogForTradeParent",
1297            reqwest::Method::GET,
1298            query_params,
1299            body_params,
1300            if HAS_TIME_UNIT {
1301                self.configuration.time_unit
1302            } else {
1303                None
1304            },
1305            true,
1306        )
1307        .await
1308    }
1309
1310    async fn query_managed_sub_account_transfer_log_sub_account_trading(
1311        &self,
1312        params: QueryManagedSubAccountTransferLogSubAccountTradingParams,
1313    ) -> anyhow::Result<
1314        RestApiResponse<models::QueryManagedSubAccountTransferLogSubAccountTradingResponse>,
1315    > {
1316        let QueryManagedSubAccountTransferLogSubAccountTradingParams {
1317            start_time,
1318            end_time,
1319            page,
1320            limit,
1321            transfers,
1322            transfer_function_account_type,
1323            recv_window,
1324        } = params;
1325
1326        let mut query_params = BTreeMap::new();
1327        let body_params = BTreeMap::new();
1328
1329        query_params.insert("startTime".to_string(), json!(start_time));
1330
1331        query_params.insert("endTime".to_string(), json!(end_time));
1332
1333        query_params.insert("page".to_string(), json!(page));
1334
1335        query_params.insert("limit".to_string(), json!(limit));
1336
1337        if let Some(rw) = transfers {
1338            query_params.insert("transfers".to_string(), json!(rw));
1339        }
1340
1341        if let Some(rw) = transfer_function_account_type {
1342            query_params.insert("transferFunctionAccountType".to_string(), json!(rw));
1343        }
1344
1345        if let Some(rw) = recv_window {
1346            query_params.insert("recvWindow".to_string(), json!(rw));
1347        }
1348
1349        send_request::<models::QueryManagedSubAccountTransferLogSubAccountTradingResponse>(
1350            &self.configuration,
1351            "/sapi/v1/managed-subaccount/query-trans-log",
1352            reqwest::Method::GET,
1353            query_params,
1354            body_params,
1355            if HAS_TIME_UNIT {
1356                self.configuration.time_unit
1357            } else {
1358                None
1359            },
1360            true,
1361        )
1362        .await
1363    }
1364
1365    async fn withdrawl_assets_from_the_managed_sub_account(
1366        &self,
1367        params: WithdrawlAssetsFromTheManagedSubAccountParams,
1368    ) -> anyhow::Result<RestApiResponse<models::WithdrawlAssetsFromTheManagedSubAccountResponse>>
1369    {
1370        let WithdrawlAssetsFromTheManagedSubAccountParams {
1371            from_email,
1372            asset,
1373            amount,
1374            transfer_date,
1375            recv_window,
1376        } = params;
1377
1378        let mut query_params = BTreeMap::new();
1379        let body_params = BTreeMap::new();
1380
1381        query_params.insert("fromEmail".to_string(), json!(from_email));
1382
1383        query_params.insert("asset".to_string(), json!(asset));
1384
1385        query_params.insert("amount".to_string(), json!(amount));
1386
1387        if let Some(rw) = transfer_date {
1388            query_params.insert("transferDate".to_string(), json!(rw));
1389        }
1390
1391        if let Some(rw) = recv_window {
1392            query_params.insert("recvWindow".to_string(), json!(rw));
1393        }
1394
1395        send_request::<models::WithdrawlAssetsFromTheManagedSubAccountResponse>(
1396            &self.configuration,
1397            "/sapi/v1/managed-subaccount/withdraw",
1398            reqwest::Method::POST,
1399            query_params,
1400            body_params,
1401            if HAS_TIME_UNIT {
1402                self.configuration.time_unit
1403            } else {
1404                None
1405            },
1406            true,
1407        )
1408        .await
1409    }
1410}
1411
1412#[cfg(all(test, feature = "sub_account"))]
1413mod tests {
1414    use super::*;
1415    use crate::TOKIO_SHARED_RT;
1416    use crate::{errors::ConnectorError, models::DataFuture, models::RestApiRateLimit};
1417    use async_trait::async_trait;
1418    use std::collections::HashMap;
1419
1420    struct DummyRestApiResponse<T> {
1421        inner: Box<dyn FnOnce() -> DataFuture<Result<T, ConnectorError>> + Send + Sync>,
1422        status: u16,
1423        headers: HashMap<String, String>,
1424        rate_limits: Option<Vec<RestApiRateLimit>>,
1425    }
1426
1427    impl<T> From<DummyRestApiResponse<T>> for RestApiResponse<T> {
1428        fn from(dummy: DummyRestApiResponse<T>) -> Self {
1429            Self {
1430                data_fn: dummy.inner,
1431                status: dummy.status,
1432                headers: dummy.headers,
1433                rate_limits: dummy.rate_limits,
1434            }
1435        }
1436    }
1437
1438    struct MockManagedSubAccountApiClient {
1439        force_error: bool,
1440    }
1441
1442    #[async_trait]
1443    impl ManagedSubAccountApi for MockManagedSubAccountApiClient {
1444        async fn deposit_assets_into_the_managed_sub_account(
1445            &self,
1446            _params: DepositAssetsIntoTheManagedSubAccountParams,
1447        ) -> anyhow::Result<RestApiResponse<models::DepositAssetsIntoTheManagedSubAccountResponse>>
1448        {
1449            if self.force_error {
1450                return Err(ConnectorError::ConnectorClientError {
1451                    msg: "ResponseError".to_string(),
1452                    code: None,
1453                }
1454                .into());
1455            }
1456
1457            let resp_json: Value = serde_json::from_str(r#"{"tranId":66157362489}"#)
1458                .unwrap_or_else(|_| serde_json::json!({}));
1459            let dummy_response: models::DepositAssetsIntoTheManagedSubAccountResponse =
1460                serde_json::from_value(resp_json.clone()).expect(
1461                    "should parse into models::DepositAssetsIntoTheManagedSubAccountResponse",
1462                );
1463
1464            let dummy = DummyRestApiResponse {
1465                inner: Box::new(move || Box::pin(async move { Ok(dummy_response) })),
1466                status: 200,
1467                headers: HashMap::new(),
1468                rate_limits: None,
1469            };
1470
1471            Ok(dummy.into())
1472        }
1473
1474        async fn get_managed_sub_account_deposit_address(
1475            &self,
1476            _params: GetManagedSubAccountDepositAddressParams,
1477        ) -> anyhow::Result<RestApiResponse<models::GetManagedSubAccountDepositAddressResponse>>
1478        {
1479            if self.force_error {
1480                return Err(ConnectorError::ConnectorClientError {
1481                    msg: "ResponseError".to_string(),
1482                    code: None,
1483                }
1484                .into());
1485            }
1486
1487            let resp_json: Value = serde_json::from_str(r#"{"coin":"USDT","address":"0x206c22d833bb0bb2102da6b7c7d4c3eb14bcf73d","tag":"","url":"https://etherscan.io/address/0x206c22d833bb0bb2102da6b7c7d4c3eb14bcf73d"}"#).unwrap_or_else(|_| serde_json::json!({}));
1488            let dummy_response: models::GetManagedSubAccountDepositAddressResponse =
1489                serde_json::from_value(resp_json.clone())
1490                    .expect("should parse into models::GetManagedSubAccountDepositAddressResponse");
1491
1492            let dummy = DummyRestApiResponse {
1493                inner: Box::new(move || Box::pin(async move { Ok(dummy_response) })),
1494                status: 200,
1495                headers: HashMap::new(),
1496                rate_limits: None,
1497            };
1498
1499            Ok(dummy.into())
1500        }
1501
1502        async fn query_managed_sub_account_asset_details(
1503            &self,
1504            _params: QueryManagedSubAccountAssetDetailsParams,
1505        ) -> anyhow::Result<
1506            RestApiResponse<Vec<models::QueryManagedSubAccountAssetDetailsResponseInner>>,
1507        > {
1508            if self.force_error {
1509                return Err(ConnectorError::ConnectorClientError {
1510                    msg: "ResponseError".to_string(),
1511                    code: None,
1512                }
1513                .into());
1514            }
1515
1516            let resp_json: Value = serde_json::from_str(r#"[{"coin":"INJ","name":"Injective Protocol","totalBalance":"0","availableBalance":"0","inOrder":"0","btcValue":"0"}]"#).unwrap_or_else(|_| serde_json::json!({}));
1517            let dummy_response : Vec<models::QueryManagedSubAccountAssetDetailsResponseInner> = serde_json::from_value(resp_json.clone()).expect("should parse into Vec<models::QueryManagedSubAccountAssetDetailsResponseInner>");
1518
1519            let dummy = DummyRestApiResponse {
1520                inner: Box::new(move || Box::pin(async move { Ok(dummy_response) })),
1521                status: 200,
1522                headers: HashMap::new(),
1523                rate_limits: None,
1524            };
1525
1526            Ok(dummy.into())
1527        }
1528
1529        async fn query_managed_sub_account_futures_asset_details(
1530            &self,
1531            _params: QueryManagedSubAccountFuturesAssetDetailsParams,
1532        ) -> anyhow::Result<
1533            RestApiResponse<models::QueryManagedSubAccountFuturesAssetDetailsResponse>,
1534        > {
1535            if self.force_error {
1536                return Err(ConnectorError::ConnectorClientError {
1537                    msg: "ResponseError".to_string(),
1538                    code: None,
1539                }
1540                .into());
1541            }
1542
1543            let resp_json: Value = serde_json::from_str(r#"{"code":"200","message":"OK","snapshotVos":[{"type":"FUTURES","updateTime":1672893855394,"data":{"assets":[{"asset":"USDT","marginBalance":100,"walletBalance":120}],"position":[{"symbol":"BTCUSDT","entryPrice":17000,"markPrice":17000,"positionAmt":1.0E-4}]}}]}"#).unwrap_or_else(|_| serde_json::json!({}));
1544            let dummy_response: models::QueryManagedSubAccountFuturesAssetDetailsResponse =
1545                serde_json::from_value(resp_json.clone()).expect(
1546                    "should parse into models::QueryManagedSubAccountFuturesAssetDetailsResponse",
1547                );
1548
1549            let dummy = DummyRestApiResponse {
1550                inner: Box::new(move || Box::pin(async move { Ok(dummy_response) })),
1551                status: 200,
1552                headers: HashMap::new(),
1553                rate_limits: None,
1554            };
1555
1556            Ok(dummy.into())
1557        }
1558
1559        async fn query_managed_sub_account_list(
1560            &self,
1561            _params: QueryManagedSubAccountListParams,
1562        ) -> anyhow::Result<RestApiResponse<models::QueryManagedSubAccountListResponse>> {
1563            if self.force_error {
1564                return Err(ConnectorError::ConnectorClientError {
1565                    msg: "ResponseError".to_string(),
1566                    code: None,
1567                }
1568                .into());
1569            }
1570
1571            let resp_json: Value = serde_json::from_str(r#"{"total":3,"managerSubUserInfoVoList":[{"rootUserId":1000138475670,"managersubUserId":1000137842513,"bindParentUserId":1000138475669,"email":"test_0_virtual@kq3kno9imanagedsub.com","insertTimeStamp":1678435149000,"bindParentEmail":"wdyw8xsh8pey@test.com","isSubUserEnabled":true,"isUserActive":true,"isMarginEnabled":false,"isFutureEnabled":false,"isSignedLVTRiskAgreement":false}]}"#).unwrap_or_else(|_| serde_json::json!({}));
1572            let dummy_response: models::QueryManagedSubAccountListResponse =
1573                serde_json::from_value(resp_json.clone())
1574                    .expect("should parse into models::QueryManagedSubAccountListResponse");
1575
1576            let dummy = DummyRestApiResponse {
1577                inner: Box::new(move || Box::pin(async move { Ok(dummy_response) })),
1578                status: 200,
1579                headers: HashMap::new(),
1580                rate_limits: None,
1581            };
1582
1583            Ok(dummy.into())
1584        }
1585
1586        async fn query_managed_sub_account_margin_asset_details(
1587            &self,
1588            _params: QueryManagedSubAccountMarginAssetDetailsParams,
1589        ) -> anyhow::Result<RestApiResponse<models::QueryManagedSubAccountMarginAssetDetailsResponse>>
1590        {
1591            if self.force_error {
1592                return Err(ConnectorError::ConnectorClientError {
1593                    msg: "ResponseError".to_string(),
1594                    code: None,
1595                }
1596                .into());
1597            }
1598
1599            let resp_json: Value = serde_json::from_str(r#"{"marginLevel":"999","totalAssetOfBtc":"0","totalLiabilityOfBtc":"0","totalNetAssetOfBtc":"0","userAssets":[{"asset":"MATIC","borrowed":"0","free":"0","interest":"0","locked":"0","netAsset":"0"}]}"#).unwrap_or_else(|_| serde_json::json!({}));
1600            let dummy_response: models::QueryManagedSubAccountMarginAssetDetailsResponse =
1601                serde_json::from_value(resp_json.clone()).expect(
1602                    "should parse into models::QueryManagedSubAccountMarginAssetDetailsResponse",
1603                );
1604
1605            let dummy = DummyRestApiResponse {
1606                inner: Box::new(move || Box::pin(async move { Ok(dummy_response) })),
1607                status: 200,
1608                headers: HashMap::new(),
1609                rate_limits: None,
1610            };
1611
1612            Ok(dummy.into())
1613        }
1614
1615        async fn query_managed_sub_account_snapshot(
1616            &self,
1617            _params: QueryManagedSubAccountSnapshotParams,
1618        ) -> anyhow::Result<RestApiResponse<models::QueryManagedSubAccountSnapshotResponse>>
1619        {
1620            if self.force_error {
1621                return Err(ConnectorError::ConnectorClientError {
1622                    msg: "ResponseError".to_string(),
1623                    code: None,
1624                }
1625                .into());
1626            }
1627
1628            let resp_json: Value = serde_json::from_str(r#"{"code":200,"msg":"","snapshotVos":[{"data":{"balances":[{"asset":"BTC","free":"0.09905021","locked":"0.00000000"}],"totalAssetOfBtc":"0.09942700","marginLevel":"2748.02909813","totalLiabilityOfBtc":"0.00000100","totalNetAssetOfBtc":"0.00274750","userAssets":[{"asset":"XRP","borrowed":"0.00000000","free":"1.00000000","interest":"0.00000000","locked":"0.00000000","netAsset":"1.00000000"}],"assets":[{"asset":"USDT","marginBalance":"118.99782335","walletBalance":"120.23811389"}],"position":[{"entryPrice":"7130.41000000","markPrice":"7257.66239673","positionAmt":"0.01000000","symbol":"BTCUSDT","unRealizedProfit":"1.24029054"}]},"type":"spot","updateTime":1576281599000}]}"#).unwrap_or_else(|_| serde_json::json!({}));
1629            let dummy_response: models::QueryManagedSubAccountSnapshotResponse =
1630                serde_json::from_value(resp_json.clone())
1631                    .expect("should parse into models::QueryManagedSubAccountSnapshotResponse");
1632
1633            let dummy = DummyRestApiResponse {
1634                inner: Box::new(move || Box::pin(async move { Ok(dummy_response) })),
1635                status: 200,
1636                headers: HashMap::new(),
1637                rate_limits: None,
1638            };
1639
1640            Ok(dummy.into())
1641        }
1642
1643        async fn query_managed_sub_account_transfer_log_master_account_investor(
1644            &self,
1645            _params: QueryManagedSubAccountTransferLogMasterAccountInvestorParams,
1646        ) -> anyhow::Result<
1647            RestApiResponse<models::QueryManagedSubAccountTransferLogMasterAccountInvestorResponse>,
1648        > {
1649            if self.force_error {
1650                return Err(ConnectorError::ConnectorClientError {
1651                    msg: "ResponseError".to_string(),
1652                    code: None,
1653                }
1654                .into());
1655            }
1656
1657            let resp_json: Value = serde_json::from_str(r#"{"managerSubTransferHistoryVos":[{"fromEmail":"test_0_virtual@kq3kno9imanagedsub.com","fromAccountType":"SPOT","toEmail":"wdywl0lddakh@test.com","toAccountType":"SPOT","asset":"BNB","amount":"0.01","scheduledData":1679416673000,"createTime":1679416673000,"status":"SUCCESS","tranId":91077779}],"count":2}"#).unwrap_or_else(|_| serde_json::json!({}));
1658            let dummy_response : models::QueryManagedSubAccountTransferLogMasterAccountInvestorResponse = serde_json::from_value(resp_json.clone()).expect("should parse into models::QueryManagedSubAccountTransferLogMasterAccountInvestorResponse");
1659
1660            let dummy = DummyRestApiResponse {
1661                inner: Box::new(move || Box::pin(async move { Ok(dummy_response) })),
1662                status: 200,
1663                headers: HashMap::new(),
1664                rate_limits: None,
1665            };
1666
1667            Ok(dummy.into())
1668        }
1669
1670        async fn query_managed_sub_account_transfer_log_master_account_trading(
1671            &self,
1672            _params: QueryManagedSubAccountTransferLogMasterAccountTradingParams,
1673        ) -> anyhow::Result<
1674            RestApiResponse<models::QueryManagedSubAccountTransferLogMasterAccountTradingResponse>,
1675        > {
1676            if self.force_error {
1677                return Err(ConnectorError::ConnectorClientError {
1678                    msg: "ResponseError".to_string(),
1679                    code: None,
1680                }
1681                .into());
1682            }
1683
1684            let resp_json: Value = serde_json::from_str(r#"{"managerSubTransferHistoryVos":[{"fromEmail":"test_0_virtual@kq3kno9imanagedsub.com","fromAccountType":"SPOT","toEmail":"wdywl0lddakh@test.com","toAccountType":"SPOT","asset":"BNB","amount":"0.01","scheduledData":1679416673000,"createTime":1679416673000,"status":"SUCCESS","tranId":91077779}],"count":2}"#).unwrap_or_else(|_| serde_json::json!({}));
1685            let dummy_response : models::QueryManagedSubAccountTransferLogMasterAccountTradingResponse = serde_json::from_value(resp_json.clone()).expect("should parse into models::QueryManagedSubAccountTransferLogMasterAccountTradingResponse");
1686
1687            let dummy = DummyRestApiResponse {
1688                inner: Box::new(move || Box::pin(async move { Ok(dummy_response) })),
1689                status: 200,
1690                headers: HashMap::new(),
1691                rate_limits: None,
1692            };
1693
1694            Ok(dummy.into())
1695        }
1696
1697        async fn query_managed_sub_account_transfer_log_sub_account_trading(
1698            &self,
1699            _params: QueryManagedSubAccountTransferLogSubAccountTradingParams,
1700        ) -> anyhow::Result<
1701            RestApiResponse<models::QueryManagedSubAccountTransferLogSubAccountTradingResponse>,
1702        > {
1703            if self.force_error {
1704                return Err(ConnectorError::ConnectorClientError {
1705                    msg: "ResponseError".to_string(),
1706                    code: None,
1707                }
1708                .into());
1709            }
1710
1711            let resp_json: Value = serde_json::from_str(r#"{"managerSubTransferHistoryVos":[{"fromEmail":"test_0_virtual@kq3kno9imanagedsub.com","fromAccountType":"SPOT","toEmail":"wdywl0lddakh@test.com","toAccountType":"SPOT","asset":"BNB","amount":"0.01","scheduledData":1679416673000,"createTime":1679416673000,"status":"SUCCESS","tranId":91077779}],"count":2}"#).unwrap_or_else(|_| serde_json::json!({}));
1712            let dummy_response : models::QueryManagedSubAccountTransferLogSubAccountTradingResponse = serde_json::from_value(resp_json.clone()).expect("should parse into models::QueryManagedSubAccountTransferLogSubAccountTradingResponse");
1713
1714            let dummy = DummyRestApiResponse {
1715                inner: Box::new(move || Box::pin(async move { Ok(dummy_response) })),
1716                status: 200,
1717                headers: HashMap::new(),
1718                rate_limits: None,
1719            };
1720
1721            Ok(dummy.into())
1722        }
1723
1724        async fn withdrawl_assets_from_the_managed_sub_account(
1725            &self,
1726            _params: WithdrawlAssetsFromTheManagedSubAccountParams,
1727        ) -> anyhow::Result<RestApiResponse<models::WithdrawlAssetsFromTheManagedSubAccountResponse>>
1728        {
1729            if self.force_error {
1730                return Err(ConnectorError::ConnectorClientError {
1731                    msg: "ResponseError".to_string(),
1732                    code: None,
1733                }
1734                .into());
1735            }
1736
1737            let resp_json: Value = serde_json::from_str(r#"{"tranId":66157362489}"#)
1738                .unwrap_or_else(|_| serde_json::json!({}));
1739            let dummy_response: models::WithdrawlAssetsFromTheManagedSubAccountResponse =
1740                serde_json::from_value(resp_json.clone()).expect(
1741                    "should parse into models::WithdrawlAssetsFromTheManagedSubAccountResponse",
1742                );
1743
1744            let dummy = DummyRestApiResponse {
1745                inner: Box::new(move || Box::pin(async move { Ok(dummy_response) })),
1746                status: 200,
1747                headers: HashMap::new(),
1748                rate_limits: None,
1749            };
1750
1751            Ok(dummy.into())
1752        }
1753    }
1754
1755    #[test]
1756    fn deposit_assets_into_the_managed_sub_account_required_params_success() {
1757        TOKIO_SHARED_RT.block_on(async {
1758            let client = MockManagedSubAccountApiClient { force_error: false };
1759
1760            let params = DepositAssetsIntoTheManagedSubAccountParams::builder(
1761                "abc@test.com".to_string(),
1762                "BTC".to_string(),
1763                dec!(1.0),
1764            )
1765            .build()
1766            .unwrap();
1767
1768            let resp_json: Value = serde_json::from_str(r#"{"tranId":66157362489}"#)
1769                .unwrap_or_else(|_| serde_json::json!({}));
1770            let expected_response: models::DepositAssetsIntoTheManagedSubAccountResponse =
1771                serde_json::from_value(resp_json.clone()).expect(
1772                    "should parse into models::DepositAssetsIntoTheManagedSubAccountResponse",
1773                );
1774
1775            let resp = client
1776                .deposit_assets_into_the_managed_sub_account(params)
1777                .await
1778                .expect("Expected a response");
1779            let data_future = resp.data();
1780            let actual_response = data_future.await.unwrap();
1781            assert_eq!(actual_response, expected_response);
1782        });
1783    }
1784
1785    #[test]
1786    fn deposit_assets_into_the_managed_sub_account_optional_params_success() {
1787        TOKIO_SHARED_RT.block_on(async {
1788            let client = MockManagedSubAccountApiClient { force_error: false };
1789
1790            let params = DepositAssetsIntoTheManagedSubAccountParams::builder(
1791                "abc@test.com".to_string(),
1792                "BTC".to_string(),
1793                dec!(1.0),
1794            )
1795            .recv_window(5000)
1796            .build()
1797            .unwrap();
1798
1799            let resp_json: Value = serde_json::from_str(r#"{"tranId":66157362489}"#)
1800                .unwrap_or_else(|_| serde_json::json!({}));
1801            let expected_response: models::DepositAssetsIntoTheManagedSubAccountResponse =
1802                serde_json::from_value(resp_json.clone()).expect(
1803                    "should parse into models::DepositAssetsIntoTheManagedSubAccountResponse",
1804                );
1805
1806            let resp = client
1807                .deposit_assets_into_the_managed_sub_account(params)
1808                .await
1809                .expect("Expected a response");
1810            let data_future = resp.data();
1811            let actual_response = data_future.await.unwrap();
1812            assert_eq!(actual_response, expected_response);
1813        });
1814    }
1815
1816    #[test]
1817    fn deposit_assets_into_the_managed_sub_account_response_error() {
1818        TOKIO_SHARED_RT.block_on(async {
1819            let client = MockManagedSubAccountApiClient { force_error: true };
1820
1821            let params = DepositAssetsIntoTheManagedSubAccountParams::builder(
1822                "abc@test.com".to_string(),
1823                "BTC".to_string(),
1824                dec!(1.0),
1825            )
1826            .build()
1827            .unwrap();
1828
1829            match client
1830                .deposit_assets_into_the_managed_sub_account(params)
1831                .await
1832            {
1833                Ok(_) => panic!("Expected an error"),
1834                Err(err) => {
1835                    assert_eq!(err.to_string(), "Connector client error: ResponseError");
1836                }
1837            }
1838        });
1839    }
1840
1841    #[test]
1842    fn get_managed_sub_account_deposit_address_required_params_success() {
1843        TOKIO_SHARED_RT.block_on(async {
1844            let client = MockManagedSubAccountApiClient { force_error: false };
1845
1846            let params = GetManagedSubAccountDepositAddressParams::builder("abc@test.com".to_string(),"USDT".to_string(),).build().unwrap();
1847
1848            let resp_json: Value = serde_json::from_str(r#"{"coin":"USDT","address":"0x206c22d833bb0bb2102da6b7c7d4c3eb14bcf73d","tag":"","url":"https://etherscan.io/address/0x206c22d833bb0bb2102da6b7c7d4c3eb14bcf73d"}"#).unwrap_or_else(|_| serde_json::json!({}));
1849            let expected_response : models::GetManagedSubAccountDepositAddressResponse = serde_json::from_value(resp_json.clone()).expect("should parse into models::GetManagedSubAccountDepositAddressResponse");
1850
1851            let resp = client.get_managed_sub_account_deposit_address(params).await.expect("Expected a response");
1852            let data_future = resp.data();
1853            let actual_response = data_future.await.unwrap();
1854            assert_eq!(actual_response, expected_response);
1855        });
1856    }
1857
1858    #[test]
1859    fn get_managed_sub_account_deposit_address_optional_params_success() {
1860        TOKIO_SHARED_RT.block_on(async {
1861            let client = MockManagedSubAccountApiClient { force_error: false };
1862
1863            let params = GetManagedSubAccountDepositAddressParams::builder("abc@test.com".to_string(),"USDT".to_string(),).network("LIGHTNING".to_string()).amount(dec!(1.0)).recv_window(5000).build().unwrap();
1864
1865            let resp_json: Value = serde_json::from_str(r#"{"coin":"USDT","address":"0x206c22d833bb0bb2102da6b7c7d4c3eb14bcf73d","tag":"","url":"https://etherscan.io/address/0x206c22d833bb0bb2102da6b7c7d4c3eb14bcf73d"}"#).unwrap_or_else(|_| serde_json::json!({}));
1866            let expected_response : models::GetManagedSubAccountDepositAddressResponse = serde_json::from_value(resp_json.clone()).expect("should parse into models::GetManagedSubAccountDepositAddressResponse");
1867
1868            let resp = client.get_managed_sub_account_deposit_address(params).await.expect("Expected a response");
1869            let data_future = resp.data();
1870            let actual_response = data_future.await.unwrap();
1871            assert_eq!(actual_response, expected_response);
1872        });
1873    }
1874
1875    #[test]
1876    fn get_managed_sub_account_deposit_address_response_error() {
1877        TOKIO_SHARED_RT.block_on(async {
1878            let client = MockManagedSubAccountApiClient { force_error: true };
1879
1880            let params = GetManagedSubAccountDepositAddressParams::builder(
1881                "abc@test.com".to_string(),
1882                "USDT".to_string(),
1883            )
1884            .build()
1885            .unwrap();
1886
1887            match client.get_managed_sub_account_deposit_address(params).await {
1888                Ok(_) => panic!("Expected an error"),
1889                Err(err) => {
1890                    assert_eq!(err.to_string(), "Connector client error: ResponseError");
1891                }
1892            }
1893        });
1894    }
1895
1896    #[test]
1897    fn query_managed_sub_account_asset_details_required_params_success() {
1898        TOKIO_SHARED_RT.block_on(async {
1899            let client = MockManagedSubAccountApiClient { force_error: false };
1900
1901            let params = QueryManagedSubAccountAssetDetailsParams::builder("abc@test.com".to_string(),).build().unwrap();
1902
1903            let resp_json: Value = serde_json::from_str(r#"[{"coin":"INJ","name":"Injective Protocol","totalBalance":"0","availableBalance":"0","inOrder":"0","btcValue":"0"}]"#).unwrap_or_else(|_| serde_json::json!({}));
1904            let expected_response : Vec<models::QueryManagedSubAccountAssetDetailsResponseInner> = serde_json::from_value(resp_json.clone()).expect("should parse into Vec<models::QueryManagedSubAccountAssetDetailsResponseInner>");
1905
1906            let resp = client.query_managed_sub_account_asset_details(params).await.expect("Expected a response");
1907            let data_future = resp.data();
1908            let actual_response = data_future.await.unwrap();
1909            assert_eq!(actual_response, expected_response);
1910        });
1911    }
1912
1913    #[test]
1914    fn query_managed_sub_account_asset_details_optional_params_success() {
1915        TOKIO_SHARED_RT.block_on(async {
1916            let client = MockManagedSubAccountApiClient { force_error: false };
1917
1918            let params = QueryManagedSubAccountAssetDetailsParams::builder("abc@test.com".to_string(),).recv_window(5000).build().unwrap();
1919
1920            let resp_json: Value = serde_json::from_str(r#"[{"coin":"INJ","name":"Injective Protocol","totalBalance":"0","availableBalance":"0","inOrder":"0","btcValue":"0"}]"#).unwrap_or_else(|_| serde_json::json!({}));
1921            let expected_response : Vec<models::QueryManagedSubAccountAssetDetailsResponseInner> = serde_json::from_value(resp_json.clone()).expect("should parse into Vec<models::QueryManagedSubAccountAssetDetailsResponseInner>");
1922
1923            let resp = client.query_managed_sub_account_asset_details(params).await.expect("Expected a response");
1924            let data_future = resp.data();
1925            let actual_response = data_future.await.unwrap();
1926            assert_eq!(actual_response, expected_response);
1927        });
1928    }
1929
1930    #[test]
1931    fn query_managed_sub_account_asset_details_response_error() {
1932        TOKIO_SHARED_RT.block_on(async {
1933            let client = MockManagedSubAccountApiClient { force_error: true };
1934
1935            let params =
1936                QueryManagedSubAccountAssetDetailsParams::builder("abc@test.com".to_string())
1937                    .build()
1938                    .unwrap();
1939
1940            match client.query_managed_sub_account_asset_details(params).await {
1941                Ok(_) => panic!("Expected an error"),
1942                Err(err) => {
1943                    assert_eq!(err.to_string(), "Connector client error: ResponseError");
1944                }
1945            }
1946        });
1947    }
1948
1949    #[test]
1950    fn query_managed_sub_account_futures_asset_details_required_params_success() {
1951        TOKIO_SHARED_RT.block_on(async {
1952            let client = MockManagedSubAccountApiClient { force_error: false };
1953
1954            let params = QueryManagedSubAccountFuturesAssetDetailsParams::builder("abc@test.com".to_string(),).build().unwrap();
1955
1956            let resp_json: Value = serde_json::from_str(r#"{"code":"200","message":"OK","snapshotVos":[{"type":"FUTURES","updateTime":1672893855394,"data":{"assets":[{"asset":"USDT","marginBalance":100,"walletBalance":120}],"position":[{"symbol":"BTCUSDT","entryPrice":17000,"markPrice":17000,"positionAmt":1.0E-4}]}}]}"#).unwrap_or_else(|_| serde_json::json!({}));
1957            let expected_response : models::QueryManagedSubAccountFuturesAssetDetailsResponse = serde_json::from_value(resp_json.clone()).expect("should parse into models::QueryManagedSubAccountFuturesAssetDetailsResponse");
1958
1959            let resp = client.query_managed_sub_account_futures_asset_details(params).await.expect("Expected a response");
1960            let data_future = resp.data();
1961            let actual_response = data_future.await.unwrap();
1962            assert_eq!(actual_response, expected_response);
1963        });
1964    }
1965
1966    #[test]
1967    fn query_managed_sub_account_futures_asset_details_optional_params_success() {
1968        TOKIO_SHARED_RT.block_on(async {
1969            let client = MockManagedSubAccountApiClient { force_error: false };
1970
1971            let params = QueryManagedSubAccountFuturesAssetDetailsParams::builder("abc@test.com".to_string(),).account_type("MARGIN".to_string()).build().unwrap();
1972
1973            let resp_json: Value = serde_json::from_str(r#"{"code":"200","message":"OK","snapshotVos":[{"type":"FUTURES","updateTime":1672893855394,"data":{"assets":[{"asset":"USDT","marginBalance":100,"walletBalance":120}],"position":[{"symbol":"BTCUSDT","entryPrice":17000,"markPrice":17000,"positionAmt":1.0E-4}]}}]}"#).unwrap_or_else(|_| serde_json::json!({}));
1974            let expected_response : models::QueryManagedSubAccountFuturesAssetDetailsResponse = serde_json::from_value(resp_json.clone()).expect("should parse into models::QueryManagedSubAccountFuturesAssetDetailsResponse");
1975
1976            let resp = client.query_managed_sub_account_futures_asset_details(params).await.expect("Expected a response");
1977            let data_future = resp.data();
1978            let actual_response = data_future.await.unwrap();
1979            assert_eq!(actual_response, expected_response);
1980        });
1981    }
1982
1983    #[test]
1984    fn query_managed_sub_account_futures_asset_details_response_error() {
1985        TOKIO_SHARED_RT.block_on(async {
1986            let client = MockManagedSubAccountApiClient { force_error: true };
1987
1988            let params = QueryManagedSubAccountFuturesAssetDetailsParams::builder(
1989                "abc@test.com".to_string(),
1990            )
1991            .build()
1992            .unwrap();
1993
1994            match client
1995                .query_managed_sub_account_futures_asset_details(params)
1996                .await
1997            {
1998                Ok(_) => panic!("Expected an error"),
1999                Err(err) => {
2000                    assert_eq!(err.to_string(), "Connector client error: ResponseError");
2001                }
2002            }
2003        });
2004    }
2005
2006    #[test]
2007    fn query_managed_sub_account_list_required_params_success() {
2008        TOKIO_SHARED_RT.block_on(async {
2009            let client = MockManagedSubAccountApiClient { force_error: false };
2010
2011            let params = QueryManagedSubAccountListParams::builder().build().unwrap();
2012
2013            let resp_json: Value = serde_json::from_str(r#"{"total":3,"managerSubUserInfoVoList":[{"rootUserId":1000138475670,"managersubUserId":1000137842513,"bindParentUserId":1000138475669,"email":"test_0_virtual@kq3kno9imanagedsub.com","insertTimeStamp":1678435149000,"bindParentEmail":"wdyw8xsh8pey@test.com","isSubUserEnabled":true,"isUserActive":true,"isMarginEnabled":false,"isFutureEnabled":false,"isSignedLVTRiskAgreement":false}]}"#).unwrap_or_else(|_| serde_json::json!({}));
2014            let expected_response : models::QueryManagedSubAccountListResponse = serde_json::from_value(resp_json.clone()).expect("should parse into models::QueryManagedSubAccountListResponse");
2015
2016            let resp = client.query_managed_sub_account_list(params).await.expect("Expected a response");
2017            let data_future = resp.data();
2018            let actual_response = data_future.await.unwrap();
2019            assert_eq!(actual_response, expected_response);
2020        });
2021    }
2022
2023    #[test]
2024    fn query_managed_sub_account_list_optional_params_success() {
2025        TOKIO_SHARED_RT.block_on(async {
2026            let client = MockManagedSubAccountApiClient { force_error: false };
2027
2028            let params = QueryManagedSubAccountListParams::builder().email("abc@test.com".to_string()).page(1).limit(10).recv_window(5000).build().unwrap();
2029
2030            let resp_json: Value = serde_json::from_str(r#"{"total":3,"managerSubUserInfoVoList":[{"rootUserId":1000138475670,"managersubUserId":1000137842513,"bindParentUserId":1000138475669,"email":"test_0_virtual@kq3kno9imanagedsub.com","insertTimeStamp":1678435149000,"bindParentEmail":"wdyw8xsh8pey@test.com","isSubUserEnabled":true,"isUserActive":true,"isMarginEnabled":false,"isFutureEnabled":false,"isSignedLVTRiskAgreement":false}]}"#).unwrap_or_else(|_| serde_json::json!({}));
2031            let expected_response : models::QueryManagedSubAccountListResponse = serde_json::from_value(resp_json.clone()).expect("should parse into models::QueryManagedSubAccountListResponse");
2032
2033            let resp = client.query_managed_sub_account_list(params).await.expect("Expected a response");
2034            let data_future = resp.data();
2035            let actual_response = data_future.await.unwrap();
2036            assert_eq!(actual_response, expected_response);
2037        });
2038    }
2039
2040    #[test]
2041    fn query_managed_sub_account_list_response_error() {
2042        TOKIO_SHARED_RT.block_on(async {
2043            let client = MockManagedSubAccountApiClient { force_error: true };
2044
2045            let params = QueryManagedSubAccountListParams::builder().build().unwrap();
2046
2047            match client.query_managed_sub_account_list(params).await {
2048                Ok(_) => panic!("Expected an error"),
2049                Err(err) => {
2050                    assert_eq!(err.to_string(), "Connector client error: ResponseError");
2051                }
2052            }
2053        });
2054    }
2055
2056    #[test]
2057    fn query_managed_sub_account_margin_asset_details_required_params_success() {
2058        TOKIO_SHARED_RT.block_on(async {
2059            let client = MockManagedSubAccountApiClient { force_error: false };
2060
2061            let params = QueryManagedSubAccountMarginAssetDetailsParams::builder("abc@test.com".to_string(),).build().unwrap();
2062
2063            let resp_json: Value = serde_json::from_str(r#"{"marginLevel":"999","totalAssetOfBtc":"0","totalLiabilityOfBtc":"0","totalNetAssetOfBtc":"0","userAssets":[{"asset":"MATIC","borrowed":"0","free":"0","interest":"0","locked":"0","netAsset":"0"}]}"#).unwrap_or_else(|_| serde_json::json!({}));
2064            let expected_response : models::QueryManagedSubAccountMarginAssetDetailsResponse = serde_json::from_value(resp_json.clone()).expect("should parse into models::QueryManagedSubAccountMarginAssetDetailsResponse");
2065
2066            let resp = client.query_managed_sub_account_margin_asset_details(params).await.expect("Expected a response");
2067            let data_future = resp.data();
2068            let actual_response = data_future.await.unwrap();
2069            assert_eq!(actual_response, expected_response);
2070        });
2071    }
2072
2073    #[test]
2074    fn query_managed_sub_account_margin_asset_details_optional_params_success() {
2075        TOKIO_SHARED_RT.block_on(async {
2076            let client = MockManagedSubAccountApiClient { force_error: false };
2077
2078            let params = QueryManagedSubAccountMarginAssetDetailsParams::builder("abc@test.com".to_string(),).account_type("MARGIN".to_string()).build().unwrap();
2079
2080            let resp_json: Value = serde_json::from_str(r#"{"marginLevel":"999","totalAssetOfBtc":"0","totalLiabilityOfBtc":"0","totalNetAssetOfBtc":"0","userAssets":[{"asset":"MATIC","borrowed":"0","free":"0","interest":"0","locked":"0","netAsset":"0"}]}"#).unwrap_or_else(|_| serde_json::json!({}));
2081            let expected_response : models::QueryManagedSubAccountMarginAssetDetailsResponse = serde_json::from_value(resp_json.clone()).expect("should parse into models::QueryManagedSubAccountMarginAssetDetailsResponse");
2082
2083            let resp = client.query_managed_sub_account_margin_asset_details(params).await.expect("Expected a response");
2084            let data_future = resp.data();
2085            let actual_response = data_future.await.unwrap();
2086            assert_eq!(actual_response, expected_response);
2087        });
2088    }
2089
2090    #[test]
2091    fn query_managed_sub_account_margin_asset_details_response_error() {
2092        TOKIO_SHARED_RT.block_on(async {
2093            let client = MockManagedSubAccountApiClient { force_error: true };
2094
2095            let params =
2096                QueryManagedSubAccountMarginAssetDetailsParams::builder("abc@test.com".to_string())
2097                    .build()
2098                    .unwrap();
2099
2100            match client
2101                .query_managed_sub_account_margin_asset_details(params)
2102                .await
2103            {
2104                Ok(_) => panic!("Expected an error"),
2105                Err(err) => {
2106                    assert_eq!(err.to_string(), "Connector client error: ResponseError");
2107                }
2108            }
2109        });
2110    }
2111
2112    #[test]
2113    fn query_managed_sub_account_snapshot_required_params_success() {
2114        TOKIO_SHARED_RT.block_on(async {
2115            let client = MockManagedSubAccountApiClient { force_error: false };
2116
2117            let params = QueryManagedSubAccountSnapshotParams::builder("abc@test.com".to_string(),QueryManagedSubAccountSnapshotTypeEnum::Spot,).build().unwrap();
2118
2119            let resp_json: Value = serde_json::from_str(r#"{"code":200,"msg":"","snapshotVos":[{"data":{"balances":[{"asset":"BTC","free":"0.09905021","locked":"0.00000000"}],"totalAssetOfBtc":"0.09942700","marginLevel":"2748.02909813","totalLiabilityOfBtc":"0.00000100","totalNetAssetOfBtc":"0.00274750","userAssets":[{"asset":"XRP","borrowed":"0.00000000","free":"1.00000000","interest":"0.00000000","locked":"0.00000000","netAsset":"1.00000000"}],"assets":[{"asset":"USDT","marginBalance":"118.99782335","walletBalance":"120.23811389"}],"position":[{"entryPrice":"7130.41000000","markPrice":"7257.66239673","positionAmt":"0.01000000","symbol":"BTCUSDT","unRealizedProfit":"1.24029054"}]},"type":"spot","updateTime":1576281599000}]}"#).unwrap_or_else(|_| serde_json::json!({}));
2120            let expected_response : models::QueryManagedSubAccountSnapshotResponse = serde_json::from_value(resp_json.clone()).expect("should parse into models::QueryManagedSubAccountSnapshotResponse");
2121
2122            let resp = client.query_managed_sub_account_snapshot(params).await.expect("Expected a response");
2123            let data_future = resp.data();
2124            let actual_response = data_future.await.unwrap();
2125            assert_eq!(actual_response, expected_response);
2126        });
2127    }
2128
2129    #[test]
2130    fn query_managed_sub_account_snapshot_optional_params_success() {
2131        TOKIO_SHARED_RT.block_on(async {
2132            let client = MockManagedSubAccountApiClient { force_error: false };
2133
2134            let params = QueryManagedSubAccountSnapshotParams::builder("abc@test.com".to_string(),QueryManagedSubAccountSnapshotTypeEnum::Spot,).start_time(1623319461670).end_time(1641782889000).limit(10).recv_window(5000).build().unwrap();
2135
2136            let resp_json: Value = serde_json::from_str(r#"{"code":200,"msg":"","snapshotVos":[{"data":{"balances":[{"asset":"BTC","free":"0.09905021","locked":"0.00000000"}],"totalAssetOfBtc":"0.09942700","marginLevel":"2748.02909813","totalLiabilityOfBtc":"0.00000100","totalNetAssetOfBtc":"0.00274750","userAssets":[{"asset":"XRP","borrowed":"0.00000000","free":"1.00000000","interest":"0.00000000","locked":"0.00000000","netAsset":"1.00000000"}],"assets":[{"asset":"USDT","marginBalance":"118.99782335","walletBalance":"120.23811389"}],"position":[{"entryPrice":"7130.41000000","markPrice":"7257.66239673","positionAmt":"0.01000000","symbol":"BTCUSDT","unRealizedProfit":"1.24029054"}]},"type":"spot","updateTime":1576281599000}]}"#).unwrap_or_else(|_| serde_json::json!({}));
2137            let expected_response : models::QueryManagedSubAccountSnapshotResponse = serde_json::from_value(resp_json.clone()).expect("should parse into models::QueryManagedSubAccountSnapshotResponse");
2138
2139            let resp = client.query_managed_sub_account_snapshot(params).await.expect("Expected a response");
2140            let data_future = resp.data();
2141            let actual_response = data_future.await.unwrap();
2142            assert_eq!(actual_response, expected_response);
2143        });
2144    }
2145
2146    #[test]
2147    fn query_managed_sub_account_snapshot_response_error() {
2148        TOKIO_SHARED_RT.block_on(async {
2149            let client = MockManagedSubAccountApiClient { force_error: true };
2150
2151            let params = QueryManagedSubAccountSnapshotParams::builder(
2152                "abc@test.com".to_string(),
2153                QueryManagedSubAccountSnapshotTypeEnum::Spot,
2154            )
2155            .build()
2156            .unwrap();
2157
2158            match client.query_managed_sub_account_snapshot(params).await {
2159                Ok(_) => panic!("Expected an error"),
2160                Err(err) => {
2161                    assert_eq!(err.to_string(), "Connector client error: ResponseError");
2162                }
2163            }
2164        });
2165    }
2166
2167    #[test]
2168    fn query_managed_sub_account_transfer_log_master_account_investor_required_params_success() {
2169        TOKIO_SHARED_RT.block_on(async {
2170            let client = MockManagedSubAccountApiClient { force_error: false };
2171
2172            let params = QueryManagedSubAccountTransferLogMasterAccountInvestorParams::builder("abc@test.com".to_string(),1623319461670,1641782889000,1,1,).build().unwrap();
2173
2174            let resp_json: Value = serde_json::from_str(r#"{"managerSubTransferHistoryVos":[{"fromEmail":"test_0_virtual@kq3kno9imanagedsub.com","fromAccountType":"SPOT","toEmail":"wdywl0lddakh@test.com","toAccountType":"SPOT","asset":"BNB","amount":"0.01","scheduledData":1679416673000,"createTime":1679416673000,"status":"SUCCESS","tranId":91077779}],"count":2}"#).unwrap_or_else(|_| serde_json::json!({}));
2175            let expected_response : models::QueryManagedSubAccountTransferLogMasterAccountInvestorResponse = serde_json::from_value(resp_json.clone()).expect("should parse into models::QueryManagedSubAccountTransferLogMasterAccountInvestorResponse");
2176
2177            let resp = client.query_managed_sub_account_transfer_log_master_account_investor(params).await.expect("Expected a response");
2178            let data_future = resp.data();
2179            let actual_response = data_future.await.unwrap();
2180            assert_eq!(actual_response, expected_response);
2181        });
2182    }
2183
2184    #[test]
2185    fn query_managed_sub_account_transfer_log_master_account_investor_optional_params_success() {
2186        TOKIO_SHARED_RT.block_on(async {
2187            let client = MockManagedSubAccountApiClient { force_error: false };
2188
2189            let params = QueryManagedSubAccountTransferLogMasterAccountInvestorParams::builder("abc@test.com".to_string(),1623319461670,1641782889000,1,1,).transfers("transfers_example".to_string()).transfer_function_account_type(QueryManagedSubAccountTransferLogMasterAccountInvestorTransferFunctionAccountTypeEnum::Spot).build().unwrap();
2190
2191            let resp_json: Value = serde_json::from_str(r#"{"managerSubTransferHistoryVos":[{"fromEmail":"test_0_virtual@kq3kno9imanagedsub.com","fromAccountType":"SPOT","toEmail":"wdywl0lddakh@test.com","toAccountType":"SPOT","asset":"BNB","amount":"0.01","scheduledData":1679416673000,"createTime":1679416673000,"status":"SUCCESS","tranId":91077779}],"count":2}"#).unwrap_or_else(|_| serde_json::json!({}));
2192            let expected_response : models::QueryManagedSubAccountTransferLogMasterAccountInvestorResponse = serde_json::from_value(resp_json.clone()).expect("should parse into models::QueryManagedSubAccountTransferLogMasterAccountInvestorResponse");
2193
2194            let resp = client.query_managed_sub_account_transfer_log_master_account_investor(params).await.expect("Expected a response");
2195            let data_future = resp.data();
2196            let actual_response = data_future.await.unwrap();
2197            assert_eq!(actual_response, expected_response);
2198        });
2199    }
2200
2201    #[test]
2202    fn query_managed_sub_account_transfer_log_master_account_investor_response_error() {
2203        TOKIO_SHARED_RT.block_on(async {
2204            let client = MockManagedSubAccountApiClient { force_error: true };
2205
2206            let params = QueryManagedSubAccountTransferLogMasterAccountInvestorParams::builder(
2207                "abc@test.com".to_string(),
2208                1623319461670,
2209                1641782889000,
2210                1,
2211                1,
2212            )
2213            .build()
2214            .unwrap();
2215
2216            match client
2217                .query_managed_sub_account_transfer_log_master_account_investor(params)
2218                .await
2219            {
2220                Ok(_) => panic!("Expected an error"),
2221                Err(err) => {
2222                    assert_eq!(err.to_string(), "Connector client error: ResponseError");
2223                }
2224            }
2225        });
2226    }
2227
2228    #[test]
2229    fn query_managed_sub_account_transfer_log_master_account_trading_required_params_success() {
2230        TOKIO_SHARED_RT.block_on(async {
2231            let client = MockManagedSubAccountApiClient { force_error: false };
2232
2233            let params = QueryManagedSubAccountTransferLogMasterAccountTradingParams::builder("abc@test.com".to_string(),1623319461670,1641782889000,1,10,).build().unwrap();
2234
2235            let resp_json: Value = serde_json::from_str(r#"{"managerSubTransferHistoryVos":[{"fromEmail":"test_0_virtual@kq3kno9imanagedsub.com","fromAccountType":"SPOT","toEmail":"wdywl0lddakh@test.com","toAccountType":"SPOT","asset":"BNB","amount":"0.01","scheduledData":1679416673000,"createTime":1679416673000,"status":"SUCCESS","tranId":91077779}],"count":2}"#).unwrap_or_else(|_| serde_json::json!({}));
2236            let expected_response : models::QueryManagedSubAccountTransferLogMasterAccountTradingResponse = serde_json::from_value(resp_json.clone()).expect("should parse into models::QueryManagedSubAccountTransferLogMasterAccountTradingResponse");
2237
2238            let resp = client.query_managed_sub_account_transfer_log_master_account_trading(params).await.expect("Expected a response");
2239            let data_future = resp.data();
2240            let actual_response = data_future.await.unwrap();
2241            assert_eq!(actual_response, expected_response);
2242        });
2243    }
2244
2245    #[test]
2246    fn query_managed_sub_account_transfer_log_master_account_trading_optional_params_success() {
2247        TOKIO_SHARED_RT.block_on(async {
2248            let client = MockManagedSubAccountApiClient { force_error: false };
2249
2250            let params = QueryManagedSubAccountTransferLogMasterAccountTradingParams::builder("abc@test.com".to_string(),1623319461670,1641782889000,1,10,).transfers("transfers_example".to_string()).transfer_function_account_type(QueryManagedSubAccountTransferLogMasterAccountTradingTransferFunctionAccountTypeEnum::Spot).build().unwrap();
2251
2252            let resp_json: Value = serde_json::from_str(r#"{"managerSubTransferHistoryVos":[{"fromEmail":"test_0_virtual@kq3kno9imanagedsub.com","fromAccountType":"SPOT","toEmail":"wdywl0lddakh@test.com","toAccountType":"SPOT","asset":"BNB","amount":"0.01","scheduledData":1679416673000,"createTime":1679416673000,"status":"SUCCESS","tranId":91077779}],"count":2}"#).unwrap_or_else(|_| serde_json::json!({}));
2253            let expected_response : models::QueryManagedSubAccountTransferLogMasterAccountTradingResponse = serde_json::from_value(resp_json.clone()).expect("should parse into models::QueryManagedSubAccountTransferLogMasterAccountTradingResponse");
2254
2255            let resp = client.query_managed_sub_account_transfer_log_master_account_trading(params).await.expect("Expected a response");
2256            let data_future = resp.data();
2257            let actual_response = data_future.await.unwrap();
2258            assert_eq!(actual_response, expected_response);
2259        });
2260    }
2261
2262    #[test]
2263    fn query_managed_sub_account_transfer_log_master_account_trading_response_error() {
2264        TOKIO_SHARED_RT.block_on(async {
2265            let client = MockManagedSubAccountApiClient { force_error: true };
2266
2267            let params = QueryManagedSubAccountTransferLogMasterAccountTradingParams::builder(
2268                "abc@test.com".to_string(),
2269                1623319461670,
2270                1641782889000,
2271                1,
2272                10,
2273            )
2274            .build()
2275            .unwrap();
2276
2277            match client
2278                .query_managed_sub_account_transfer_log_master_account_trading(params)
2279                .await
2280            {
2281                Ok(_) => panic!("Expected an error"),
2282                Err(err) => {
2283                    assert_eq!(err.to_string(), "Connector client error: ResponseError");
2284                }
2285            }
2286        });
2287    }
2288
2289    #[test]
2290    fn query_managed_sub_account_transfer_log_sub_account_trading_required_params_success() {
2291        TOKIO_SHARED_RT.block_on(async {
2292            let client = MockManagedSubAccountApiClient { force_error: false };
2293
2294            let params = QueryManagedSubAccountTransferLogSubAccountTradingParams::builder(1623319461670,1641782889000,1,10,).build().unwrap();
2295
2296            let resp_json: Value = serde_json::from_str(r#"{"managerSubTransferHistoryVos":[{"fromEmail":"test_0_virtual@kq3kno9imanagedsub.com","fromAccountType":"SPOT","toEmail":"wdywl0lddakh@test.com","toAccountType":"SPOT","asset":"BNB","amount":"0.01","scheduledData":1679416673000,"createTime":1679416673000,"status":"SUCCESS","tranId":91077779}],"count":2}"#).unwrap_or_else(|_| serde_json::json!({}));
2297            let expected_response : models::QueryManagedSubAccountTransferLogSubAccountTradingResponse = serde_json::from_value(resp_json.clone()).expect("should parse into models::QueryManagedSubAccountTransferLogSubAccountTradingResponse");
2298
2299            let resp = client.query_managed_sub_account_transfer_log_sub_account_trading(params).await.expect("Expected a response");
2300            let data_future = resp.data();
2301            let actual_response = data_future.await.unwrap();
2302            assert_eq!(actual_response, expected_response);
2303        });
2304    }
2305
2306    #[test]
2307    fn query_managed_sub_account_transfer_log_sub_account_trading_optional_params_success() {
2308        TOKIO_SHARED_RT.block_on(async {
2309            let client = MockManagedSubAccountApiClient { force_error: false };
2310
2311            let params = QueryManagedSubAccountTransferLogSubAccountTradingParams::builder(1623319461670,1641782889000,1,10,).transfers("transfers_example".to_string()).transfer_function_account_type(QueryManagedSubAccountTransferLogSubAccountTradingTransferFunctionAccountTypeEnum::Spot).recv_window(5000).build().unwrap();
2312
2313            let resp_json: Value = serde_json::from_str(r#"{"managerSubTransferHistoryVos":[{"fromEmail":"test_0_virtual@kq3kno9imanagedsub.com","fromAccountType":"SPOT","toEmail":"wdywl0lddakh@test.com","toAccountType":"SPOT","asset":"BNB","amount":"0.01","scheduledData":1679416673000,"createTime":1679416673000,"status":"SUCCESS","tranId":91077779}],"count":2}"#).unwrap_or_else(|_| serde_json::json!({}));
2314            let expected_response : models::QueryManagedSubAccountTransferLogSubAccountTradingResponse = serde_json::from_value(resp_json.clone()).expect("should parse into models::QueryManagedSubAccountTransferLogSubAccountTradingResponse");
2315
2316            let resp = client.query_managed_sub_account_transfer_log_sub_account_trading(params).await.expect("Expected a response");
2317            let data_future = resp.data();
2318            let actual_response = data_future.await.unwrap();
2319            assert_eq!(actual_response, expected_response);
2320        });
2321    }
2322
2323    #[test]
2324    fn query_managed_sub_account_transfer_log_sub_account_trading_response_error() {
2325        TOKIO_SHARED_RT.block_on(async {
2326            let client = MockManagedSubAccountApiClient { force_error: true };
2327
2328            let params = QueryManagedSubAccountTransferLogSubAccountTradingParams::builder(
2329                1623319461670,
2330                1641782889000,
2331                1,
2332                10,
2333            )
2334            .build()
2335            .unwrap();
2336
2337            match client
2338                .query_managed_sub_account_transfer_log_sub_account_trading(params)
2339                .await
2340            {
2341                Ok(_) => panic!("Expected an error"),
2342                Err(err) => {
2343                    assert_eq!(err.to_string(), "Connector client error: ResponseError");
2344                }
2345            }
2346        });
2347    }
2348
2349    #[test]
2350    fn withdrawl_assets_from_the_managed_sub_account_required_params_success() {
2351        TOKIO_SHARED_RT.block_on(async {
2352            let client = MockManagedSubAccountApiClient { force_error: false };
2353
2354            let params = WithdrawlAssetsFromTheManagedSubAccountParams::builder(
2355                "from@test.com".to_string(),
2356                "BTC".to_string(),
2357                dec!(1.0),
2358            )
2359            .build()
2360            .unwrap();
2361
2362            let resp_json: Value = serde_json::from_str(r#"{"tranId":66157362489}"#)
2363                .unwrap_or_else(|_| serde_json::json!({}));
2364            let expected_response: models::WithdrawlAssetsFromTheManagedSubAccountResponse =
2365                serde_json::from_value(resp_json.clone()).expect(
2366                    "should parse into models::WithdrawlAssetsFromTheManagedSubAccountResponse",
2367                );
2368
2369            let resp = client
2370                .withdrawl_assets_from_the_managed_sub_account(params)
2371                .await
2372                .expect("Expected a response");
2373            let data_future = resp.data();
2374            let actual_response = data_future.await.unwrap();
2375            assert_eq!(actual_response, expected_response);
2376        });
2377    }
2378
2379    #[test]
2380    fn withdrawl_assets_from_the_managed_sub_account_optional_params_success() {
2381        TOKIO_SHARED_RT.block_on(async {
2382            let client = MockManagedSubAccountApiClient { force_error: false };
2383
2384            let params = WithdrawlAssetsFromTheManagedSubAccountParams::builder(
2385                "from@test.com".to_string(),
2386                "BTC".to_string(),
2387                dec!(1.0),
2388            )
2389            .transfer_date(789)
2390            .recv_window(5000)
2391            .build()
2392            .unwrap();
2393
2394            let resp_json: Value = serde_json::from_str(r#"{"tranId":66157362489}"#)
2395                .unwrap_or_else(|_| serde_json::json!({}));
2396            let expected_response: models::WithdrawlAssetsFromTheManagedSubAccountResponse =
2397                serde_json::from_value(resp_json.clone()).expect(
2398                    "should parse into models::WithdrawlAssetsFromTheManagedSubAccountResponse",
2399                );
2400
2401            let resp = client
2402                .withdrawl_assets_from_the_managed_sub_account(params)
2403                .await
2404                .expect("Expected a response");
2405            let data_future = resp.data();
2406            let actual_response = data_future.await.unwrap();
2407            assert_eq!(actual_response, expected_response);
2408        });
2409    }
2410
2411    #[test]
2412    fn withdrawl_assets_from_the_managed_sub_account_response_error() {
2413        TOKIO_SHARED_RT.block_on(async {
2414            let client = MockManagedSubAccountApiClient { force_error: true };
2415
2416            let params = WithdrawlAssetsFromTheManagedSubAccountParams::builder(
2417                "from@test.com".to_string(),
2418                "BTC".to_string(),
2419                dec!(1.0),
2420            )
2421            .build()
2422            .unwrap();
2423
2424            match client
2425                .withdrawl_assets_from_the_managed_sub_account(params)
2426                .await
2427            {
2428                Ok(_) => panic!("Expected an error"),
2429                Err(err) => {
2430                    assert_eq!(err.to_string(), "Connector client error: ResponseError");
2431                }
2432            }
2433        });
2434    }
2435}