1#![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::mining::rest_api::models;
29
30const HAS_TIME_UNIT: bool = false;
31
32#[async_trait]
33pub trait MiningApi: Send + Sync {
34 async fn account_list(
35 &self,
36 params: AccountListParams,
37 ) -> anyhow::Result<RestApiResponse<models::AccountListResponse>>;
38 async fn acquiring_algorithm(
39 &self,
40 ) -> anyhow::Result<RestApiResponse<models::AcquiringAlgorithmResponse>>;
41 async fn acquiring_coinname(
42 &self,
43 ) -> anyhow::Result<RestApiResponse<models::AcquiringCoinnameResponse>>;
44 async fn cancel_hashrate_resale_configuration(
45 &self,
46 params: CancelHashrateResaleConfigurationParams,
47 ) -> anyhow::Result<RestApiResponse<models::CancelHashrateResaleConfigurationResponse>>;
48 async fn earnings_list(
49 &self,
50 params: EarningsListParams,
51 ) -> anyhow::Result<RestApiResponse<models::EarningsListResponse>>;
52 async fn extra_bonus_list(
53 &self,
54 params: ExtraBonusListParams,
55 ) -> anyhow::Result<RestApiResponse<models::ExtraBonusListResponse>>;
56 async fn hashrate_resale_detail(
57 &self,
58 params: HashrateResaleDetailParams,
59 ) -> anyhow::Result<RestApiResponse<models::HashrateResaleDetailResponse>>;
60 async fn hashrate_resale_list(
61 &self,
62 params: HashrateResaleListParams,
63 ) -> anyhow::Result<RestApiResponse<models::HashrateResaleListResponse>>;
64 async fn hashrate_resale_request(
65 &self,
66 params: HashrateResaleRequestParams,
67 ) -> anyhow::Result<RestApiResponse<models::HashrateResaleRequestResponse>>;
68 async fn mining_account_earning(
69 &self,
70 params: MiningAccountEarningParams,
71 ) -> anyhow::Result<RestApiResponse<models::MiningAccountEarningResponse>>;
72 async fn request_for_detail_miner_list(
73 &self,
74 params: RequestForDetailMinerListParams,
75 ) -> anyhow::Result<RestApiResponse<models::RequestForDetailMinerListResponse>>;
76 async fn request_for_miner_list(
77 &self,
78 params: RequestForMinerListParams,
79 ) -> anyhow::Result<RestApiResponse<models::RequestForMinerListResponse>>;
80 async fn statistic_list(
81 &self,
82 params: StatisticListParams,
83 ) -> anyhow::Result<RestApiResponse<models::StatisticListResponse>>;
84}
85
86#[derive(Debug, Clone)]
87pub struct MiningApiClient {
88 configuration: ConfigurationRestApi,
89}
90
91impl MiningApiClient {
92 pub fn new(configuration: ConfigurationRestApi) -> Self {
93 Self { configuration }
94 }
95}
96
97#[derive(Clone, Debug, Builder)]
102#[builder(pattern = "owned", build_fn(error = "ParamBuildError"))]
103pub struct AccountListParams {
104 #[builder(setter(into))]
108 pub algo: String,
109 #[builder(setter(into))]
113 pub user_name: String,
114 #[builder(setter(into), default)]
119 pub recv_window: Option<i64>,
120}
121
122impl AccountListParams {
123 #[must_use]
131 pub fn builder(algo: String, user_name: String) -> AccountListParamsBuilder {
132 AccountListParamsBuilder::default()
133 .algo(algo)
134 .user_name(user_name)
135 }
136}
137#[derive(Clone, Debug, Builder)]
142#[builder(pattern = "owned", build_fn(error = "ParamBuildError"))]
143pub struct CancelHashrateResaleConfigurationParams {
144 #[builder(setter(into))]
148 pub config_id: i64,
149 #[builder(setter(into))]
153 pub user_name: String,
154 #[builder(setter(into), default)]
159 pub recv_window: Option<i64>,
160}
161
162impl CancelHashrateResaleConfigurationParams {
163 #[must_use]
171 pub fn builder(
172 config_id: i64,
173 user_name: String,
174 ) -> CancelHashrateResaleConfigurationParamsBuilder {
175 CancelHashrateResaleConfigurationParamsBuilder::default()
176 .config_id(config_id)
177 .user_name(user_name)
178 }
179}
180#[derive(Clone, Debug, Builder)]
185#[builder(pattern = "owned", build_fn(error = "ParamBuildError"))]
186pub struct EarningsListParams {
187 #[builder(setter(into))]
191 pub algo: String,
192 #[builder(setter(into))]
196 pub user_name: String,
197 #[builder(setter(into), default)]
201 pub coin: Option<String>,
202 #[builder(setter(into), default)]
206 pub start_date: Option<i64>,
207 #[builder(setter(into), default)]
211 pub end_date: Option<i64>,
212 #[builder(setter(into), default)]
216 pub page_index: Option<i64>,
217 #[builder(setter(into), default)]
221 pub page_size: Option<i64>,
222 #[builder(setter(into), default)]
227 pub recv_window: Option<i64>,
228}
229
230impl EarningsListParams {
231 #[must_use]
239 pub fn builder(algo: String, user_name: String) -> EarningsListParamsBuilder {
240 EarningsListParamsBuilder::default()
241 .algo(algo)
242 .user_name(user_name)
243 }
244}
245#[derive(Clone, Debug, Builder)]
250#[builder(pattern = "owned", build_fn(error = "ParamBuildError"))]
251pub struct ExtraBonusListParams {
252 #[builder(setter(into))]
256 pub algo: String,
257 #[builder(setter(into))]
261 pub user_name: String,
262 #[builder(setter(into), default)]
266 pub coin: Option<String>,
267 #[builder(setter(into), default)]
271 pub start_date: Option<i64>,
272 #[builder(setter(into), default)]
276 pub end_date: Option<i64>,
277 #[builder(setter(into), default)]
281 pub page_index: Option<i64>,
282 #[builder(setter(into), default)]
286 pub page_size: Option<i64>,
287 #[builder(setter(into), default)]
292 pub recv_window: Option<i64>,
293}
294
295impl ExtraBonusListParams {
296 #[must_use]
304 pub fn builder(algo: String, user_name: String) -> ExtraBonusListParamsBuilder {
305 ExtraBonusListParamsBuilder::default()
306 .algo(algo)
307 .user_name(user_name)
308 }
309}
310#[derive(Clone, Debug, Builder)]
315#[builder(pattern = "owned", build_fn(error = "ParamBuildError"))]
316pub struct HashrateResaleDetailParams {
317 #[builder(setter(into))]
321 pub config_id: i64,
322 #[builder(setter(into), default)]
326 pub page_index: Option<i64>,
327 #[builder(setter(into), default)]
331 pub page_size: Option<i64>,
332 #[builder(setter(into), default)]
337 pub recv_window: Option<i64>,
338}
339
340impl HashrateResaleDetailParams {
341 #[must_use]
348 pub fn builder(config_id: i64) -> HashrateResaleDetailParamsBuilder {
349 HashrateResaleDetailParamsBuilder::default().config_id(config_id)
350 }
351}
352#[derive(Clone, Debug, Builder, Default)]
357#[builder(pattern = "owned", build_fn(error = "ParamBuildError"))]
358pub struct HashrateResaleListParams {
359 #[builder(setter(into), default)]
363 pub page_index: Option<i64>,
364 #[builder(setter(into), default)]
368 pub page_size: Option<i64>,
369 #[builder(setter(into), default)]
374 pub recv_window: Option<i64>,
375}
376
377impl HashrateResaleListParams {
378 #[must_use]
381 pub fn builder() -> HashrateResaleListParamsBuilder {
382 HashrateResaleListParamsBuilder::default()
383 }
384}
385#[derive(Clone, Debug, Builder)]
390#[builder(pattern = "owned", build_fn(error = "ParamBuildError"))]
391pub struct HashrateResaleRequestParams {
392 #[builder(setter(into))]
396 pub user_name: String,
397 #[builder(setter(into))]
401 pub algo: String,
402 #[builder(setter(into))]
406 pub end_date: i64,
407 #[builder(setter(into))]
411 pub start_date: i64,
412 #[builder(setter(into))]
416 pub to_pool_user: String,
417 #[builder(setter(into))]
421 pub hash_rate: i64,
422 #[builder(setter(into), default)]
427 pub recv_window: Option<i64>,
428}
429
430impl HashrateResaleRequestParams {
431 #[must_use]
443 pub fn builder(
444 user_name: String,
445 algo: String,
446 end_date: i64,
447 start_date: i64,
448 to_pool_user: String,
449 hash_rate: i64,
450 ) -> HashrateResaleRequestParamsBuilder {
451 HashrateResaleRequestParamsBuilder::default()
452 .user_name(user_name)
453 .algo(algo)
454 .end_date(end_date)
455 .start_date(start_date)
456 .to_pool_user(to_pool_user)
457 .hash_rate(hash_rate)
458 }
459}
460#[derive(Clone, Debug, Builder)]
465#[builder(pattern = "owned", build_fn(error = "ParamBuildError"))]
466pub struct MiningAccountEarningParams {
467 #[builder(setter(into))]
471 pub algo: String,
472 #[builder(setter(into), default)]
476 pub start_date: Option<i64>,
477 #[builder(setter(into), default)]
481 pub end_date: Option<i64>,
482 #[builder(setter(into), default)]
486 pub page_index: Option<i64>,
487 #[builder(setter(into), default)]
491 pub page_size: Option<i64>,
492 #[builder(setter(into), default)]
497 pub recv_window: Option<i64>,
498}
499
500impl MiningAccountEarningParams {
501 #[must_use]
508 pub fn builder(algo: String) -> MiningAccountEarningParamsBuilder {
509 MiningAccountEarningParamsBuilder::default().algo(algo)
510 }
511}
512#[derive(Clone, Debug, Builder)]
517#[builder(pattern = "owned", build_fn(error = "ParamBuildError"))]
518pub struct RequestForDetailMinerListParams {
519 #[builder(setter(into))]
523 pub algo: String,
524 #[builder(setter(into))]
528 pub user_name: String,
529 #[builder(setter(into))]
533 pub worker_name: String,
534 #[builder(setter(into), default)]
539 pub recv_window: Option<i64>,
540}
541
542impl RequestForDetailMinerListParams {
543 #[must_use]
552 pub fn builder(
553 algo: String,
554 user_name: String,
555 worker_name: String,
556 ) -> RequestForDetailMinerListParamsBuilder {
557 RequestForDetailMinerListParamsBuilder::default()
558 .algo(algo)
559 .user_name(user_name)
560 .worker_name(worker_name)
561 }
562}
563#[derive(Clone, Debug, Builder)]
568#[builder(pattern = "owned", build_fn(error = "ParamBuildError"))]
569pub struct RequestForMinerListParams {
570 #[builder(setter(into))]
574 pub algo: String,
575 #[builder(setter(into))]
579 pub user_name: String,
580 #[builder(setter(into), default)]
584 pub page_index: Option<i64>,
585 #[builder(setter(into), default)]
589 pub sort: Option<i64>,
590 #[builder(setter(into), default)]
594 pub sort_column: Option<i64>,
595 #[builder(setter(into), default)]
599 pub worker_status: Option<i64>,
600 #[builder(setter(into), default)]
605 pub recv_window: Option<i64>,
606}
607
608impl RequestForMinerListParams {
609 #[must_use]
617 pub fn builder(algo: String, user_name: String) -> RequestForMinerListParamsBuilder {
618 RequestForMinerListParamsBuilder::default()
619 .algo(algo)
620 .user_name(user_name)
621 }
622}
623#[derive(Clone, Debug, Builder)]
628#[builder(pattern = "owned", build_fn(error = "ParamBuildError"))]
629pub struct StatisticListParams {
630 #[builder(setter(into))]
634 pub algo: String,
635 #[builder(setter(into))]
639 pub user_name: String,
640 #[builder(setter(into), default)]
645 pub recv_window: Option<i64>,
646}
647
648impl StatisticListParams {
649 #[must_use]
657 pub fn builder(algo: String, user_name: String) -> StatisticListParamsBuilder {
658 StatisticListParamsBuilder::default()
659 .algo(algo)
660 .user_name(user_name)
661 }
662}
663
664#[async_trait]
665impl MiningApi for MiningApiClient {
666 async fn account_list(
667 &self,
668 params: AccountListParams,
669 ) -> anyhow::Result<RestApiResponse<models::AccountListResponse>> {
670 let AccountListParams {
671 algo,
672 user_name,
673 recv_window,
674 } = params;
675
676 let mut query_params = BTreeMap::new();
677 let body_params = BTreeMap::new();
678
679 query_params.insert("algo".to_string(), json!(algo));
680
681 query_params.insert("userName".to_string(), json!(user_name));
682
683 if let Some(rw) = recv_window {
684 query_params.insert("recvWindow".to_string(), json!(rw));
685 }
686
687 send_request::<models::AccountListResponse>(
688 &self.configuration,
689 "/sapi/v1/mining/statistics/user/list",
690 reqwest::Method::GET,
691 query_params,
692 body_params,
693 if HAS_TIME_UNIT {
694 self.configuration.time_unit
695 } else {
696 None
697 },
698 true,
699 )
700 .await
701 }
702
703 async fn acquiring_algorithm(
704 &self,
705 ) -> anyhow::Result<RestApiResponse<models::AcquiringAlgorithmResponse>> {
706 let query_params = BTreeMap::new();
707 let body_params = BTreeMap::new();
708
709 send_request::<models::AcquiringAlgorithmResponse>(
710 &self.configuration,
711 "/sapi/v1/mining/pub/algoList",
712 reqwest::Method::GET,
713 query_params,
714 body_params,
715 if HAS_TIME_UNIT {
716 self.configuration.time_unit
717 } else {
718 None
719 },
720 false,
721 )
722 .await
723 }
724
725 async fn acquiring_coinname(
726 &self,
727 ) -> anyhow::Result<RestApiResponse<models::AcquiringCoinnameResponse>> {
728 let query_params = BTreeMap::new();
729 let body_params = BTreeMap::new();
730
731 send_request::<models::AcquiringCoinnameResponse>(
732 &self.configuration,
733 "/sapi/v1/mining/pub/coinList",
734 reqwest::Method::GET,
735 query_params,
736 body_params,
737 if HAS_TIME_UNIT {
738 self.configuration.time_unit
739 } else {
740 None
741 },
742 false,
743 )
744 .await
745 }
746
747 async fn cancel_hashrate_resale_configuration(
748 &self,
749 params: CancelHashrateResaleConfigurationParams,
750 ) -> anyhow::Result<RestApiResponse<models::CancelHashrateResaleConfigurationResponse>> {
751 let CancelHashrateResaleConfigurationParams {
752 config_id,
753 user_name,
754 recv_window,
755 } = params;
756
757 let mut query_params = BTreeMap::new();
758 let body_params = BTreeMap::new();
759
760 query_params.insert("configId".to_string(), json!(config_id));
761
762 query_params.insert("userName".to_string(), json!(user_name));
763
764 if let Some(rw) = recv_window {
765 query_params.insert("recvWindow".to_string(), json!(rw));
766 }
767
768 send_request::<models::CancelHashrateResaleConfigurationResponse>(
769 &self.configuration,
770 "/sapi/v1/mining/hash-transfer/config/cancel",
771 reqwest::Method::POST,
772 query_params,
773 body_params,
774 if HAS_TIME_UNIT {
775 self.configuration.time_unit
776 } else {
777 None
778 },
779 true,
780 )
781 .await
782 }
783
784 async fn earnings_list(
785 &self,
786 params: EarningsListParams,
787 ) -> anyhow::Result<RestApiResponse<models::EarningsListResponse>> {
788 let EarningsListParams {
789 algo,
790 user_name,
791 coin,
792 start_date,
793 end_date,
794 page_index,
795 page_size,
796 recv_window,
797 } = params;
798
799 let mut query_params = BTreeMap::new();
800 let body_params = BTreeMap::new();
801
802 query_params.insert("algo".to_string(), json!(algo));
803
804 query_params.insert("userName".to_string(), json!(user_name));
805
806 if let Some(rw) = coin {
807 query_params.insert("coin".to_string(), json!(rw));
808 }
809
810 if let Some(rw) = start_date {
811 query_params.insert("startDate".to_string(), json!(rw));
812 }
813
814 if let Some(rw) = end_date {
815 query_params.insert("endDate".to_string(), json!(rw));
816 }
817
818 if let Some(rw) = page_index {
819 query_params.insert("pageIndex".to_string(), json!(rw));
820 }
821
822 if let Some(rw) = page_size {
823 query_params.insert("pageSize".to_string(), json!(rw));
824 }
825
826 if let Some(rw) = recv_window {
827 query_params.insert("recvWindow".to_string(), json!(rw));
828 }
829
830 send_request::<models::EarningsListResponse>(
831 &self.configuration,
832 "/sapi/v1/mining/payment/list",
833 reqwest::Method::GET,
834 query_params,
835 body_params,
836 if HAS_TIME_UNIT {
837 self.configuration.time_unit
838 } else {
839 None
840 },
841 true,
842 )
843 .await
844 }
845
846 async fn extra_bonus_list(
847 &self,
848 params: ExtraBonusListParams,
849 ) -> anyhow::Result<RestApiResponse<models::ExtraBonusListResponse>> {
850 let ExtraBonusListParams {
851 algo,
852 user_name,
853 coin,
854 start_date,
855 end_date,
856 page_index,
857 page_size,
858 recv_window,
859 } = params;
860
861 let mut query_params = BTreeMap::new();
862 let body_params = BTreeMap::new();
863
864 query_params.insert("algo".to_string(), json!(algo));
865
866 query_params.insert("userName".to_string(), json!(user_name));
867
868 if let Some(rw) = coin {
869 query_params.insert("coin".to_string(), json!(rw));
870 }
871
872 if let Some(rw) = start_date {
873 query_params.insert("startDate".to_string(), json!(rw));
874 }
875
876 if let Some(rw) = end_date {
877 query_params.insert("endDate".to_string(), json!(rw));
878 }
879
880 if let Some(rw) = page_index {
881 query_params.insert("pageIndex".to_string(), json!(rw));
882 }
883
884 if let Some(rw) = page_size {
885 query_params.insert("pageSize".to_string(), json!(rw));
886 }
887
888 if let Some(rw) = recv_window {
889 query_params.insert("recvWindow".to_string(), json!(rw));
890 }
891
892 send_request::<models::ExtraBonusListResponse>(
893 &self.configuration,
894 "/sapi/v1/mining/payment/other",
895 reqwest::Method::GET,
896 query_params,
897 body_params,
898 if HAS_TIME_UNIT {
899 self.configuration.time_unit
900 } else {
901 None
902 },
903 true,
904 )
905 .await
906 }
907
908 async fn hashrate_resale_detail(
909 &self,
910 params: HashrateResaleDetailParams,
911 ) -> anyhow::Result<RestApiResponse<models::HashrateResaleDetailResponse>> {
912 let HashrateResaleDetailParams {
913 config_id,
914 page_index,
915 page_size,
916 recv_window,
917 } = params;
918
919 let mut query_params = BTreeMap::new();
920 let body_params = BTreeMap::new();
921
922 query_params.insert("configId".to_string(), json!(config_id));
923
924 if let Some(rw) = page_index {
925 query_params.insert("pageIndex".to_string(), json!(rw));
926 }
927
928 if let Some(rw) = page_size {
929 query_params.insert("pageSize".to_string(), json!(rw));
930 }
931
932 if let Some(rw) = recv_window {
933 query_params.insert("recvWindow".to_string(), json!(rw));
934 }
935
936 send_request::<models::HashrateResaleDetailResponse>(
937 &self.configuration,
938 "/sapi/v1/mining/hash-transfer/profit/details",
939 reqwest::Method::GET,
940 query_params,
941 body_params,
942 if HAS_TIME_UNIT {
943 self.configuration.time_unit
944 } else {
945 None
946 },
947 true,
948 )
949 .await
950 }
951
952 async fn hashrate_resale_list(
953 &self,
954 params: HashrateResaleListParams,
955 ) -> anyhow::Result<RestApiResponse<models::HashrateResaleListResponse>> {
956 let HashrateResaleListParams {
957 page_index,
958 page_size,
959 recv_window,
960 } = params;
961
962 let mut query_params = BTreeMap::new();
963 let body_params = BTreeMap::new();
964
965 if let Some(rw) = page_index {
966 query_params.insert("pageIndex".to_string(), json!(rw));
967 }
968
969 if let Some(rw) = page_size {
970 query_params.insert("pageSize".to_string(), json!(rw));
971 }
972
973 if let Some(rw) = recv_window {
974 query_params.insert("recvWindow".to_string(), json!(rw));
975 }
976
977 send_request::<models::HashrateResaleListResponse>(
978 &self.configuration,
979 "/sapi/v1/mining/hash-transfer/config/details/list",
980 reqwest::Method::GET,
981 query_params,
982 body_params,
983 if HAS_TIME_UNIT {
984 self.configuration.time_unit
985 } else {
986 None
987 },
988 true,
989 )
990 .await
991 }
992
993 async fn hashrate_resale_request(
994 &self,
995 params: HashrateResaleRequestParams,
996 ) -> anyhow::Result<RestApiResponse<models::HashrateResaleRequestResponse>> {
997 let HashrateResaleRequestParams {
998 user_name,
999 algo,
1000 end_date,
1001 start_date,
1002 to_pool_user,
1003 hash_rate,
1004 recv_window,
1005 } = params;
1006
1007 let mut query_params = BTreeMap::new();
1008 let body_params = BTreeMap::new();
1009
1010 query_params.insert("userName".to_string(), json!(user_name));
1011
1012 query_params.insert("algo".to_string(), json!(algo));
1013
1014 query_params.insert("endDate".to_string(), json!(end_date));
1015
1016 query_params.insert("startDate".to_string(), json!(start_date));
1017
1018 query_params.insert("toPoolUser".to_string(), json!(to_pool_user));
1019
1020 query_params.insert("hashRate".to_string(), json!(hash_rate));
1021
1022 if let Some(rw) = recv_window {
1023 query_params.insert("recvWindow".to_string(), json!(rw));
1024 }
1025
1026 send_request::<models::HashrateResaleRequestResponse>(
1027 &self.configuration,
1028 "/sapi/v1/mining/hash-transfer/config",
1029 reqwest::Method::POST,
1030 query_params,
1031 body_params,
1032 if HAS_TIME_UNIT {
1033 self.configuration.time_unit
1034 } else {
1035 None
1036 },
1037 true,
1038 )
1039 .await
1040 }
1041
1042 async fn mining_account_earning(
1043 &self,
1044 params: MiningAccountEarningParams,
1045 ) -> anyhow::Result<RestApiResponse<models::MiningAccountEarningResponse>> {
1046 let MiningAccountEarningParams {
1047 algo,
1048 start_date,
1049 end_date,
1050 page_index,
1051 page_size,
1052 recv_window,
1053 } = params;
1054
1055 let mut query_params = BTreeMap::new();
1056 let body_params = BTreeMap::new();
1057
1058 query_params.insert("algo".to_string(), json!(algo));
1059
1060 if let Some(rw) = start_date {
1061 query_params.insert("startDate".to_string(), json!(rw));
1062 }
1063
1064 if let Some(rw) = end_date {
1065 query_params.insert("endDate".to_string(), json!(rw));
1066 }
1067
1068 if let Some(rw) = page_index {
1069 query_params.insert("pageIndex".to_string(), json!(rw));
1070 }
1071
1072 if let Some(rw) = page_size {
1073 query_params.insert("pageSize".to_string(), json!(rw));
1074 }
1075
1076 if let Some(rw) = recv_window {
1077 query_params.insert("recvWindow".to_string(), json!(rw));
1078 }
1079
1080 send_request::<models::MiningAccountEarningResponse>(
1081 &self.configuration,
1082 "/sapi/v1/mining/payment/uid",
1083 reqwest::Method::GET,
1084 query_params,
1085 body_params,
1086 if HAS_TIME_UNIT {
1087 self.configuration.time_unit
1088 } else {
1089 None
1090 },
1091 true,
1092 )
1093 .await
1094 }
1095
1096 async fn request_for_detail_miner_list(
1097 &self,
1098 params: RequestForDetailMinerListParams,
1099 ) -> anyhow::Result<RestApiResponse<models::RequestForDetailMinerListResponse>> {
1100 let RequestForDetailMinerListParams {
1101 algo,
1102 user_name,
1103 worker_name,
1104 recv_window,
1105 } = params;
1106
1107 let mut query_params = BTreeMap::new();
1108 let body_params = BTreeMap::new();
1109
1110 query_params.insert("algo".to_string(), json!(algo));
1111
1112 query_params.insert("userName".to_string(), json!(user_name));
1113
1114 query_params.insert("workerName".to_string(), json!(worker_name));
1115
1116 if let Some(rw) = recv_window {
1117 query_params.insert("recvWindow".to_string(), json!(rw));
1118 }
1119
1120 send_request::<models::RequestForDetailMinerListResponse>(
1121 &self.configuration,
1122 "/sapi/v1/mining/worker/detail",
1123 reqwest::Method::GET,
1124 query_params,
1125 body_params,
1126 if HAS_TIME_UNIT {
1127 self.configuration.time_unit
1128 } else {
1129 None
1130 },
1131 true,
1132 )
1133 .await
1134 }
1135
1136 async fn request_for_miner_list(
1137 &self,
1138 params: RequestForMinerListParams,
1139 ) -> anyhow::Result<RestApiResponse<models::RequestForMinerListResponse>> {
1140 let RequestForMinerListParams {
1141 algo,
1142 user_name,
1143 page_index,
1144 sort,
1145 sort_column,
1146 worker_status,
1147 recv_window,
1148 } = params;
1149
1150 let mut query_params = BTreeMap::new();
1151 let body_params = BTreeMap::new();
1152
1153 query_params.insert("algo".to_string(), json!(algo));
1154
1155 query_params.insert("userName".to_string(), json!(user_name));
1156
1157 if let Some(rw) = page_index {
1158 query_params.insert("pageIndex".to_string(), json!(rw));
1159 }
1160
1161 if let Some(rw) = sort {
1162 query_params.insert("sort".to_string(), json!(rw));
1163 }
1164
1165 if let Some(rw) = sort_column {
1166 query_params.insert("sortColumn".to_string(), json!(rw));
1167 }
1168
1169 if let Some(rw) = worker_status {
1170 query_params.insert("workerStatus".to_string(), json!(rw));
1171 }
1172
1173 if let Some(rw) = recv_window {
1174 query_params.insert("recvWindow".to_string(), json!(rw));
1175 }
1176
1177 send_request::<models::RequestForMinerListResponse>(
1178 &self.configuration,
1179 "/sapi/v1/mining/worker/list",
1180 reqwest::Method::GET,
1181 query_params,
1182 body_params,
1183 if HAS_TIME_UNIT {
1184 self.configuration.time_unit
1185 } else {
1186 None
1187 },
1188 true,
1189 )
1190 .await
1191 }
1192
1193 async fn statistic_list(
1194 &self,
1195 params: StatisticListParams,
1196 ) -> anyhow::Result<RestApiResponse<models::StatisticListResponse>> {
1197 let StatisticListParams {
1198 algo,
1199 user_name,
1200 recv_window,
1201 } = params;
1202
1203 let mut query_params = BTreeMap::new();
1204 let body_params = BTreeMap::new();
1205
1206 query_params.insert("algo".to_string(), json!(algo));
1207
1208 query_params.insert("userName".to_string(), json!(user_name));
1209
1210 if let Some(rw) = recv_window {
1211 query_params.insert("recvWindow".to_string(), json!(rw));
1212 }
1213
1214 send_request::<models::StatisticListResponse>(
1215 &self.configuration,
1216 "/sapi/v1/mining/statistics/user/status",
1217 reqwest::Method::GET,
1218 query_params,
1219 body_params,
1220 if HAS_TIME_UNIT {
1221 self.configuration.time_unit
1222 } else {
1223 None
1224 },
1225 true,
1226 )
1227 .await
1228 }
1229}
1230
1231#[cfg(all(test, feature = "mining"))]
1232mod tests {
1233 use super::*;
1234 use crate::TOKIO_SHARED_RT;
1235 use crate::{errors::ConnectorError, models::DataFuture, models::RestApiRateLimit};
1236 use async_trait::async_trait;
1237 use std::collections::HashMap;
1238
1239 struct DummyRestApiResponse<T> {
1240 inner: Box<dyn FnOnce() -> DataFuture<Result<T, ConnectorError>> + Send + Sync>,
1241 status: u16,
1242 headers: HashMap<String, String>,
1243 rate_limits: Option<Vec<RestApiRateLimit>>,
1244 }
1245
1246 impl<T> From<DummyRestApiResponse<T>> for RestApiResponse<T> {
1247 fn from(dummy: DummyRestApiResponse<T>) -> Self {
1248 Self {
1249 data_fn: dummy.inner,
1250 status: dummy.status,
1251 headers: dummy.headers,
1252 rate_limits: dummy.rate_limits,
1253 }
1254 }
1255 }
1256
1257 struct MockMiningApiClient {
1258 force_error: bool,
1259 }
1260
1261 #[async_trait]
1262 impl MiningApi for MockMiningApiClient {
1263 async fn account_list(
1264 &self,
1265 _params: AccountListParams,
1266 ) -> anyhow::Result<RestApiResponse<models::AccountListResponse>> {
1267 if self.force_error {
1268 return Err(ConnectorError::ConnectorClientError {
1269 msg: "ResponseError".to_string(),
1270 code: None,
1271 }
1272 .into());
1273 }
1274
1275 let resp_json: Value = serde_json::from_str(r#"{"code":0,"msg":"","data":[{"type":"H_hashrate","userName":"test","list":[{"time":1585267200000,"hashrate":"0.00000000","reject":"0.00000000"},{"time":1585353600000,"hashrate":"0.00000000","reject":"0.00000000"}]},{"type":"D_hashrate","userName":"test","list":[{"time":1587906000000,"hashrate":"0.00000000","reject":"0.00000000"},{"time":1587909600000,"hashrate":"0.00000000","reject":"0.00000000"}]}]}"#).unwrap();
1276 let dummy_response: models::AccountListResponse =
1277 serde_json::from_value(resp_json.clone())
1278 .expect("should parse into models::AccountListResponse");
1279
1280 let dummy = DummyRestApiResponse {
1281 inner: Box::new(move || Box::pin(async move { Ok(dummy_response) })),
1282 status: 200,
1283 headers: HashMap::new(),
1284 rate_limits: None,
1285 };
1286
1287 Ok(dummy.into())
1288 }
1289
1290 async fn acquiring_algorithm(
1291 &self,
1292 ) -> anyhow::Result<RestApiResponse<models::AcquiringAlgorithmResponse>> {
1293 if self.force_error {
1294 return Err(ConnectorError::ConnectorClientError {
1295 msg: "ResponseError".to_string(),
1296 code: None,
1297 }
1298 .into());
1299 }
1300
1301 let resp_json: Value = serde_json::from_str(r#"{"code":0,"msg":"","data":[{"algoName":"sha256","algoId":1,"poolIndex":0,"unit":"h/s"}]}"#).unwrap();
1302 let dummy_response: models::AcquiringAlgorithmResponse =
1303 serde_json::from_value(resp_json.clone())
1304 .expect("should parse into models::AcquiringAlgorithmResponse");
1305
1306 let dummy = DummyRestApiResponse {
1307 inner: Box::new(move || Box::pin(async move { Ok(dummy_response) })),
1308 status: 200,
1309 headers: HashMap::new(),
1310 rate_limits: None,
1311 };
1312
1313 Ok(dummy.into())
1314 }
1315
1316 async fn acquiring_coinname(
1317 &self,
1318 ) -> anyhow::Result<RestApiResponse<models::AcquiringCoinnameResponse>> {
1319 if self.force_error {
1320 return Err(ConnectorError::ConnectorClientError {
1321 msg: "ResponseError".to_string(),
1322 code: None,
1323 }
1324 .into());
1325 }
1326
1327 let resp_json: Value = serde_json::from_str(r#"{"code":0,"msg":"","data":[{"coinName":"BTC","coinId":1,"poolIndex":0,"algoId":1,"algoName":"sha256"}]}"#).unwrap();
1328 let dummy_response: models::AcquiringCoinnameResponse =
1329 serde_json::from_value(resp_json.clone())
1330 .expect("should parse into models::AcquiringCoinnameResponse");
1331
1332 let dummy = DummyRestApiResponse {
1333 inner: Box::new(move || Box::pin(async move { Ok(dummy_response) })),
1334 status: 200,
1335 headers: HashMap::new(),
1336 rate_limits: None,
1337 };
1338
1339 Ok(dummy.into())
1340 }
1341
1342 async fn cancel_hashrate_resale_configuration(
1343 &self,
1344 _params: CancelHashrateResaleConfigurationParams,
1345 ) -> anyhow::Result<RestApiResponse<models::CancelHashrateResaleConfigurationResponse>>
1346 {
1347 if self.force_error {
1348 return Err(ConnectorError::ConnectorClientError {
1349 msg: "ResponseError".to_string(),
1350 code: None,
1351 }
1352 .into());
1353 }
1354
1355 let resp_json: Value =
1356 serde_json::from_str(r#"{"code":0,"msg":"","data":true}"#).unwrap();
1357 let dummy_response: models::CancelHashrateResaleConfigurationResponse =
1358 serde_json::from_value(resp_json.clone())
1359 .expect("should parse into models::CancelHashrateResaleConfigurationResponse");
1360
1361 let dummy = DummyRestApiResponse {
1362 inner: Box::new(move || Box::pin(async move { Ok(dummy_response) })),
1363 status: 200,
1364 headers: HashMap::new(),
1365 rate_limits: None,
1366 };
1367
1368 Ok(dummy.into())
1369 }
1370
1371 async fn earnings_list(
1372 &self,
1373 _params: EarningsListParams,
1374 ) -> anyhow::Result<RestApiResponse<models::EarningsListResponse>> {
1375 if self.force_error {
1376 return Err(ConnectorError::ConnectorClientError {
1377 msg: "ResponseError".to_string(),
1378 code: None,
1379 }
1380 .into());
1381 }
1382
1383 let resp_json: Value = serde_json::from_str(r#"{"code":0,"msg":"","data":{"accountProfits":[{"time":1586188800000,"type":31,"hashTransfer":null,"transferAmount":null,"dayHashRate":129129903378244,"profitAmount":8.6083060304,"coinName":"BTC","status":2},{"time":1607529600000,"coinName":"BTC","type":0,"dayHashRate":9942053925926,"profitAmount":0.85426469,"hashTransfer":200000000000,"transferAmount":0.02180958,"status":2},{"time":1607443200000,"coinName":"BTC","type":31,"dayHashRate":200000000000,"profitAmount":0.02905916,"hashTransfer":null,"transferAmount":null,"status":2}],"totalNum":3,"pageSize":20}}"#).unwrap();
1384 let dummy_response: models::EarningsListResponse =
1385 serde_json::from_value(resp_json.clone())
1386 .expect("should parse into models::EarningsListResponse");
1387
1388 let dummy = DummyRestApiResponse {
1389 inner: Box::new(move || Box::pin(async move { Ok(dummy_response) })),
1390 status: 200,
1391 headers: HashMap::new(),
1392 rate_limits: None,
1393 };
1394
1395 Ok(dummy.into())
1396 }
1397
1398 async fn extra_bonus_list(
1399 &self,
1400 _params: ExtraBonusListParams,
1401 ) -> anyhow::Result<RestApiResponse<models::ExtraBonusListResponse>> {
1402 if self.force_error {
1403 return Err(ConnectorError::ConnectorClientError {
1404 msg: "ResponseError".to_string(),
1405 code: None,
1406 }
1407 .into());
1408 }
1409
1410 let resp_json: Value = serde_json::from_str(r#"{"code":0,"msg":"","data":{"otherProfits":[{"time":1607443200000,"coinName":"BTC","type":4,"profitAmount":0.0011859,"status":2}],"totalNum":3,"pageSize":20}}"#).unwrap();
1411 let dummy_response: models::ExtraBonusListResponse =
1412 serde_json::from_value(resp_json.clone())
1413 .expect("should parse into models::ExtraBonusListResponse");
1414
1415 let dummy = DummyRestApiResponse {
1416 inner: Box::new(move || Box::pin(async move { Ok(dummy_response) })),
1417 status: 200,
1418 headers: HashMap::new(),
1419 rate_limits: None,
1420 };
1421
1422 Ok(dummy.into())
1423 }
1424
1425 async fn hashrate_resale_detail(
1426 &self,
1427 _params: HashrateResaleDetailParams,
1428 ) -> anyhow::Result<RestApiResponse<models::HashrateResaleDetailResponse>> {
1429 if self.force_error {
1430 return Err(ConnectorError::ConnectorClientError {
1431 msg: "ResponseError".to_string(),
1432 code: None,
1433 }
1434 .into());
1435 }
1436
1437 let resp_json: Value = serde_json::from_str(r#"{"code":0,"msg":"","data":{"profitTransferDetails":[{"poolUsername":"test4001","toPoolUsername":"pop","algoName":"sha256","hashRate":200000000000,"day":20201213,"amount":0.2256872,"coinName":"BTC"},{"poolUsername":"test4001","toPoolUsername":"pop","algoName":"sha256","hashRate":200000000000,"day":20201213,"amount":0.2256872,"coinName":"BTC"}],"totalNum":8,"pageSize":200}}"#).unwrap();
1438 let dummy_response: models::HashrateResaleDetailResponse =
1439 serde_json::from_value(resp_json.clone())
1440 .expect("should parse into models::HashrateResaleDetailResponse");
1441
1442 let dummy = DummyRestApiResponse {
1443 inner: Box::new(move || Box::pin(async move { Ok(dummy_response) })),
1444 status: 200,
1445 headers: HashMap::new(),
1446 rate_limits: None,
1447 };
1448
1449 Ok(dummy.into())
1450 }
1451
1452 async fn hashrate_resale_list(
1453 &self,
1454 _params: HashrateResaleListParams,
1455 ) -> anyhow::Result<RestApiResponse<models::HashrateResaleListResponse>> {
1456 if self.force_error {
1457 return Err(ConnectorError::ConnectorClientError {
1458 msg: "ResponseError".to_string(),
1459 code: None,
1460 }
1461 .into());
1462 }
1463
1464 let resp_json: Value = serde_json::from_str(r#"{"code":0,"msg":"","data":{"configDetails":[{"configId":168,"poolUsername":"123","toPoolUsername":"user1","algoName":"Ethash","hashRate":5000000,"startDay":20201210,"endDay":20210405,"status":1,"type":0},{"configId":166,"poolUsername":"pop","toPoolUsername":"111111","algoName":"Ethash","hashRate":3320000,"startDay":20201226,"endDay":20201227,"status":0,"type":0}],"totalNum":21,"pageSize":200}}"#).unwrap();
1465 let dummy_response: models::HashrateResaleListResponse =
1466 serde_json::from_value(resp_json.clone())
1467 .expect("should parse into models::HashrateResaleListResponse");
1468
1469 let dummy = DummyRestApiResponse {
1470 inner: Box::new(move || Box::pin(async move { Ok(dummy_response) })),
1471 status: 200,
1472 headers: HashMap::new(),
1473 rate_limits: None,
1474 };
1475
1476 Ok(dummy.into())
1477 }
1478
1479 async fn hashrate_resale_request(
1480 &self,
1481 _params: HashrateResaleRequestParams,
1482 ) -> anyhow::Result<RestApiResponse<models::HashrateResaleRequestResponse>> {
1483 if self.force_error {
1484 return Err(ConnectorError::ConnectorClientError {
1485 msg: "ResponseError".to_string(),
1486 code: None,
1487 }
1488 .into());
1489 }
1490
1491 let resp_json: Value =
1492 serde_json::from_str(r#"{"code":0,"msg":"","data":171}"#).unwrap();
1493 let dummy_response: models::HashrateResaleRequestResponse =
1494 serde_json::from_value(resp_json.clone())
1495 .expect("should parse into models::HashrateResaleRequestResponse");
1496
1497 let dummy = DummyRestApiResponse {
1498 inner: Box::new(move || Box::pin(async move { Ok(dummy_response) })),
1499 status: 200,
1500 headers: HashMap::new(),
1501 rate_limits: None,
1502 };
1503
1504 Ok(dummy.into())
1505 }
1506
1507 async fn mining_account_earning(
1508 &self,
1509 _params: MiningAccountEarningParams,
1510 ) -> anyhow::Result<RestApiResponse<models::MiningAccountEarningResponse>> {
1511 if self.force_error {
1512 return Err(ConnectorError::ConnectorClientError {
1513 msg: "ResponseError".to_string(),
1514 code: None,
1515 }
1516 .into());
1517 }
1518
1519 let resp_json: Value = serde_json::from_str(r#"{"code":0,"msg":"","data":{"accountProfits":[{"time":1607443200000,"coinName":"BTC","type":2,"puid":59985472,"subName":"vdvaghani","amount":0.09186957}],"totalNum":3,"pageSize":20}}"#).unwrap();
1520 let dummy_response: models::MiningAccountEarningResponse =
1521 serde_json::from_value(resp_json.clone())
1522 .expect("should parse into models::MiningAccountEarningResponse");
1523
1524 let dummy = DummyRestApiResponse {
1525 inner: Box::new(move || Box::pin(async move { Ok(dummy_response) })),
1526 status: 200,
1527 headers: HashMap::new(),
1528 rate_limits: None,
1529 };
1530
1531 Ok(dummy.into())
1532 }
1533
1534 async fn request_for_detail_miner_list(
1535 &self,
1536 _params: RequestForDetailMinerListParams,
1537 ) -> anyhow::Result<RestApiResponse<models::RequestForDetailMinerListResponse>> {
1538 if self.force_error {
1539 return Err(ConnectorError::ConnectorClientError {
1540 msg: "ResponseError".to_string(),
1541 code: None,
1542 }
1543 .into());
1544 }
1545
1546 let resp_json: Value = serde_json::from_str(r#"{"code":0,"msg":"","data":[{"workerName":"bhdc1.16A10404B","type":"H_hashrate","hashrateDatas":[{"time":1587902400000,"hashrate":"0","reject":0},{"time":1587906000000,"hashrate":"0","reject":0}]},{"workerName":"bhdc1.16A10404B","type":"D_hashrate","hashrateDatas":[{"time":1587902400000,"hashrate":"0","reject":0},{"time":1587906000000,"hashrate":"0","reject":0}]}]}"#).unwrap();
1547 let dummy_response: models::RequestForDetailMinerListResponse =
1548 serde_json::from_value(resp_json.clone())
1549 .expect("should parse into models::RequestForDetailMinerListResponse");
1550
1551 let dummy = DummyRestApiResponse {
1552 inner: Box::new(move || Box::pin(async move { Ok(dummy_response) })),
1553 status: 200,
1554 headers: HashMap::new(),
1555 rate_limits: None,
1556 };
1557
1558 Ok(dummy.into())
1559 }
1560
1561 async fn request_for_miner_list(
1562 &self,
1563 _params: RequestForMinerListParams,
1564 ) -> anyhow::Result<RestApiResponse<models::RequestForMinerListResponse>> {
1565 if self.force_error {
1566 return Err(ConnectorError::ConnectorClientError {
1567 msg: "ResponseError".to_string(),
1568 code: None,
1569 }
1570 .into());
1571 }
1572
1573 let resp_json: Value = serde_json::from_str(r#"{"code":0,"msg":"","data":{"workerDatas":[{"workerId":"1420554439452400131","workerName":"2X73","status":3,"hashRate":0,"dayHashRate":0,"rejectRate":0,"lastShareTime":1587712919000},{"workerId":"7893926126382807951","workerName":"AZDC1.1A10101","status":2,"hashRate":29711247541680,"dayHashRate":1.269778129801366E13,"rejectRate":0,"lastShareTime":1587969727000}],"totalNum":18530,"pageSize":20}}"#).unwrap();
1574 let dummy_response: models::RequestForMinerListResponse =
1575 serde_json::from_value(resp_json.clone())
1576 .expect("should parse into models::RequestForMinerListResponse");
1577
1578 let dummy = DummyRestApiResponse {
1579 inner: Box::new(move || Box::pin(async move { Ok(dummy_response) })),
1580 status: 200,
1581 headers: HashMap::new(),
1582 rate_limits: None,
1583 };
1584
1585 Ok(dummy.into())
1586 }
1587
1588 async fn statistic_list(
1589 &self,
1590 _params: StatisticListParams,
1591 ) -> anyhow::Result<RestApiResponse<models::StatisticListResponse>> {
1592 if self.force_error {
1593 return Err(ConnectorError::ConnectorClientError {
1594 msg: "ResponseError".to_string(),
1595 code: None,
1596 }
1597 .into());
1598 }
1599
1600 let resp_json: Value = serde_json::from_str(r#"{"code":0,"msg":"","data":{"fifteenMinHashRate":"457835490067496409.00000000","dayHashRate":"214289268068874127.65000000","validNum":0,"invalidNum":17562,"profitToday":{"BTC":"0.00314332","BSV":"56.17055953","BCH":"106.61586001"},"profitYesterday":{"BTC":"0.00314332","BSV":"56.17055953","BCH":"106.61586001"},"userName":"test","unit":"h/s","algo":"sha256"}}"#).unwrap();
1601 let dummy_response: models::StatisticListResponse =
1602 serde_json::from_value(resp_json.clone())
1603 .expect("should parse into models::StatisticListResponse");
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
1616 #[test]
1617 fn account_list_required_params_success() {
1618 TOKIO_SHARED_RT.block_on(async {
1619 let client = MockMiningApiClient { force_error: false };
1620
1621 let params = AccountListParams::builder("algo_example".to_string(),"user_name_example".to_string(),).build().unwrap();
1622
1623 let resp_json: Value = serde_json::from_str(r#"{"code":0,"msg":"","data":[{"type":"H_hashrate","userName":"test","list":[{"time":1585267200000,"hashrate":"0.00000000","reject":"0.00000000"},{"time":1585353600000,"hashrate":"0.00000000","reject":"0.00000000"}]},{"type":"D_hashrate","userName":"test","list":[{"time":1587906000000,"hashrate":"0.00000000","reject":"0.00000000"},{"time":1587909600000,"hashrate":"0.00000000","reject":"0.00000000"}]}]}"#).unwrap();
1624 let expected_response : models::AccountListResponse = serde_json::from_value(resp_json.clone()).expect("should parse into models::AccountListResponse");
1625
1626 let resp = client.account_list(params).await.expect("Expected a response");
1627 let data_future = resp.data();
1628 let actual_response = data_future.await.unwrap();
1629 assert_eq!(actual_response, expected_response);
1630 });
1631 }
1632
1633 #[test]
1634 fn account_list_optional_params_success() {
1635 TOKIO_SHARED_RT.block_on(async {
1636 let client = MockMiningApiClient { force_error: false };
1637
1638 let params = AccountListParams::builder("algo_example".to_string(),"user_name_example".to_string(),).recv_window(5000).build().unwrap();
1639
1640 let resp_json: Value = serde_json::from_str(r#"{"code":0,"msg":"","data":[{"type":"H_hashrate","userName":"test","list":[{"time":1585267200000,"hashrate":"0.00000000","reject":"0.00000000"},{"time":1585353600000,"hashrate":"0.00000000","reject":"0.00000000"}]},{"type":"D_hashrate","userName":"test","list":[{"time":1587906000000,"hashrate":"0.00000000","reject":"0.00000000"},{"time":1587909600000,"hashrate":"0.00000000","reject":"0.00000000"}]}]}"#).unwrap();
1641 let expected_response : models::AccountListResponse = serde_json::from_value(resp_json.clone()).expect("should parse into models::AccountListResponse");
1642
1643 let resp = client.account_list(params).await.expect("Expected a response");
1644 let data_future = resp.data();
1645 let actual_response = data_future.await.unwrap();
1646 assert_eq!(actual_response, expected_response);
1647 });
1648 }
1649
1650 #[test]
1651 fn account_list_response_error() {
1652 TOKIO_SHARED_RT.block_on(async {
1653 let client = MockMiningApiClient { force_error: true };
1654
1655 let params = AccountListParams::builder(
1656 "algo_example".to_string(),
1657 "user_name_example".to_string(),
1658 )
1659 .build()
1660 .unwrap();
1661
1662 match client.account_list(params).await {
1663 Ok(_) => panic!("Expected an error"),
1664 Err(err) => {
1665 assert_eq!(err.to_string(), "Connector client error: ResponseError");
1666 }
1667 }
1668 });
1669 }
1670
1671 #[test]
1672 fn acquiring_algorithm_required_params_success() {
1673 TOKIO_SHARED_RT.block_on(async {
1674 let client = MockMiningApiClient { force_error: false };
1675
1676
1677 let resp_json: Value = serde_json::from_str(r#"{"code":0,"msg":"","data":[{"algoName":"sha256","algoId":1,"poolIndex":0,"unit":"h/s"}]}"#).unwrap();
1678 let expected_response : models::AcquiringAlgorithmResponse = serde_json::from_value(resp_json.clone()).expect("should parse into models::AcquiringAlgorithmResponse");
1679
1680 let resp = client.acquiring_algorithm().await.expect("Expected a response");
1681 let data_future = resp.data();
1682 let actual_response = data_future.await.unwrap();
1683 assert_eq!(actual_response, expected_response);
1684 });
1685 }
1686
1687 #[test]
1688 fn acquiring_algorithm_optional_params_success() {
1689 TOKIO_SHARED_RT.block_on(async {
1690 let client = MockMiningApiClient { force_error: false };
1691
1692
1693 let resp_json: Value = serde_json::from_str(r#"{"code":0,"msg":"","data":[{"algoName":"sha256","algoId":1,"poolIndex":0,"unit":"h/s"}]}"#).unwrap();
1694 let expected_response : models::AcquiringAlgorithmResponse = serde_json::from_value(resp_json.clone()).expect("should parse into models::AcquiringAlgorithmResponse");
1695
1696 let resp = client.acquiring_algorithm().await.expect("Expected a response");
1697 let data_future = resp.data();
1698 let actual_response = data_future.await.unwrap();
1699 assert_eq!(actual_response, expected_response);
1700 });
1701 }
1702
1703 #[test]
1704 fn acquiring_algorithm_response_error() {
1705 TOKIO_SHARED_RT.block_on(async {
1706 let client = MockMiningApiClient { force_error: true };
1707
1708 match client.acquiring_algorithm().await {
1709 Ok(_) => panic!("Expected an error"),
1710 Err(err) => {
1711 assert_eq!(err.to_string(), "Connector client error: ResponseError");
1712 }
1713 }
1714 });
1715 }
1716
1717 #[test]
1718 fn acquiring_coinname_required_params_success() {
1719 TOKIO_SHARED_RT.block_on(async {
1720 let client = MockMiningApiClient { force_error: false };
1721
1722
1723 let resp_json: Value = serde_json::from_str(r#"{"code":0,"msg":"","data":[{"coinName":"BTC","coinId":1,"poolIndex":0,"algoId":1,"algoName":"sha256"}]}"#).unwrap();
1724 let expected_response : models::AcquiringCoinnameResponse = serde_json::from_value(resp_json.clone()).expect("should parse into models::AcquiringCoinnameResponse");
1725
1726 let resp = client.acquiring_coinname().await.expect("Expected a response");
1727 let data_future = resp.data();
1728 let actual_response = data_future.await.unwrap();
1729 assert_eq!(actual_response, expected_response);
1730 });
1731 }
1732
1733 #[test]
1734 fn acquiring_coinname_optional_params_success() {
1735 TOKIO_SHARED_RT.block_on(async {
1736 let client = MockMiningApiClient { force_error: false };
1737
1738
1739 let resp_json: Value = serde_json::from_str(r#"{"code":0,"msg":"","data":[{"coinName":"BTC","coinId":1,"poolIndex":0,"algoId":1,"algoName":"sha256"}]}"#).unwrap();
1740 let expected_response : models::AcquiringCoinnameResponse = serde_json::from_value(resp_json.clone()).expect("should parse into models::AcquiringCoinnameResponse");
1741
1742 let resp = client.acquiring_coinname().await.expect("Expected a response");
1743 let data_future = resp.data();
1744 let actual_response = data_future.await.unwrap();
1745 assert_eq!(actual_response, expected_response);
1746 });
1747 }
1748
1749 #[test]
1750 fn acquiring_coinname_response_error() {
1751 TOKIO_SHARED_RT.block_on(async {
1752 let client = MockMiningApiClient { force_error: true };
1753
1754 match client.acquiring_coinname().await {
1755 Ok(_) => panic!("Expected an error"),
1756 Err(err) => {
1757 assert_eq!(err.to_string(), "Connector client error: ResponseError");
1758 }
1759 }
1760 });
1761 }
1762
1763 #[test]
1764 fn cancel_hashrate_resale_configuration_required_params_success() {
1765 TOKIO_SHARED_RT.block_on(async {
1766 let client = MockMiningApiClient { force_error: false };
1767
1768 let params = CancelHashrateResaleConfigurationParams::builder(
1769 1,
1770 "user_name_example".to_string(),
1771 )
1772 .build()
1773 .unwrap();
1774
1775 let resp_json: Value =
1776 serde_json::from_str(r#"{"code":0,"msg":"","data":true}"#).unwrap();
1777 let expected_response: models::CancelHashrateResaleConfigurationResponse =
1778 serde_json::from_value(resp_json.clone())
1779 .expect("should parse into models::CancelHashrateResaleConfigurationResponse");
1780
1781 let resp = client
1782 .cancel_hashrate_resale_configuration(params)
1783 .await
1784 .expect("Expected a response");
1785 let data_future = resp.data();
1786 let actual_response = data_future.await.unwrap();
1787 assert_eq!(actual_response, expected_response);
1788 });
1789 }
1790
1791 #[test]
1792 fn cancel_hashrate_resale_configuration_optional_params_success() {
1793 TOKIO_SHARED_RT.block_on(async {
1794 let client = MockMiningApiClient { force_error: false };
1795
1796 let params = CancelHashrateResaleConfigurationParams::builder(
1797 1,
1798 "user_name_example".to_string(),
1799 )
1800 .recv_window(5000)
1801 .build()
1802 .unwrap();
1803
1804 let resp_json: Value =
1805 serde_json::from_str(r#"{"code":0,"msg":"","data":true}"#).unwrap();
1806 let expected_response: models::CancelHashrateResaleConfigurationResponse =
1807 serde_json::from_value(resp_json.clone())
1808 .expect("should parse into models::CancelHashrateResaleConfigurationResponse");
1809
1810 let resp = client
1811 .cancel_hashrate_resale_configuration(params)
1812 .await
1813 .expect("Expected a response");
1814 let data_future = resp.data();
1815 let actual_response = data_future.await.unwrap();
1816 assert_eq!(actual_response, expected_response);
1817 });
1818 }
1819
1820 #[test]
1821 fn cancel_hashrate_resale_configuration_response_error() {
1822 TOKIO_SHARED_RT.block_on(async {
1823 let client = MockMiningApiClient { force_error: true };
1824
1825 let params = CancelHashrateResaleConfigurationParams::builder(
1826 1,
1827 "user_name_example".to_string(),
1828 )
1829 .build()
1830 .unwrap();
1831
1832 match client.cancel_hashrate_resale_configuration(params).await {
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 earnings_list_required_params_success() {
1843 TOKIO_SHARED_RT.block_on(async {
1844 let client = MockMiningApiClient { force_error: false };
1845
1846 let params = EarningsListParams::builder("algo_example".to_string(),"user_name_example".to_string(),).build().unwrap();
1847
1848 let resp_json: Value = serde_json::from_str(r#"{"code":0,"msg":"","data":{"accountProfits":[{"time":1586188800000,"type":31,"hashTransfer":null,"transferAmount":null,"dayHashRate":129129903378244,"profitAmount":8.6083060304,"coinName":"BTC","status":2},{"time":1607529600000,"coinName":"BTC","type":0,"dayHashRate":9942053925926,"profitAmount":0.85426469,"hashTransfer":200000000000,"transferAmount":0.02180958,"status":2},{"time":1607443200000,"coinName":"BTC","type":31,"dayHashRate":200000000000,"profitAmount":0.02905916,"hashTransfer":null,"transferAmount":null,"status":2}],"totalNum":3,"pageSize":20}}"#).unwrap();
1849 let expected_response : models::EarningsListResponse = serde_json::from_value(resp_json.clone()).expect("should parse into models::EarningsListResponse");
1850
1851 let resp = client.earnings_list(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 earnings_list_optional_params_success() {
1860 TOKIO_SHARED_RT.block_on(async {
1861 let client = MockMiningApiClient { force_error: false };
1862
1863 let params = EarningsListParams::builder("algo_example".to_string(),"user_name_example".to_string(),).coin("coin_example".to_string()).start_date(789).end_date(789).page_index(1).page_size(789).recv_window(5000).build().unwrap();
1864
1865 let resp_json: Value = serde_json::from_str(r#"{"code":0,"msg":"","data":{"accountProfits":[{"time":1586188800000,"type":31,"hashTransfer":null,"transferAmount":null,"dayHashRate":129129903378244,"profitAmount":8.6083060304,"coinName":"BTC","status":2},{"time":1607529600000,"coinName":"BTC","type":0,"dayHashRate":9942053925926,"profitAmount":0.85426469,"hashTransfer":200000000000,"transferAmount":0.02180958,"status":2},{"time":1607443200000,"coinName":"BTC","type":31,"dayHashRate":200000000000,"profitAmount":0.02905916,"hashTransfer":null,"transferAmount":null,"status":2}],"totalNum":3,"pageSize":20}}"#).unwrap();
1866 let expected_response : models::EarningsListResponse = serde_json::from_value(resp_json.clone()).expect("should parse into models::EarningsListResponse");
1867
1868 let resp = client.earnings_list(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 earnings_list_response_error() {
1877 TOKIO_SHARED_RT.block_on(async {
1878 let client = MockMiningApiClient { force_error: true };
1879
1880 let params = EarningsListParams::builder(
1881 "algo_example".to_string(),
1882 "user_name_example".to_string(),
1883 )
1884 .build()
1885 .unwrap();
1886
1887 match client.earnings_list(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 extra_bonus_list_required_params_success() {
1898 TOKIO_SHARED_RT.block_on(async {
1899 let client = MockMiningApiClient { force_error: false };
1900
1901 let params = ExtraBonusListParams::builder("algo_example".to_string(),"user_name_example".to_string(),).build().unwrap();
1902
1903 let resp_json: Value = serde_json::from_str(r#"{"code":0,"msg":"","data":{"otherProfits":[{"time":1607443200000,"coinName":"BTC","type":4,"profitAmount":0.0011859,"status":2}],"totalNum":3,"pageSize":20}}"#).unwrap();
1904 let expected_response : models::ExtraBonusListResponse = serde_json::from_value(resp_json.clone()).expect("should parse into models::ExtraBonusListResponse");
1905
1906 let resp = client.extra_bonus_list(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 extra_bonus_list_optional_params_success() {
1915 TOKIO_SHARED_RT.block_on(async {
1916 let client = MockMiningApiClient { force_error: false };
1917
1918 let params = ExtraBonusListParams::builder("algo_example".to_string(),"user_name_example".to_string(),).coin("coin_example".to_string()).start_date(789).end_date(789).page_index(1).page_size(789).recv_window(5000).build().unwrap();
1919
1920 let resp_json: Value = serde_json::from_str(r#"{"code":0,"msg":"","data":{"otherProfits":[{"time":1607443200000,"coinName":"BTC","type":4,"profitAmount":0.0011859,"status":2}],"totalNum":3,"pageSize":20}}"#).unwrap();
1921 let expected_response : models::ExtraBonusListResponse = serde_json::from_value(resp_json.clone()).expect("should parse into models::ExtraBonusListResponse");
1922
1923 let resp = client.extra_bonus_list(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 extra_bonus_list_response_error() {
1932 TOKIO_SHARED_RT.block_on(async {
1933 let client = MockMiningApiClient { force_error: true };
1934
1935 let params = ExtraBonusListParams::builder(
1936 "algo_example".to_string(),
1937 "user_name_example".to_string(),
1938 )
1939 .build()
1940 .unwrap();
1941
1942 match client.extra_bonus_list(params).await {
1943 Ok(_) => panic!("Expected an error"),
1944 Err(err) => {
1945 assert_eq!(err.to_string(), "Connector client error: ResponseError");
1946 }
1947 }
1948 });
1949 }
1950
1951 #[test]
1952 fn hashrate_resale_detail_required_params_success() {
1953 TOKIO_SHARED_RT.block_on(async {
1954 let client = MockMiningApiClient { force_error: false };
1955
1956 let params = HashrateResaleDetailParams::builder(1,).build().unwrap();
1957
1958 let resp_json: Value = serde_json::from_str(r#"{"code":0,"msg":"","data":{"profitTransferDetails":[{"poolUsername":"test4001","toPoolUsername":"pop","algoName":"sha256","hashRate":200000000000,"day":20201213,"amount":0.2256872,"coinName":"BTC"},{"poolUsername":"test4001","toPoolUsername":"pop","algoName":"sha256","hashRate":200000000000,"day":20201213,"amount":0.2256872,"coinName":"BTC"}],"totalNum":8,"pageSize":200}}"#).unwrap();
1959 let expected_response : models::HashrateResaleDetailResponse = serde_json::from_value(resp_json.clone()).expect("should parse into models::HashrateResaleDetailResponse");
1960
1961 let resp = client.hashrate_resale_detail(params).await.expect("Expected a response");
1962 let data_future = resp.data();
1963 let actual_response = data_future.await.unwrap();
1964 assert_eq!(actual_response, expected_response);
1965 });
1966 }
1967
1968 #[test]
1969 fn hashrate_resale_detail_optional_params_success() {
1970 TOKIO_SHARED_RT.block_on(async {
1971 let client = MockMiningApiClient { force_error: false };
1972
1973 let params = HashrateResaleDetailParams::builder(1,).page_index(1).page_size(789).recv_window(5000).build().unwrap();
1974
1975 let resp_json: Value = serde_json::from_str(r#"{"code":0,"msg":"","data":{"profitTransferDetails":[{"poolUsername":"test4001","toPoolUsername":"pop","algoName":"sha256","hashRate":200000000000,"day":20201213,"amount":0.2256872,"coinName":"BTC"},{"poolUsername":"test4001","toPoolUsername":"pop","algoName":"sha256","hashRate":200000000000,"day":20201213,"amount":0.2256872,"coinName":"BTC"}],"totalNum":8,"pageSize":200}}"#).unwrap();
1976 let expected_response : models::HashrateResaleDetailResponse = serde_json::from_value(resp_json.clone()).expect("should parse into models::HashrateResaleDetailResponse");
1977
1978 let resp = client.hashrate_resale_detail(params).await.expect("Expected a response");
1979 let data_future = resp.data();
1980 let actual_response = data_future.await.unwrap();
1981 assert_eq!(actual_response, expected_response);
1982 });
1983 }
1984
1985 #[test]
1986 fn hashrate_resale_detail_response_error() {
1987 TOKIO_SHARED_RT.block_on(async {
1988 let client = MockMiningApiClient { force_error: true };
1989
1990 let params = HashrateResaleDetailParams::builder(1).build().unwrap();
1991
1992 match client.hashrate_resale_detail(params).await {
1993 Ok(_) => panic!("Expected an error"),
1994 Err(err) => {
1995 assert_eq!(err.to_string(), "Connector client error: ResponseError");
1996 }
1997 }
1998 });
1999 }
2000
2001 #[test]
2002 fn hashrate_resale_list_required_params_success() {
2003 TOKIO_SHARED_RT.block_on(async {
2004 let client = MockMiningApiClient { force_error: false };
2005
2006 let params = HashrateResaleListParams::builder().build().unwrap();
2007
2008 let resp_json: Value = serde_json::from_str(r#"{"code":0,"msg":"","data":{"configDetails":[{"configId":168,"poolUsername":"123","toPoolUsername":"user1","algoName":"Ethash","hashRate":5000000,"startDay":20201210,"endDay":20210405,"status":1,"type":0},{"configId":166,"poolUsername":"pop","toPoolUsername":"111111","algoName":"Ethash","hashRate":3320000,"startDay":20201226,"endDay":20201227,"status":0,"type":0}],"totalNum":21,"pageSize":200}}"#).unwrap();
2009 let expected_response : models::HashrateResaleListResponse = serde_json::from_value(resp_json.clone()).expect("should parse into models::HashrateResaleListResponse");
2010
2011 let resp = client.hashrate_resale_list(params).await.expect("Expected a response");
2012 let data_future = resp.data();
2013 let actual_response = data_future.await.unwrap();
2014 assert_eq!(actual_response, expected_response);
2015 });
2016 }
2017
2018 #[test]
2019 fn hashrate_resale_list_optional_params_success() {
2020 TOKIO_SHARED_RT.block_on(async {
2021 let client = MockMiningApiClient { force_error: false };
2022
2023 let params = HashrateResaleListParams::builder().page_index(1).page_size(789).recv_window(5000).build().unwrap();
2024
2025 let resp_json: Value = serde_json::from_str(r#"{"code":0,"msg":"","data":{"configDetails":[{"configId":168,"poolUsername":"123","toPoolUsername":"user1","algoName":"Ethash","hashRate":5000000,"startDay":20201210,"endDay":20210405,"status":1,"type":0},{"configId":166,"poolUsername":"pop","toPoolUsername":"111111","algoName":"Ethash","hashRate":3320000,"startDay":20201226,"endDay":20201227,"status":0,"type":0}],"totalNum":21,"pageSize":200}}"#).unwrap();
2026 let expected_response : models::HashrateResaleListResponse = serde_json::from_value(resp_json.clone()).expect("should parse into models::HashrateResaleListResponse");
2027
2028 let resp = client.hashrate_resale_list(params).await.expect("Expected a response");
2029 let data_future = resp.data();
2030 let actual_response = data_future.await.unwrap();
2031 assert_eq!(actual_response, expected_response);
2032 });
2033 }
2034
2035 #[test]
2036 fn hashrate_resale_list_response_error() {
2037 TOKIO_SHARED_RT.block_on(async {
2038 let client = MockMiningApiClient { force_error: true };
2039
2040 let params = HashrateResaleListParams::builder().build().unwrap();
2041
2042 match client.hashrate_resale_list(params).await {
2043 Ok(_) => panic!("Expected an error"),
2044 Err(err) => {
2045 assert_eq!(err.to_string(), "Connector client error: ResponseError");
2046 }
2047 }
2048 });
2049 }
2050
2051 #[test]
2052 fn hashrate_resale_request_required_params_success() {
2053 TOKIO_SHARED_RT.block_on(async {
2054 let client = MockMiningApiClient { force_error: false };
2055
2056 let params = HashrateResaleRequestParams::builder(
2057 "user_name_example".to_string(),
2058 "algo_example".to_string(),
2059 789,
2060 789,
2061 "to_pool_user_example".to_string(),
2062 789,
2063 )
2064 .build()
2065 .unwrap();
2066
2067 let resp_json: Value =
2068 serde_json::from_str(r#"{"code":0,"msg":"","data":171}"#).unwrap();
2069 let expected_response: models::HashrateResaleRequestResponse =
2070 serde_json::from_value(resp_json.clone())
2071 .expect("should parse into models::HashrateResaleRequestResponse");
2072
2073 let resp = client
2074 .hashrate_resale_request(params)
2075 .await
2076 .expect("Expected a response");
2077 let data_future = resp.data();
2078 let actual_response = data_future.await.unwrap();
2079 assert_eq!(actual_response, expected_response);
2080 });
2081 }
2082
2083 #[test]
2084 fn hashrate_resale_request_optional_params_success() {
2085 TOKIO_SHARED_RT.block_on(async {
2086 let client = MockMiningApiClient { force_error: false };
2087
2088 let params = HashrateResaleRequestParams::builder(
2089 "user_name_example".to_string(),
2090 "algo_example".to_string(),
2091 789,
2092 789,
2093 "to_pool_user_example".to_string(),
2094 789,
2095 )
2096 .recv_window(5000)
2097 .build()
2098 .unwrap();
2099
2100 let resp_json: Value =
2101 serde_json::from_str(r#"{"code":0,"msg":"","data":171}"#).unwrap();
2102 let expected_response: models::HashrateResaleRequestResponse =
2103 serde_json::from_value(resp_json.clone())
2104 .expect("should parse into models::HashrateResaleRequestResponse");
2105
2106 let resp = client
2107 .hashrate_resale_request(params)
2108 .await
2109 .expect("Expected a response");
2110 let data_future = resp.data();
2111 let actual_response = data_future.await.unwrap();
2112 assert_eq!(actual_response, expected_response);
2113 });
2114 }
2115
2116 #[test]
2117 fn hashrate_resale_request_response_error() {
2118 TOKIO_SHARED_RT.block_on(async {
2119 let client = MockMiningApiClient { force_error: true };
2120
2121 let params = HashrateResaleRequestParams::builder(
2122 "user_name_example".to_string(),
2123 "algo_example".to_string(),
2124 789,
2125 789,
2126 "to_pool_user_example".to_string(),
2127 789,
2128 )
2129 .build()
2130 .unwrap();
2131
2132 match client.hashrate_resale_request(params).await {
2133 Ok(_) => panic!("Expected an error"),
2134 Err(err) => {
2135 assert_eq!(err.to_string(), "Connector client error: ResponseError");
2136 }
2137 }
2138 });
2139 }
2140
2141 #[test]
2142 fn mining_account_earning_required_params_success() {
2143 TOKIO_SHARED_RT.block_on(async {
2144 let client = MockMiningApiClient { force_error: false };
2145
2146 let params = MiningAccountEarningParams::builder("algo_example".to_string(),).build().unwrap();
2147
2148 let resp_json: Value = serde_json::from_str(r#"{"code":0,"msg":"","data":{"accountProfits":[{"time":1607443200000,"coinName":"BTC","type":2,"puid":59985472,"subName":"vdvaghani","amount":0.09186957}],"totalNum":3,"pageSize":20}}"#).unwrap();
2149 let expected_response : models::MiningAccountEarningResponse = serde_json::from_value(resp_json.clone()).expect("should parse into models::MiningAccountEarningResponse");
2150
2151 let resp = client.mining_account_earning(params).await.expect("Expected a response");
2152 let data_future = resp.data();
2153 let actual_response = data_future.await.unwrap();
2154 assert_eq!(actual_response, expected_response);
2155 });
2156 }
2157
2158 #[test]
2159 fn mining_account_earning_optional_params_success() {
2160 TOKIO_SHARED_RT.block_on(async {
2161 let client = MockMiningApiClient { force_error: false };
2162
2163 let params = MiningAccountEarningParams::builder("algo_example".to_string(),).start_date(789).end_date(789).page_index(1).page_size(789).recv_window(5000).build().unwrap();
2164
2165 let resp_json: Value = serde_json::from_str(r#"{"code":0,"msg":"","data":{"accountProfits":[{"time":1607443200000,"coinName":"BTC","type":2,"puid":59985472,"subName":"vdvaghani","amount":0.09186957}],"totalNum":3,"pageSize":20}}"#).unwrap();
2166 let expected_response : models::MiningAccountEarningResponse = serde_json::from_value(resp_json.clone()).expect("should parse into models::MiningAccountEarningResponse");
2167
2168 let resp = client.mining_account_earning(params).await.expect("Expected a response");
2169 let data_future = resp.data();
2170 let actual_response = data_future.await.unwrap();
2171 assert_eq!(actual_response, expected_response);
2172 });
2173 }
2174
2175 #[test]
2176 fn mining_account_earning_response_error() {
2177 TOKIO_SHARED_RT.block_on(async {
2178 let client = MockMiningApiClient { force_error: true };
2179
2180 let params = MiningAccountEarningParams::builder("algo_example".to_string())
2181 .build()
2182 .unwrap();
2183
2184 match client.mining_account_earning(params).await {
2185 Ok(_) => panic!("Expected an error"),
2186 Err(err) => {
2187 assert_eq!(err.to_string(), "Connector client error: ResponseError");
2188 }
2189 }
2190 });
2191 }
2192
2193 #[test]
2194 fn request_for_detail_miner_list_required_params_success() {
2195 TOKIO_SHARED_RT.block_on(async {
2196 let client = MockMiningApiClient { force_error: false };
2197
2198 let params = RequestForDetailMinerListParams::builder("algo_example".to_string(),"user_name_example".to_string(),"worker_name_example".to_string(),).build().unwrap();
2199
2200 let resp_json: Value = serde_json::from_str(r#"{"code":0,"msg":"","data":[{"workerName":"bhdc1.16A10404B","type":"H_hashrate","hashrateDatas":[{"time":1587902400000,"hashrate":"0","reject":0},{"time":1587906000000,"hashrate":"0","reject":0}]},{"workerName":"bhdc1.16A10404B","type":"D_hashrate","hashrateDatas":[{"time":1587902400000,"hashrate":"0","reject":0},{"time":1587906000000,"hashrate":"0","reject":0}]}]}"#).unwrap();
2201 let expected_response : models::RequestForDetailMinerListResponse = serde_json::from_value(resp_json.clone()).expect("should parse into models::RequestForDetailMinerListResponse");
2202
2203 let resp = client.request_for_detail_miner_list(params).await.expect("Expected a response");
2204 let data_future = resp.data();
2205 let actual_response = data_future.await.unwrap();
2206 assert_eq!(actual_response, expected_response);
2207 });
2208 }
2209
2210 #[test]
2211 fn request_for_detail_miner_list_optional_params_success() {
2212 TOKIO_SHARED_RT.block_on(async {
2213 let client = MockMiningApiClient { force_error: false };
2214
2215 let params = RequestForDetailMinerListParams::builder("algo_example".to_string(),"user_name_example".to_string(),"worker_name_example".to_string(),).recv_window(5000).build().unwrap();
2216
2217 let resp_json: Value = serde_json::from_str(r#"{"code":0,"msg":"","data":[{"workerName":"bhdc1.16A10404B","type":"H_hashrate","hashrateDatas":[{"time":1587902400000,"hashrate":"0","reject":0},{"time":1587906000000,"hashrate":"0","reject":0}]},{"workerName":"bhdc1.16A10404B","type":"D_hashrate","hashrateDatas":[{"time":1587902400000,"hashrate":"0","reject":0},{"time":1587906000000,"hashrate":"0","reject":0}]}]}"#).unwrap();
2218 let expected_response : models::RequestForDetailMinerListResponse = serde_json::from_value(resp_json.clone()).expect("should parse into models::RequestForDetailMinerListResponse");
2219
2220 let resp = client.request_for_detail_miner_list(params).await.expect("Expected a response");
2221 let data_future = resp.data();
2222 let actual_response = data_future.await.unwrap();
2223 assert_eq!(actual_response, expected_response);
2224 });
2225 }
2226
2227 #[test]
2228 fn request_for_detail_miner_list_response_error() {
2229 TOKIO_SHARED_RT.block_on(async {
2230 let client = MockMiningApiClient { force_error: true };
2231
2232 let params = RequestForDetailMinerListParams::builder(
2233 "algo_example".to_string(),
2234 "user_name_example".to_string(),
2235 "worker_name_example".to_string(),
2236 )
2237 .build()
2238 .unwrap();
2239
2240 match client.request_for_detail_miner_list(params).await {
2241 Ok(_) => panic!("Expected an error"),
2242 Err(err) => {
2243 assert_eq!(err.to_string(), "Connector client error: ResponseError");
2244 }
2245 }
2246 });
2247 }
2248
2249 #[test]
2250 fn request_for_miner_list_required_params_success() {
2251 TOKIO_SHARED_RT.block_on(async {
2252 let client = MockMiningApiClient { force_error: false };
2253
2254 let params = RequestForMinerListParams::builder("algo_example".to_string(),"user_name_example".to_string(),).build().unwrap();
2255
2256 let resp_json: Value = serde_json::from_str(r#"{"code":0,"msg":"","data":{"workerDatas":[{"workerId":"1420554439452400131","workerName":"2X73","status":3,"hashRate":0,"dayHashRate":0,"rejectRate":0,"lastShareTime":1587712919000},{"workerId":"7893926126382807951","workerName":"AZDC1.1A10101","status":2,"hashRate":29711247541680,"dayHashRate":1.269778129801366E13,"rejectRate":0,"lastShareTime":1587969727000}],"totalNum":18530,"pageSize":20}}"#).unwrap();
2257 let expected_response : models::RequestForMinerListResponse = serde_json::from_value(resp_json.clone()).expect("should parse into models::RequestForMinerListResponse");
2258
2259 let resp = client.request_for_miner_list(params).await.expect("Expected a response");
2260 let data_future = resp.data();
2261 let actual_response = data_future.await.unwrap();
2262 assert_eq!(actual_response, expected_response);
2263 });
2264 }
2265
2266 #[test]
2267 fn request_for_miner_list_optional_params_success() {
2268 TOKIO_SHARED_RT.block_on(async {
2269 let client = MockMiningApiClient { force_error: false };
2270
2271 let params = RequestForMinerListParams::builder("algo_example".to_string(),"user_name_example".to_string(),).page_index(1).sort(0).sort_column(1).worker_status(0).recv_window(5000).build().unwrap();
2272
2273 let resp_json: Value = serde_json::from_str(r#"{"code":0,"msg":"","data":{"workerDatas":[{"workerId":"1420554439452400131","workerName":"2X73","status":3,"hashRate":0,"dayHashRate":0,"rejectRate":0,"lastShareTime":1587712919000},{"workerId":"7893926126382807951","workerName":"AZDC1.1A10101","status":2,"hashRate":29711247541680,"dayHashRate":1.269778129801366E13,"rejectRate":0,"lastShareTime":1587969727000}],"totalNum":18530,"pageSize":20}}"#).unwrap();
2274 let expected_response : models::RequestForMinerListResponse = serde_json::from_value(resp_json.clone()).expect("should parse into models::RequestForMinerListResponse");
2275
2276 let resp = client.request_for_miner_list(params).await.expect("Expected a response");
2277 let data_future = resp.data();
2278 let actual_response = data_future.await.unwrap();
2279 assert_eq!(actual_response, expected_response);
2280 });
2281 }
2282
2283 #[test]
2284 fn request_for_miner_list_response_error() {
2285 TOKIO_SHARED_RT.block_on(async {
2286 let client = MockMiningApiClient { force_error: true };
2287
2288 let params = RequestForMinerListParams::builder(
2289 "algo_example".to_string(),
2290 "user_name_example".to_string(),
2291 )
2292 .build()
2293 .unwrap();
2294
2295 match client.request_for_miner_list(params).await {
2296 Ok(_) => panic!("Expected an error"),
2297 Err(err) => {
2298 assert_eq!(err.to_string(), "Connector client error: ResponseError");
2299 }
2300 }
2301 });
2302 }
2303
2304 #[test]
2305 fn statistic_list_required_params_success() {
2306 TOKIO_SHARED_RT.block_on(async {
2307 let client = MockMiningApiClient { force_error: false };
2308
2309 let params = StatisticListParams::builder("algo_example".to_string(),"user_name_example".to_string(),).build().unwrap();
2310
2311 let resp_json: Value = serde_json::from_str(r#"{"code":0,"msg":"","data":{"fifteenMinHashRate":"457835490067496409.00000000","dayHashRate":"214289268068874127.65000000","validNum":0,"invalidNum":17562,"profitToday":{"BTC":"0.00314332","BSV":"56.17055953","BCH":"106.61586001"},"profitYesterday":{"BTC":"0.00314332","BSV":"56.17055953","BCH":"106.61586001"},"userName":"test","unit":"h/s","algo":"sha256"}}"#).unwrap();
2312 let expected_response : models::StatisticListResponse = serde_json::from_value(resp_json.clone()).expect("should parse into models::StatisticListResponse");
2313
2314 let resp = client.statistic_list(params).await.expect("Expected a response");
2315 let data_future = resp.data();
2316 let actual_response = data_future.await.unwrap();
2317 assert_eq!(actual_response, expected_response);
2318 });
2319 }
2320
2321 #[test]
2322 fn statistic_list_optional_params_success() {
2323 TOKIO_SHARED_RT.block_on(async {
2324 let client = MockMiningApiClient { force_error: false };
2325
2326 let params = StatisticListParams::builder("algo_example".to_string(),"user_name_example".to_string(),).recv_window(5000).build().unwrap();
2327
2328 let resp_json: Value = serde_json::from_str(r#"{"code":0,"msg":"","data":{"fifteenMinHashRate":"457835490067496409.00000000","dayHashRate":"214289268068874127.65000000","validNum":0,"invalidNum":17562,"profitToday":{"BTC":"0.00314332","BSV":"56.17055953","BCH":"106.61586001"},"profitYesterday":{"BTC":"0.00314332","BSV":"56.17055953","BCH":"106.61586001"},"userName":"test","unit":"h/s","algo":"sha256"}}"#).unwrap();
2329 let expected_response : models::StatisticListResponse = serde_json::from_value(resp_json.clone()).expect("should parse into models::StatisticListResponse");
2330
2331 let resp = client.statistic_list(params).await.expect("Expected a response");
2332 let data_future = resp.data();
2333 let actual_response = data_future.await.unwrap();
2334 assert_eq!(actual_response, expected_response);
2335 });
2336 }
2337
2338 #[test]
2339 fn statistic_list_response_error() {
2340 TOKIO_SHARED_RT.block_on(async {
2341 let client = MockMiningApiClient { force_error: true };
2342
2343 let params = StatisticListParams::builder(
2344 "algo_example".to_string(),
2345 "user_name_example".to_string(),
2346 )
2347 .build()
2348 .unwrap();
2349
2350 match client.statistic_list(params).await {
2351 Ok(_) => panic!("Expected an error"),
2352 Err(err) => {
2353 assert_eq!(err.to_string(), "Connector client error: ResponseError");
2354 }
2355 }
2356 });
2357 }
2358}