1pub mod admin;
2pub mod config;
3pub mod errors;
4pub mod kvstore;
5pub mod streams;
6pub mod webhooks;
7
8pub use config::{
9 AdminConfig, HttpConfig, KvStoreConfig, SdkFullConfig, StreamsConfig, WebhooksConfig,
10};
11pub use kvstore::{
12 AddListItemParams, BulkSetsParams, CreateListParams, CreateSetParams, GetListData,
13 GetListParams, GetListResponse, GetListsData, GetListsParams, GetListsResponse, GetSetResponse,
14 GetSetsParams, GetSetsResponse, KvSetEntry, KvStoreApiClient, ListContainsItemResponse,
15 UpdateListParams,
16};
17
18use reqwest::header::{HeaderMap, HeaderValue};
19use reqwest::Client as ReqwestClient;
20use std::sync::Arc;
21
22use errors::SdkError;
23
24const DEFAULT_TIMEOUT_SECS: u64 = 30;
25
26#[derive(Clone)]
28pub struct SdkConfig(Arc<SdkConfigInner>);
29
30impl std::fmt::Debug for SdkConfig {
31 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
32 f.debug_struct("SdkConfig")
33 .field("api_key", &"[redacted]")
34 .field("admin_base_url", &self.0.admin.base_url)
35 .field("streams_base_url", &self.0.streams.base_url)
36 .field("webhooks_base_url", &self.0.webhooks.base_url)
37 .field("kvstore_base_url", &self.0.kvstore.base_url)
38 .finish()
39 }
40}
41
42struct SdkConfigInner {
43 http_client: ReqwestClient,
44 admin: admin::ResolvedAdminConfig,
45 streams: streams::ResolvedStreamsConfig,
46 webhooks: webhooks::ResolvedWebhooksConfig,
47 kvstore: kvstore::ResolvedKvStoreConfig,
48}
49
50impl SdkConfig {
51 pub fn new(config: &SdkFullConfig) -> Result<Self, SdkError> {
52 let mut builder = ReqwestClient::builder();
53
54 let timeout_secs = match &config.http {
55 Some(h) => match h.timeout_secs {
56 Some(secs) if secs < 0 => {
57 return Err(SdkError::Config("timeout_secs must be non-negative".into()));
58 }
59 Some(secs) => secs as u64,
60 None => DEFAULT_TIMEOUT_SECS,
61 },
62 None => DEFAULT_TIMEOUT_SECS,
63 };
64 builder = builder.timeout(std::time::Duration::from_secs(timeout_secs));
65
66 if let Some(http) = &config.http {
67 if let Some(max_idle) = http.pool_max_idle_per_host {
68 builder = builder.pool_max_idle_per_host(max_idle as usize);
69 }
70 }
71
72 let mut default_headers = HeaderMap::new();
73 default_headers.insert(
74 reqwest::header::ACCEPT,
75 HeaderValue::from_static("application/json"),
76 );
77 default_headers.insert(
78 reqwest::header::CONTENT_TYPE,
79 HeaderValue::from_static("application/json"),
80 );
81 default_headers.insert(
82 "x-api-key",
83 HeaderValue::from_str(&config.api_key).map_err(|e| SdkError::Config(e.to_string()))?,
84 );
85 builder = builder.default_headers(default_headers);
86
87 let http_client = builder
88 .build()
89 .map_err(|e| SdkError::Config(e.to_string()))?;
90
91 Ok(Self(Arc::new(SdkConfigInner {
92 http_client,
93 admin: admin::ResolvedAdminConfig::from_config(config.admin.as_ref())?,
94 streams: streams::ResolvedStreamsConfig::from_config(config.streams.as_ref())?,
95 webhooks: webhooks::ResolvedWebhooksConfig::from_config(config.webhooks.as_ref())?,
96 kvstore: kvstore::ResolvedKvStoreConfig::from_config(config.kvstore.as_ref())?,
97 })))
98 }
99
100 pub(crate) fn http_client(&self) -> &ReqwestClient {
101 &self.0.http_client
102 }
103
104 pub(crate) fn admin(&self) -> &admin::ResolvedAdminConfig {
105 &self.0.admin
106 }
107
108 pub(crate) fn streams(&self) -> &streams::ResolvedStreamsConfig {
109 &self.0.streams
110 }
111
112 pub(crate) fn webhooks(&self) -> &webhooks::ResolvedWebhooksConfig {
113 &self.0.webhooks
114 }
115
116 pub(crate) fn kvstore(&self) -> &kvstore::ResolvedKvStoreConfig {
117 &self.0.kvstore
118 }
119}
120
121pub struct QuickNodeSdk {
124 pub admin: admin::AdminApiClient,
127 pub streams: streams::StreamsApiClient,
129 pub webhooks: webhooks::WebhooksApiClient,
131 pub kvstore: kvstore::KvStoreApiClient,
134}
135
136impl QuickNodeSdk {
137 pub fn new(config: &SdkFullConfig) -> Result<Self, SdkError> {
139 let sdk_config = SdkConfig::new(config)?;
140 Ok(Self {
141 admin: admin::AdminApiClient::new(sdk_config.clone()),
142 streams: streams::StreamsApiClient::new(sdk_config.clone()),
143 webhooks: webhooks::WebhooksApiClient::new(sdk_config.clone()),
144 kvstore: kvstore::KvStoreApiClient::new(sdk_config),
145 })
146 }
147
148 pub fn from_env() -> Result<Self, SdkError> {
150 Self::new(&SdkFullConfig::from_env()?)
151 }
152}