Skip to main content

contentstack_api_client_rs/client/
config.rs

1use std::time::Duration;
2
3pub enum Region {
4    AwsNa,
5    AwsEu,
6    AwsAu,
7    AzureNa,
8    AzureEu,
9    GcpNa,
10    GcpEu,
11}
12
13pub enum ClientType {
14    Delivery,
15    Management,
16}
17
18impl Region {
19    pub fn delivery_base_url(&self) -> &'static str {
20        match &self {
21            Region::AwsNa => "https://cdn.contentstack.io",
22            Region::AwsEu => "https://eu-cdn.contentstack.com",
23            Region::AwsAu => "https://au-cdn.contentstack.com",
24            Region::AzureNa => "https://azure-na-cdn.contentstack.com",
25            Region::AzureEu => "https://azure-eu-cdn.contentstack.com",
26            Region::GcpNa => "https://gcp-na-cdn.contentstack.com",
27            Region::GcpEu => "https://gcp-eu-cdn.contentstack.com",
28        }
29    }
30
31    pub fn management_base_url(&self) -> &'static str {
32        match &self {
33            Region::AwsNa => "https://api.contentstack.io",
34            Region::AwsEu => "https://eu-api.contentstack.com",
35            Region::AwsAu => "https://au-api.contentstack.com",
36            Region::AzureNa => "https://azure-na-api.contentstack.com",
37            Region::AzureEu => "https://azure-eu-api.contentstack.com",
38            Region::GcpNa => "https://gcp-na-api.contentstack.com",
39            Region::GcpEu => "https://gcp-eu-api.contentstack.com",
40        }
41    }
42}
43
44pub struct ClientConfig {
45    pub base_url: String,
46    pub api_key: String,
47    pub management_token: String,
48    pub delivery_token: String,
49    pub environment: Option<String>,
50    pub timeout: Duration,
51    pub max_connections: usize,
52    pub region: Region,
53}
54
55pub struct ClientOptions {
56    pub base_url: Option<String>,
57    pub timeout: Option<Duration>,
58    pub max_connections: Option<usize>,
59    pub region: Option<Region>,
60}
61
62impl ClientConfig {
63    pub fn delivery(
64        api_key: &str,
65        delivery_token: &str,
66        environment: &str,
67        opts: Option<ClientOptions>,
68    ) -> Self {
69        let defaults = ClientOptions::get_defaults(ClientType::Delivery);
70        let defaults = if let Some(config) = opts {
71            ClientOptions {
72                base_url: config.base_url.or(defaults.base_url),
73                timeout: config.timeout.or(defaults.timeout),
74                max_connections: config.max_connections.or(defaults.max_connections),
75                region: config.region.or(defaults.region),
76            }
77        } else {
78            defaults
79        };
80
81        Self {
82            base_url: Option::expect(defaults.base_url, "Base Url not provided"),
83            api_key: api_key.into(),
84            delivery_token: delivery_token.into(),
85            management_token: String::new(),
86            environment: Some(environment.into()),
87            timeout: defaults.timeout.unwrap_or(Duration::from_secs(30)),
88            max_connections: defaults.max_connections.unwrap_or(50),
89            region: Option::expect(defaults.region, "Region not provided"),
90        }
91    }
92
93    /// Builds a [`ClientConfig`] for the Management API.
94    ///
95    /// Defaults to AWS NA region (`https://api.contentstack.io`) if no
96    /// `base_url` or `region` override is provided. Management API requests
97    /// do not use an environment, so that field is left empty.
98    ///
99    /// # Arguments
100    ///
101    /// * `api_key` - Your stack's API key
102    /// * `management_token` - Stack management token
103    /// * `opts` - Optional configuration overrides (region, timeout, max connections)
104    pub fn management(api_key: &str, management_token: &str, opts: Option<ClientOptions>) -> Self {
105        let defaults = ClientOptions::get_defaults(ClientType::Management);
106
107        let defaults = if let Some(config) = opts {
108            ClientOptions {
109                base_url: config.base_url.or(defaults.base_url),
110                timeout: config.timeout.or(defaults.timeout),
111                max_connections: config.max_connections.or(defaults.max_connections),
112                region: config.region.or(defaults.region),
113            }
114        } else {
115            defaults
116        };
117
118        Self {
119            base_url: Option::expect(defaults.base_url, "Base Url not provided"),
120            api_key: api_key.into(),
121            delivery_token: String::new(),
122            management_token: management_token.into(),
123            environment: None,
124            timeout: defaults.timeout.unwrap_or(Duration::from_secs(30)),
125            max_connections: defaults.max_connections.unwrap_or(50),
126            region: Option::expect(defaults.region, "Region not provided"),
127        }
128    }
129}
130
131impl ClientOptions {
132    fn get_defaults(client_type: ClientType) -> ClientOptions {
133        let timeout: Duration = Duration::from_secs(30);
134        let max_connections = 50;
135
136        let base_url = match client_type {
137            ClientType::Delivery => Region::AwsNa.delivery_base_url(),
138            ClientType::Management => Region::AwsNa.management_base_url(),
139        };
140
141        ClientOptions {
142            base_url: Some(base_url.into()),
143            timeout: Some(timeout),
144            max_connections: Some(max_connections),
145            region: Some(Region::AwsNa),
146        }
147    }
148}