diff --git a/Cargo.lock b/Cargo.lock index 642edbd..2e5849e 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -7,13 +7,13 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "78d1833b3838dbe990df0f1f87baf640cf6146e898166afe401839d1b001e570" dependencies = [ "bitflags", - "bytes", + "bytes 0.5.6", "futures-core", "futures-sink", "log", "pin-project 0.4.27", - "tokio", - "tokio-util", + "tokio 0.2.24", + "tokio-util 0.3.1", ] [[package]] @@ -50,7 +50,7 @@ dependencies = [ "base64 0.13.0", "bitflags", "brotli2", - "bytes", + "bytes 0.5.6", "cookie", "copyless", "derive_more", @@ -61,7 +61,7 @@ dependencies = [ "futures-core", "futures-util", "fxhash", - "h2", + "h2 0.2.7", "http", "httparse", "indexmap", @@ -117,7 +117,7 @@ dependencies = [ "futures-channel", "futures-util", "smallvec", - "tokio", + "tokio 0.2.24", ] [[package]] @@ -133,7 +133,7 @@ dependencies = [ "futures-channel", "futures-util", "log", - "mio", + "mio 0.6.23", "mio-uds", "num_cpus", "slab", @@ -201,7 +201,7 @@ dependencies = [ "actix-rt", "actix-service", "bitflags", - "bytes", + "bytes 0.5.6", "either", "futures-channel", "futures-sink", @@ -230,7 +230,7 @@ dependencies = [ "actix-utils", "actix-web-codegen", "awc", - "bytes", + "bytes 0.5.6", "derive_more", "encoding_rs", "futures-channel", @@ -311,12 +311,29 @@ dependencies = [ "winapi 0.3.9", ] +[[package]] +name = "anyhow" +version = "1.0.38" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "afddf7f520a80dbf76e6f50a35bca42a2331ef227a28b3b6dc5c2e2338d114b1" + [[package]] name = "arrayvec" version = "0.5.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "23b62fc65de8e4e7f52534fb52b0f3ed04746ae267519eef2a83941e8085068b" +[[package]] +name = "async-channel" +version = "1.5.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "59740d83946db6a5af71ae25ddf9562c2b176b2ca42cf99a455f09f4a220d6b9" +dependencies = [ + "concurrent-queue", + "event-listener", + "futures-core", +] + [[package]] name = "async-trait" version = "0.1.42" @@ -354,7 +371,7 @@ dependencies = [ "actix-rt", "actix-service", "base64 0.13.0", - "bytes", + "bytes 0.5.6", "cfg-if 1.0.0", "derive_more", "futures-core", @@ -497,15 +514,27 @@ version = "0.5.6" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "0e4cec68f03f32e44924783795810fa50a7035d8c8ebe78580ad7e6c703fba38" +[[package]] +name = "bytes" +version = "1.0.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b700ce4376041dcd0a327fd0097c41095743c4c8af8887265942faf1100bd040" + [[package]] name = "bytestring" version = "0.1.5" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "fc7c05fa5172da78a62d9949d662d2ac89d4cc7355d7b49adee5163f1fb3f363" dependencies = [ - "bytes", + "bytes 0.5.6", ] +[[package]] +name = "cache-padded" +version = "1.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "631ae5198c9be5e753e5cc215e1bd73c2b466a3565173db433f52bb9d3e66dba" + [[package]] name = "cargo_metadata" version = "0.12.1" @@ -558,6 +587,15 @@ dependencies = [ "autocfg", ] +[[package]] +name = "concurrent-queue" +version = "1.2.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "30ed07550be01594c6026cff2a1d7fe9c8f683caa798e12b68694ac9e88286a3" +dependencies = [ + "cache-padded", +] + [[package]] name = "config" version = "0.10.1" @@ -658,6 +696,26 @@ dependencies = [ "subtle", ] +[[package]] +name = "data-encoding" +version = "2.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "993a608597367c6377b258c25d7120740f00ed23a2252b729b1932dd7866f908" + +[[package]] +name = "deadpool" +version = "0.7.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3d126179d86aee4556e54f5f3c6bf6d9884e7cc52cef82f77ee6f90a7747616d" +dependencies = [ + "async-trait", + "config", + "crossbeam-queue", + "num_cpus", + "serde", + "tokio 1.0.2", +] + [[package]] name = "derive_more" version = "0.99.11" @@ -739,6 +797,12 @@ dependencies = [ "regex", ] +[[package]] +name = "event-listener" +version = "2.5.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f7531096570974c3a9dcf9e4b8e1cede1ec26cf5046219fb3b9d897503b9be59" + [[package]] name = "fake" version = "2.3.0" @@ -754,6 +818,15 @@ version = "0.1.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "e88a8acf291dafb59c2d96e8f59828f3838bb1a70398823ade51a84de6a6deed" +[[package]] +name = "fastrand" +version = "1.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ca5faf057445ce5c9d4329e382b2ce7ca38550ef3b73a5348362d5f24e0c7fe3" +dependencies = [ + "instant", +] + [[package]] name = "flate2" version = "1.0.19" @@ -852,6 +925,21 @@ version = "0.3.8" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "611834ce18aaa1bd13c4b374f5d653e1027cf99b6b502584ff8c9a64413b30bb" +[[package]] +name = "futures-lite" +version = "1.11.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b4481d0cd0de1d204a4fa55e7d45f07b1d958abcb06714b3446438e2eff695fb" +dependencies = [ + "fastrand", + "futures-core", + "futures-io", + "memchr", + "parking", + "pin-project-lite 0.2.0", + "waker-fn", +] + [[package]] name = "futures-macro" version = "0.3.8" @@ -879,6 +967,12 @@ dependencies = [ "once_cell", ] +[[package]] +name = "futures-timer" +version = "3.0.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e64b03909df88034c26dc1547e8970b91f98bdb65165d6a4e9110d94263dbb2c" + [[package]] name = "futures-util" version = "0.3.8" @@ -984,7 +1078,7 @@ version = "0.2.7" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "5e4728fd124914ad25e99e3d15a9361a879f6620f63cb56bbb08f95abb97a535" dependencies = [ - "bytes", + "bytes 0.5.6", "fnv", "futures-core", "futures-sink", @@ -992,8 +1086,28 @@ dependencies = [ "http", "indexmap", "slab", - "tokio", - "tokio-util", + "tokio 0.2.24", + "tokio-util 0.3.1", + "tracing", + "tracing-futures", +] + +[[package]] +name = "h2" +version = "0.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6b67e66362108efccd8ac053abafc8b7a8d86a37e6e48fc4f6f7485eb5e9e6a5" +dependencies = [ + "bytes 1.0.1", + "fnv", + "futures-core", + "futures-sink", + "futures-util", + "http", + "indexmap", + "slab", + "tokio 1.0.2", + "tokio-util 0.6.1", "tracing", "tracing-futures", ] @@ -1067,7 +1181,7 @@ version = "0.2.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "84129d298a6d57d246960ff8eb831ca4af3f96d29e2e28848dae275408658e26" dependencies = [ - "bytes", + "bytes 0.5.6", "fnv", "itoa", ] @@ -1078,10 +1192,42 @@ version = "0.3.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "13d5ff830006f7646652e057693569bfe0d51760c0085a071769d142a205111b" dependencies = [ - "bytes", + "bytes 0.5.6", "http", ] +[[package]] +name = "http-body" +version = "0.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2861bd27ee074e5ee891e8b539837a9430012e249d7f0ca2d795650f579c1994" +dependencies = [ + "bytes 1.0.1", + "http", +] + +[[package]] +name = "http-types" +version = "2.9.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f2ab8d0085fb82859c9adf050bd53992297ecdd03a665a230dfa50c8c964bf3d" +dependencies = [ + "anyhow", + "async-channel", + "base64 0.13.0", + "cookie", + "futures-lite", + "http", + "infer", + "pin-project-lite 0.1.11", + "rand", + "serde", + "serde_json", + "serde_qs", + "serde_urlencoded", + "url", +] + [[package]] name = "httparse" version = "1.3.4" @@ -1100,19 +1246,43 @@ version = "0.13.9" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "f6ad767baac13b44d4529fcf58ba2cd0995e36e7b435bc5b039de6f47e880dbf" dependencies = [ - "bytes", + "bytes 0.5.6", "futures-channel", "futures-core", "futures-util", - "h2", + "h2 0.2.7", "http", - "http-body", + "http-body 0.3.1", "httparse", "httpdate", "itoa", "pin-project 1.0.2", "socket2", - "tokio", + "tokio 0.2.24", + "tower-service", + "tracing", + "want", +] + +[[package]] +name = "hyper" +version = "0.14.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "12219dc884514cb4a6a03737f4413c0e01c23a1b059b0156004b23f1e19dccbe" +dependencies = [ + "bytes 1.0.1", + "futures-channel", + "futures-core", + "futures-util", + "h2 0.3.0", + "http", + "http-body 0.4.0", + "httparse", + "httpdate", + "itoa", + "pin-project 1.0.2", + "socket2", + "tokio 1.0.2", "tower-service", "tracing", "want", @@ -1124,12 +1294,12 @@ version = "0.21.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "37743cc83e8ee85eacfce90f2f4102030d9ff0a95244098d781e9bee4a90abb6" dependencies = [ - "bytes", + "bytes 0.5.6", "futures-util", - "hyper", + "hyper 0.13.9", "log", "rustls", - "tokio", + "tokio 0.2.24", "tokio-rustls", "webpki", ] @@ -1155,6 +1325,12 @@ dependencies = [ "hashbrown", ] +[[package]] +name = "infer" +version = "0.2.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "64e9829a50b42bb782c1df523f78d332fe371b10c661e78b7a3c34b0198e9fac" + [[package]] name = "instant" version = "0.1.9" @@ -1376,12 +1552,25 @@ dependencies = [ "kernel32-sys", "libc", "log", - "miow", + "miow 0.2.2", "net2", "slab", "winapi 0.2.8", ] +[[package]] +name = "mio" +version = "0.7.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e50ae3f04d169fcc9bde0b547d1c205219b7157e07ded9c5aff03e0637cb3ed7" +dependencies = [ + "libc", + "log", + "miow 0.3.6", + "ntapi", + "winapi 0.3.9", +] + [[package]] name = "mio-uds" version = "0.6.8" @@ -1390,7 +1579,7 @@ checksum = "afcb699eb26d4332647cc848492bbc15eafb26f08d0304550d5aa1f612e066f0" dependencies = [ "iovec", "libc", - "mio", + "mio 0.6.23", ] [[package]] @@ -1405,6 +1594,16 @@ dependencies = [ "ws2_32-sys", ] +[[package]] +name = "miow" +version = "0.3.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5a33c1b55807fbed163481b5ba66db4b2fa6cde694a5027be10fb724206c5897" +dependencies = [ + "socket2", + "winapi 0.3.9", +] + [[package]] name = "net2" version = "0.2.37" @@ -1439,6 +1638,15 @@ dependencies = [ "version_check", ] +[[package]] +name = "ntapi" +version = "0.3.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3f6bb902e437b6d86e03cce10a7e2af662292c5dfef23b65899ea3ac9354ad44" +dependencies = [ + "winapi 0.3.9", +] + [[package]] name = "num-integer" version = "0.1.44" @@ -1492,6 +1700,12 @@ version = "0.3.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "624a8340c38c1b80fd549087862da4ba43e08858af025b236e509b6649fc13d5" +[[package]] +name = "parking" +version = "2.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "427c3892f9e783d91cc128285287e70a59e206ca452770ece88a76f7a3eddd72" + [[package]] name = "parking_lot" version = "0.11.1" @@ -1777,13 +1991,13 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "0718f81a8e14c4dbb3b34cf23dc6aaf9ab8a0dfec160c534b3dbca1aaa21f47c" dependencies = [ "base64 0.13.0", - "bytes", + "bytes 0.5.6", "encoding_rs", "futures-core", "futures-util", "http", - "http-body", - "hyper", + "http-body 0.3.1", + "hyper 0.13.9", "hyper-rustls", "ipnet", "js-sys", @@ -1797,7 +2011,7 @@ dependencies = [ "serde", "serde_json", "serde_urlencoded", - "tokio", + "tokio 0.2.24", "tokio-rustls", "url", "wasm-bindgen", @@ -1966,6 +2180,18 @@ dependencies = [ "serde", ] +[[package]] +name = "serde_qs" +version = "0.7.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5af82de3c6549b001bec34961ff2d6a54339a87bab37ce901b693401f27de6cb" +dependencies = [ + "data-encoding", + "percent-encoding", + "serde", + "thiserror", +] + [[package]] name = "serde_urlencoded" version = "0.7.0" @@ -2104,7 +2330,7 @@ dependencies = [ "base64 0.13.0", "bitflags", "byteorder", - "bytes", + "bytes 0.5.6", "chrono", "crc", "crossbeam-channel", @@ -2175,7 +2401,7 @@ dependencies = [ "actix-rt", "actix-threadpool", "once_cell", - "tokio", + "tokio 0.2.24", "tokio-rustls", ] @@ -2384,14 +2610,14 @@ version = "0.2.24" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "099837d3464c16a808060bb3f02263b412f6fafcb5d01c533d309985fbeebe48" dependencies = [ - "bytes", + "bytes 0.5.6", "fnv", "futures-core", "iovec", "lazy_static", "libc", "memchr", - "mio", + "mio 0.6.23", "mio-uds", "num_cpus", "pin-project-lite 0.1.11", @@ -2401,6 +2627,20 @@ dependencies = [ "winapi 0.3.9", ] +[[package]] +name = "tokio" +version = "1.0.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0ca04cec6ff2474c638057b65798f60ac183e5e79d3448bb7163d36a39cff6ec" +dependencies = [ + "autocfg", + "bytes 1.0.1", + "libc", + "memchr", + "mio 0.7.7", + "pin-project-lite 0.2.0", +] + [[package]] name = "tokio-macros" version = "0.2.6" @@ -2420,22 +2660,48 @@ checksum = "e12831b255bcfa39dc0436b01e19fea231a37db570686c06ee72c423479f889a" dependencies = [ "futures-core", "rustls", - "tokio", + "tokio 0.2.24", "webpki", ] +[[package]] +name = "tokio-stream" +version = "0.1.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "76066865172052eb8796c686f0b441a93df8b08d40a950b062ffb9a426f00edd" +dependencies = [ + "futures-core", + "pin-project-lite 0.2.0", + "tokio 1.0.2", +] + [[package]] name = "tokio-util" version = "0.3.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "be8242891f2b6cbef26a2d7e8605133c2c554cd35b3e4948ea892d6d68436499" dependencies = [ - "bytes", + "bytes 0.5.6", "futures-core", "futures-sink", "log", "pin-project-lite 0.1.11", - "tokio", + "tokio 0.2.24", +] + +[[package]] +name = "tokio-util" +version = "0.6.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "12ae4751faa60b9f96dd8344d74592e5a17c0c9a220413dbc6942d14139bbfcc" +dependencies = [ + "bytes 1.0.1", + "futures-core", + "futures-sink", + "log", + "pin-project-lite 0.2.0", + "tokio 1.0.2", + "tokio-stream", ] [[package]] @@ -2576,7 +2842,7 @@ dependencies = [ "rand", "smallvec", "thiserror", - "tokio", + "tokio 0.2.24", "url", ] @@ -2596,7 +2862,7 @@ dependencies = [ "resolv-conf", "smallvec", "thiserror", - "tokio", + "tokio 0.2.24", "trust-dns-proto", ] @@ -2679,6 +2945,7 @@ dependencies = [ "idna", "matches", "percent-encoding", + "serde", ] [[package]] @@ -2718,6 +2985,12 @@ version = "0.9.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "b5a972e5669d67ba988ce3dc826706fb0a8b01471c088cb0b6110b805cc36aed" +[[package]] +name = "waker-fn" +version = "1.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9d5b2c62b4012a3e1eca5a7e077d13b3bf498c4073e33ccd58626607748ceeca" + [[package]] name = "want" version = "0.3.0" @@ -2914,6 +3187,26 @@ dependencies = [ "winapi 0.3.9", ] +[[package]] +name = "wiremock" +version = "0.4.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d9297d85d701557878bb9b768b048f464874b8c287b1426499f385f804817db1" +dependencies = [ + "async-trait", + "deadpool", + "futures", + "futures-timer", + "http-types", + "hyper 0.14.2", + "log", + "once_cell", + "regex", + "serde", + "serde_json", + "tokio 1.0.2", +] + [[package]] name = "ws2_32-sys" version = "0.2.1" @@ -2955,8 +3248,9 @@ dependencies = [ "reqwest", "serde", "serde-aux", + "serde_json", "sqlx", - "tokio", + "tokio 0.2.24", "tracing", "tracing-actix-web", "tracing-bunyan-formatter", @@ -2966,4 +3260,5 @@ dependencies = [ "unicode-segmentation", "uuid", "validator", + "wiremock", ] diff --git a/Cargo.toml b/Cargo.toml index 09aa013..e9bdb3d 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -38,3 +38,5 @@ claim = "0.4.0" quickcheck = "0.9.2" quickcheck_macros = "0.9.1" fake = "~2.3.0" +wiremock = "0.4.7" +serde_json = "1.0.61" diff --git a/configuration/base.yaml b/configuration/base.yaml index 885fa69..0c6780b 100644 --- a/configuration/base.yaml +++ b/configuration/base.yaml @@ -9,4 +9,6 @@ database: database_name: "newsletter" require_ssl: false email_client: - base_url: "localhost" \ No newline at end of file + base_url: "localhost" + sender_email: "test@gmail.com" + authorization_token: "my-secret-token" \ No newline at end of file diff --git a/src/configuration.rs b/src/configuration.rs index ad89e28..79752e6 100644 --- a/src/configuration.rs +++ b/src/configuration.rs @@ -1,3 +1,4 @@ +use crate::domain::SubscriberEmail; use serde_aux::field_attributes::deserialize_number_from_string; use sqlx::postgres::{PgConnectOptions, PgSslMode}; use std::convert::{TryFrom, TryInto}; @@ -50,6 +51,14 @@ impl DatabaseSettings { #[derive(serde::Deserialize)] pub struct EmailClientSettings { pub base_url: String, + pub sender_email: String, + pub authorization_token: String, +} + +impl EmailClientSettings { + pub fn sender(&self) -> Result { + SubscriberEmail::parse(self.sender_email.clone()) + } } pub fn get_configuration() -> Result { diff --git a/src/email_client.rs b/src/email_client.rs index dc51bd9..dc0217c 100644 --- a/src/email_client.rs +++ b/src/email_client.rs @@ -4,13 +4,17 @@ use reqwest::Client; pub struct EmailClient { http_client: Client, base_url: String, + sender: SubscriberEmail, + authorization_token: String, } impl EmailClient { - pub fn new(base_url: String) -> Self { + pub fn new(base_url: String, sender: SubscriberEmail, authorization_token: String) -> Self { Self { http_client: Client::new(), base_url, + sender, + authorization_token, } } @@ -20,7 +24,89 @@ impl EmailClient { subject: &str, html_content: &str, text_content: &str, - ) -> Result<(), String> { - todo!() + ) -> Result<(), reqwest::Error> { + let url = format!("{}/email", self.base_url); + let request_body = SendEmailRequest { + from: self.sender.as_ref().to_owned(), + to: recipient.as_ref().to_owned(), + subject: subject.into(), + html_body: html_content.into(), + text_body: text_content.into(), + }; + self.http_client + .post(&url) + .header("X-Postmark-Server-Token", &self.authorization_token) + .json(&request_body) + .send() + .await?; + Ok(()) + } +} + +#[derive(serde::Serialize)] +#[serde(rename_all = "PascalCase")] +struct SendEmailRequest { + from: String, + to: String, + subject: String, + html_body: String, + text_body: String, +} + +#[cfg(test)] +mod tests { + use crate::domain::SubscriberEmail; + use crate::email_client::EmailClient; + use fake::faker::internet::en::SafeEmail; + use fake::faker::lorem::en::{Paragraph, Sentence}; + use fake::{Fake, Faker}; + use wiremock::matchers::{header, header_exists, method, path}; + use wiremock::{Mock, MockServer, Request, ResponseTemplate}; + + struct SendEmailBodyMatcher; + + impl wiremock::Match for SendEmailBodyMatcher { + fn matches(&self, request: &Request) -> bool { + let result: Result = serde_json::from_slice(&request.body); + if let Ok(body) = result { + dbg!(&body); + body.get("From").is_some() + && body.get("To").is_some() + && body.get("Subject").is_some() + && body.get("HtmlBody").is_some() + && body.get("TextBody").is_some() + } else { + false + } + } + } + + #[actix_rt::test] + async fn send_email_fires_a_request_to_base_url() { + // Arrange + let mock_server = MockServer::start().await; + let sender = SubscriberEmail::parse(SafeEmail().fake()).unwrap(); + let email_client = EmailClient::new(mock_server.uri(), sender, Faker.fake()); + + let subscriber_email = SubscriberEmail::parse(SafeEmail().fake()).unwrap(); + let subject: String = Sentence(1..2).fake(); + let content: String = Paragraph(1..10).fake(); + + Mock::given(header_exists("X-Postmark-Server-Token")) + .and(header("Content-Type", "application/json")) + .and(path("/email")) + .and(method("POST")) + .and(SendEmailBodyMatcher) + .respond_with(ResponseTemplate::new(200)) + .expect(1) + .mount(&mock_server) + .await; + + // Act + let _ = email_client + .send_email(subscriber_email, &subject, &content, &content) + .await; + + // Assert } } diff --git a/src/main.rs b/src/main.rs index f68a351..081de94 100644 --- a/src/main.rs +++ b/src/main.rs @@ -16,7 +16,16 @@ async fn main() -> std::io::Result<()> { .connect_with(configuration.database.with_db()) .await .expect("Failed to connect to Postgres."); - let email_client = EmailClient::new(configuration.email_client.base_url); + + let sender_email = configuration + .email_client + .sender() + .expect("Invalid sender email address."); + let email_client = EmailClient::new( + configuration.email_client.base_url, + sender_email, + configuration.email_client.authorization_token, + ); let address = format!( "{}:{}", diff --git a/tests/health_check.rs b/tests/health_check.rs index 97af0c5..4041625 100644 --- a/tests/health_check.rs +++ b/tests/health_check.rs @@ -33,7 +33,16 @@ async fn spawn_app() -> TestApp { let mut configuration = get_configuration().expect("Failed to read configuration."); configuration.database.database_name = Uuid::new_v4().to_string(); let connection_pool = configure_database(&configuration.database).await; - let email_client = EmailClient::new(configuration.email_client.base_url); + + let sender_email = configuration + .email_client + .sender() + .expect("Invalid sender email address."); + let email_client = EmailClient::new( + configuration.email_client.base_url, + sender_email, + configuration.email_client.authorization_token, + ); let server = run(listener, connection_pool.clone(), email_client).expect("Failed to bind address");