tencentcloud_sms_sdk/core/
profile.rs

1//! Configuration profiles for HTTP and client settings
2
3use std::time::Duration;
4
5/// HTTP configuration profile
6#[derive(Debug, Clone)]
7pub struct HttpProfile {
8    /// HTTP request method (GET, POST)
9    pub req_method: String,
10    /// API endpoint URL
11    pub endpoint: String,
12    /// Request timeout in seconds
13    pub req_timeout: u64,
14    /// Connection timeout in seconds
15    pub connect_timeout: u64,
16    /// Keep-alive setting
17    pub keep_alive: bool,
18    /// Proxy host (optional)
19    pub proxy_host: Option<String>,
20    /// Proxy port (optional)
21    pub proxy_port: Option<u16>,
22    /// User-Agent header
23    pub user_agent: String,
24}
25
26impl HttpProfile {
27    /// Create a new HTTP profile with default settings
28    pub fn new() -> Self {
29        Self {
30            req_method: "POST".to_string(),
31            endpoint: "sms.tencentcloudapi.com".to_string(),
32            req_timeout: 60,
33            connect_timeout: 60,
34            keep_alive: false,
35            proxy_host: None,
36            proxy_port: None,
37            user_agent: "TencentCloud-SDK-Rust/1.0.0".to_string(),
38        }
39    }
40
41    /// Set the HTTP request method
42    pub fn set_req_method<S: Into<String>>(&mut self, method: S) -> &mut Self {
43        self.req_method = method.into();
44        self
45    }
46
47    /// Set the API endpoint
48    pub fn set_endpoint<S: Into<String>>(&mut self, endpoint: S) -> &mut Self {
49        self.endpoint = endpoint.into();
50        self
51    }
52
53    /// Set the request timeout in seconds
54    pub fn set_req_timeout(&mut self, timeout: u64) -> &mut Self {
55        self.req_timeout = timeout;
56        self
57    }
58
59    /// Set the connection timeout in seconds
60    pub fn set_connect_timeout(&mut self, timeout: u64) -> &mut Self {
61        self.connect_timeout = timeout;
62        self
63    }
64
65    /// Set the keep-alive setting
66    pub fn set_keep_alive(&mut self, keep_alive: bool) -> &mut Self {
67        self.keep_alive = keep_alive;
68        self
69    }
70
71    /// Set the proxy host
72    pub fn set_proxy_host<S: Into<String>>(&mut self, host: Option<S>) -> &mut Self {
73        self.proxy_host = host.map(|h| h.into());
74        self
75    }
76
77    /// Set the proxy port
78    pub fn set_proxy_port(&mut self, port: Option<u16>) -> &mut Self {
79        self.proxy_port = port;
80        self
81    }
82
83    /// Set the User-Agent header
84    pub fn set_user_agent<S: Into<String>>(&mut self, user_agent: S) -> &mut Self {
85        self.user_agent = user_agent.into();
86        self
87    }
88
89    /// Get the full endpoint URL with protocol
90    pub fn get_full_endpoint(&self) -> String {
91        if self.endpoint.starts_with("http://") || self.endpoint.starts_with("https://") {
92            self.endpoint.clone()
93        } else {
94            format!("https://{}", self.endpoint)
95        }
96    }
97
98    /// Get request timeout as Duration
99    pub fn get_req_timeout(&self) -> Duration {
100        Duration::from_secs(self.req_timeout)
101    }
102
103    /// Get connection timeout as Duration
104    pub fn get_connect_timeout(&self) -> Duration {
105        Duration::from_secs(self.connect_timeout)
106    }
107
108    /// Check if proxy is configured
109    pub fn has_proxy(&self) -> bool {
110        self.proxy_host.is_some() && self.proxy_port.is_some()
111    }
112
113    /// Get proxy URL if configured
114    pub fn get_proxy_url(&self) -> Option<String> {
115        if let (Some(host), Some(port)) = (&self.proxy_host, self.proxy_port) {
116            Some(format!("http://{}:{}", host, port))
117        } else {
118            None
119        }
120    }
121}
122
123impl Default for HttpProfile {
124    fn default() -> Self {
125        Self::new()
126    }
127}
128
129/// Client configuration profile
130#[derive(Debug, Clone)]
131pub struct ClientProfile {
132    /// HTTP profile for request settings
133    pub http_profile: HttpProfile,
134    /// Signature method (default: HmacSHA256)
135    pub sign_method: String,
136    /// API version
137    pub api_version: String,
138    /// Language for error messages
139    pub language: String,
140    /// Debug mode
141    pub debug: bool,
142}
143
144impl ClientProfile {
145    /// Create a new client profile with default settings
146    pub fn new() -> Self {
147        Self {
148            http_profile: HttpProfile::new(),
149            sign_method: "HmacSHA256".to_string(),
150            api_version: "2021-01-11".to_string(),
151            language: "en-US".to_string(),
152            debug: false,
153        }
154    }
155
156    /// Create a new client profile with custom HTTP profile
157    pub fn with_http_profile(http_profile: HttpProfile) -> Self {
158        Self {
159            http_profile,
160            sign_method: "HmacSHA256".to_string(),
161            api_version: "2021-01-11".to_string(),
162            language: "en-US".to_string(),
163            debug: false,
164        }
165    }
166
167    /// Set the HTTP profile
168    pub fn set_http_profile(&mut self, profile: HttpProfile) -> &mut Self {
169        self.http_profile = profile;
170        self
171    }
172
173    /// Set the signature method
174    pub fn set_sign_method<S: Into<String>>(&mut self, method: S) -> &mut Self {
175        self.sign_method = method.into();
176        self
177    }
178
179    /// Set the API version
180    pub fn set_api_version<S: Into<String>>(&mut self, version: S) -> &mut Self {
181        self.api_version = version.into();
182        self
183    }
184
185    /// Set the language
186    pub fn set_language<S: Into<String>>(&mut self, language: S) -> &mut Self {
187        self.language = language.into();
188        self
189    }
190
191    /// Set the debug mode
192    pub fn set_debug(&mut self, debug: bool) -> &mut Self {
193        self.debug = debug;
194        self
195    }
196
197    /// Get the HTTP profile
198    pub fn get_http_profile(&self) -> &HttpProfile {
199        &self.http_profile
200    }
201
202    /// Get the signature method
203    pub fn get_sign_method(&self) -> &str {
204        &self.sign_method
205    }
206
207    /// Get the API version
208    pub fn get_api_version(&self) -> &str {
209        &self.api_version
210    }
211
212    /// Get the language
213    pub fn get_language(&self) -> &str {
214        &self.language
215    }
216
217    /// Check if debug mode is enabled
218    pub fn is_debug(&self) -> bool {
219        self.debug
220    }
221}
222
223impl Default for ClientProfile {
224    fn default() -> Self {
225        Self::new()
226    }
227}
228
229#[cfg(test)]
230mod tests {
231    use super::*;
232
233    #[test]
234    fn test_http_profile_defaults() {
235        let profile = HttpProfile::new();
236        assert_eq!(profile.req_method, "POST");
237        assert_eq!(profile.endpoint, "sms.tencentcloudapi.com");
238        assert_eq!(profile.req_timeout, 60);
239        assert_eq!(profile.connect_timeout, 60);
240        assert!(!profile.keep_alive);
241        assert!(profile.proxy_host.is_none());
242        assert!(profile.proxy_port.is_none());
243    }
244
245    #[test]
246    fn test_http_profile_configuration() {
247        let mut profile = HttpProfile::new();
248        profile
249            .set_req_method("GET")
250            .set_endpoint("custom.endpoint.com")
251            .set_req_timeout(30)
252            .set_connect_timeout(30)
253            .set_keep_alive(true)
254            .set_proxy_host(Some("proxy.example.com"))
255            .set_proxy_port(Some(8080));
256
257        assert_eq!(profile.req_method, "GET");
258        assert_eq!(profile.endpoint, "custom.endpoint.com");
259        assert_eq!(profile.req_timeout, 30);
260        assert_eq!(profile.connect_timeout, 30);
261        assert!(profile.keep_alive);
262        assert_eq!(profile.proxy_host, Some("proxy.example.com".to_string()));
263        assert_eq!(profile.proxy_port, Some(8080));
264    }
265
266    #[test]
267    fn test_http_profile_full_endpoint() {
268        let mut profile = HttpProfile::new();
269        assert_eq!(
270            profile.get_full_endpoint(),
271            "https://sms.tencentcloudapi.com"
272        );
273
274        profile.set_endpoint("http://custom.endpoint.com");
275        assert_eq!(profile.get_full_endpoint(), "http://custom.endpoint.com");
276
277        profile.set_endpoint("https://custom.endpoint.com");
278        assert_eq!(profile.get_full_endpoint(), "https://custom.endpoint.com");
279    }
280
281    #[test]
282    fn test_http_profile_proxy() {
283        let mut profile = HttpProfile::new();
284        assert!(!profile.has_proxy());
285        assert!(profile.get_proxy_url().is_none());
286
287        profile.set_proxy_host(Some("proxy.example.com"));
288        assert!(!profile.has_proxy()); // Still false because port is not set
289
290        profile.set_proxy_port(Some(8080));
291        assert!(profile.has_proxy());
292        assert_eq!(
293            profile.get_proxy_url(),
294            Some("http://proxy.example.com:8080".to_string())
295        );
296    }
297
298    #[test]
299    fn test_client_profile_defaults() {
300        let profile = ClientProfile::new();
301        assert_eq!(profile.sign_method, "HmacSHA256");
302        assert_eq!(profile.api_version, "2021-01-11");
303        assert_eq!(profile.language, "en-US");
304        assert!(!profile.debug);
305    }
306
307    #[test]
308    fn test_client_profile_configuration() {
309        let mut profile = ClientProfile::new();
310        profile
311            .set_sign_method("HmacSHA1")
312            .set_api_version("2019-07-11")
313            .set_language("zh-CN")
314            .set_debug(true);
315
316        assert_eq!(profile.sign_method, "HmacSHA1");
317        assert_eq!(profile.api_version, "2019-07-11");
318        assert_eq!(profile.language, "zh-CN");
319        assert!(profile.debug);
320    }
321}