deepl_rustls/lib.rs
1//! # deepl-rs
2//!
3//! Deepl-rs is a simple library for making requests to the DeepL API endpoint easier.
4//! And it also provides types wrapping to guarantee runtime safety.
5//!
6//! This is still a **WORK IN PROGRESS** library, please open an issue on GitHub to request
7//! features. Be aware breaking changes will be released frequently.
8//!
9//! # Usage
10//!
11//! ```rust
12//! use deepl::DeepLApi;
13//!
14//! let key = std::env::var("DEEPL_API_KEY").unwrap();
15//! let api = DeepLApi::with(&key).new();
16//! let response = api.translate_text("Hello World", Lang::ZH).await.unwrap();
17//!
18//! assert!(!response.translations.is_empty());
19//! ```
20//!
21//! See [`DeepLApi`] for detailed usage.
22//!
23//! # License
24//!
25//! This project is licensed under MIT license.
26//!
27
28mod endpoint;
29mod lang;
30
31use std::sync::Arc;
32
33//- Type Re-exporting
34pub use endpoint::{
35 document::{DocumentStatusResp, DocumentTranslateStatus, UploadDocumentResp},
36 glossary,
37 languages::{LangInfo, LangType},
38 translate::{TagHandling, TranslateTextResp},
39 usage::UsageResponse,
40 Error, Formality,
41};
42pub use lang::{Lang, LangConvertError};
43pub use reqwest;
44//-
45
46/// A struct that contains necessary data for runtime. Data is stored in
47/// [`Arc`], so it is cheap to clone in your App's code.
48///
49/// # Example
50///
51/// ```
52/// // simple API creation
53/// let deepl = DeepLApi::with("Your DeepL Key").new();
54///
55/// // **OR** customize it
56/// let duration = std::time::Duration::from_secs(30);
57/// let client = reqwest::Client::builder()
58/// .timeout(duration)
59/// .build()
60/// .unwrap();
61///
62/// // use the pro version API, and a custom client with
63/// // 30 secs timeout
64/// let deepl = DeepLApi::with("Your DeepL Key")
65/// .is_pro(true)
66/// .client(client)
67/// .new();
68/// ```
69#[derive(Debug, Clone)]
70pub struct DeepLApi {
71 inner: Arc<DeepLApiInner>,
72}
73
74/// The inner instance which actually holds data
75#[derive(Debug)]
76struct DeepLApiInner {
77 client: reqwest::Client,
78 key: String,
79 endpoint: reqwest::Url,
80}
81
82impl DeepLApi {
83 /// Create a new api instance with auth key.
84 pub fn with(key: &str) -> DeepLApiBuilder {
85 DeepLApiBuilder::init(key.to_string())
86 }
87
88 fn del(&self, url: reqwest::Url) -> reqwest::RequestBuilder {
89 self.inner
90 .client
91 .delete(url)
92 .header("Authorization", &self.inner.key)
93 }
94
95 fn post(&self, url: reqwest::Url) -> reqwest::RequestBuilder {
96 self.inner
97 .client
98 .post(url)
99 .header("Authorization", &self.inner.key)
100 }
101
102 fn get(&self, url: reqwest::Url) -> reqwest::RequestBuilder {
103 self.inner
104 .client
105 .get(url)
106 .header("Authorization", &self.inner.key)
107 }
108
109 fn get_endpoint(&self, route: &str) -> reqwest::Url {
110 self.inner.endpoint.join(route).unwrap()
111 }
112}
113
114/// The builder struct. **DO NOT USE IT IN YOUR APPS**
115pub struct DeepLApiBuilder {
116 is_pro: bool,
117 client: Option<reqwest::Client>,
118 key: String,
119}
120
121impl DeepLApiBuilder {
122 fn init(key: String) -> Self {
123 Self {
124 key,
125 is_pro: false,
126 client: None,
127 }
128 }
129
130 /// Set the a user defined [`reqwest::Client`]
131 pub fn client(&mut self, c: reqwest::Client) -> &mut Self {
132 self.client = Some(c);
133 self
134 }
135
136 /// Set if you want to use the pro version DeepL Api
137 pub fn is_pro(&mut self, is_pro: bool) -> &mut Self {
138 self.is_pro = is_pro;
139 self
140 }
141
142 /// Create a new instance of the DeepLApi
143 pub fn new(&self) -> DeepLApi {
144 let client = self.client.clone().unwrap_or_else(reqwest::Client::new);
145 let endpoint = if self.is_pro || !self.key.ends_with(":fx") {
146 "https://api.deepl.com/v2/"
147 } else {
148 "https://api-free.deepl.com/v2/"
149 };
150
151 let inner = DeepLApiInner {
152 key: format!("DeepL-Auth-Key {}", self.key),
153 client,
154 endpoint: reqwest::Url::parse(endpoint).unwrap(),
155 };
156
157 DeepLApi {
158 inner: Arc::new(inner),
159 }
160 }
161}