three_commas_client/
lib.rs1mod deals;
2mod errors;
3mod middleware;
4
5pub use deals::{Deals, DealsScope};
6pub use errors::{ClientError, RequestError};
7pub use three_commas_types::{
8 Account, AccountId, AutoBalanceMethod, Bot, BotStats, Deal, MarketType, Pair,
9};
10
11use middleware::RequestBuilderExt;
12use std::result::Result as StdResult;
13use std::time::Duration;
14use surf::{http::Result, Client, Config, Url};
15
16#[derive(Clone)]
17pub struct ThreeCommasClient {
18 pub(crate) client: Client,
19}
20
21impl ThreeCommasClient {
22 pub fn new(api_key: impl AsRef<str>, secret: impl AsRef<str>) -> StdResult<Self, ClientError> {
23 let client: Client = Config::new()
24 .set_base_url(Url::parse("https://api.3commas.io/public/api/").unwrap())
25 .try_into()
26 .map_err(ClientError::FailedCreate)?;
27
28 let client = client
29 .with(middleware::TracingRequestLoggerMiddlware)
30 .with(middleware::ApiKeyMiddleware::new(api_key.as_ref()))
31 .with(middleware::SigningMiddleware::new(secret.as_ref()))
32 .with(middleware::ErrorHandlerMiddleware)
33 .with(middleware::Limit::new(2, Duration::from_secs(1)))
34 .with(middleware::Limit::new(30, Duration::from_secs(60)))
35 .with(middleware::TracingPipelineLoggerMiddlware);
36
37 Ok(Self { client })
38 }
39
40 pub async fn accounts(&self) -> Result<Vec<Account>> {
41 let req = self.client.get("ver1/accounts").signed();
42 self.client.recv_json(req).await
43 }
44
45 pub async fn account(&self, account_id: AccountId) -> Result<Account> {
46 let req = self
47 .client
48 .get(format!("ver1/accounts/{}", account_id))
49 .signed();
50 self.client.recv_json(req).await
51 }
52
53 pub async fn bots(&self) -> Result<Vec<Bot>> {
54 let req = self.client.get("ver1/bots").signed();
55 self.client.recv_json(req).await
56 }
57
58 pub async fn bot_stats(&self, bot: &Bot) -> Result<BotStats> {
59 let req = self
60 .client
61 .get(format!(
62 "ver1/bots/stats?account_id={}&bot_id={}",
63 bot.account_id(),
64 bot.id()
65 ))
66 .signed();
67 self.client.recv_json(req).await
68 }
69
70 pub fn deals(&self) -> Deals {
71 Deals::new(self.clone())
72 }
73}