oci_api/services/email/
client.rs1use crate::client::Oci;
4use crate::error::{Error, Result};
5use crate::services::email::models::*;
6
7#[derive(Clone)]
9pub struct EmailDelivery {
10 oci_client: Oci,
12
13 submit_endpoint: String,
15}
16
17impl EmailDelivery {
18 pub async fn new(oci_client: Oci) -> Result<Self> {
25 let tenancy_id = oci_client.tenancy_id().to_string();
27 let region = oci_client.region().to_string();
28
29 let config =
31 Self::get_email_configuration_internal(&oci_client, &tenancy_id, ®ion).await?;
32
33 Ok(Self {
34 oci_client,
35 submit_endpoint: config.http_submit_endpoint,
36 })
37 }
38
39 async fn get_email_configuration_internal(
41 oci_client: &Oci,
42 compartment_id: &str,
43 region: &str,
44 ) -> Result<EmailConfiguration> {
45 let path = format!("/20170907/configuration?compartmentId={compartment_id}");
47 let host = format!("ctrl.email.{region}.oci.oraclecloud.com");
48 let url = format!("https://{host}{path}");
49
50 let (date_header, auth_header) = oci_client
52 .signer()
53 .sign_request("GET", &path, &host, None)?;
54
55 let response = oci_client
57 .client()
58 .get(&url)
59 .header("host", &host)
60 .header("date", &date_header)
61 .header("authorization", &auth_header)
62 .send()
63 .await?;
64
65 if !response.status().is_success() {
66 let status = response.status();
67 let body = response.text().await?;
68 return Err(Error::ApiError {
69 code: status.to_string(),
70 message: body,
71 });
72 }
73
74 response.json().await.map_err(Into::into)
75 }
76
77 pub async fn get_email_configuration(
82 &self,
83 compartment_id: impl Into<String>,
84 ) -> Result<EmailConfiguration> {
85 let compartment_id = compartment_id.into();
86 let region = self.oci_client.region().to_string();
87 Self::get_email_configuration_internal(&self.oci_client, &compartment_id, ®ion).await
88 }
89
90 pub async fn send(&self, mut email: Email) -> Result<SubmitEmailResponse> {
98 let compartment_id = self.oci_client.compartment_id().to_string();
100
101 if email.sender.compartment_id.is_empty() {
103 email.sender.set_compartment_id(&compartment_id);
104 }
105
106 let path = "/20220926/actions/submitEmail";
108 let url = format!("https://{}{}", &self.submit_endpoint, path);
109
110 let body_json = serde_json::to_string(&email)?;
112
113 let body_sha256 = {
115 use base64::{Engine, engine::general_purpose};
116 use sha2::{Digest, Sha256};
117 let mut hasher = Sha256::new();
118 hasher.update(body_json.as_bytes());
119 let result = hasher.finalize();
120 general_purpose::STANDARD.encode(result)
121 };
122
123 let (date_header, auth_header) = self.oci_client.signer().sign_request(
125 "POST",
126 path,
127 &self.submit_endpoint,
128 Some(&body_json),
129 )?;
130
131 let response = self
133 .oci_client
134 .client()
135 .post(&url)
136 .header("host", &self.submit_endpoint)
137 .header("date", &date_header)
138 .header("authorization", &auth_header)
139 .header("content-type", "application/json")
140 .header("content-length", body_json.len().to_string())
141 .header("x-content-sha256", &body_sha256)
142 .body(body_json)
143 .send()
144 .await?;
145
146 if !response.status().is_success() {
147 let status = response.status();
148 let body = response.text().await?;
149 return Err(Error::ApiError {
150 code: status.to_string(),
151 message: body,
152 });
153 }
154
155 let submit_response: SubmitEmailResponse = response.json().await?;
156 Ok(submit_response)
157 }
158
159 pub async fn list_senders(
166 &self,
167 compartment_id: impl Into<String>,
168 lifecycle_state: Option<&str>,
169 email_address: Option<&str>,
170 ) -> Result<Vec<SenderSummary>> {
171 let compartment_id = compartment_id.into();
172
173 let mut query_params = vec![format!("compartmentId={}", compartment_id)];
175
176 if let Some(state) = lifecycle_state {
177 query_params.push(format!("lifecycleState={state}"));
178 }
179
180 if let Some(email) = email_address {
181 query_params.push(format!("emailAddress={email}"));
182 }
183
184 let query_string = query_params.join("&");
185 let path = format!("/20170907/senders?{query_string}");
186 let host = format!(
187 "ctrl.email.{}.oci.oraclecloud.com",
188 self.oci_client.region()
189 );
190 let url = format!("https://{host}{path}");
191
192 let (date_header, auth_header) = self
194 .oci_client
195 .signer()
196 .sign_request("GET", &path, &host, None)?;
197
198 let response = self
200 .oci_client
201 .client()
202 .get(&url)
203 .header("host", &host)
204 .header("date", &date_header)
205 .header("authorization", &auth_header)
206 .send()
207 .await?;
208
209 if !response.status().is_success() {
210 let status = response.status();
211 let body = response.text().await?;
212 return Err(Error::ApiError {
213 code: status.to_string(),
214 message: body,
215 });
216 }
217
218 let senders: Vec<SenderSummary> = response.json().await?;
219 Ok(senders)
220 }
221}