Current section

Files

Jump to
gleesend src resend emails.gleam
Raw

src/resend/emails.gleam

import gleam/dynamic
import gleam/hackney
import gleam/http.{Post}
import gleam/http/request
import gleam/json
import gleam/list
import gleam/option.{type Option, None, Some}
import gleam/result.{try}
import resend.{type Resend}
pub type ResendEmail {
ResendEmail(
client: Resend,
from: String,
to: List(String),
subject: String,
bcc: Option(List(String)),
cc: Option(List(String)),
reply_to: Option(List(String)),
html: Option(String),
text: Option(String),
)
}
pub fn with_bcc(resend: ResendEmail, bcc: List(String)) {
ResendEmail(..resend, bcc: Some(bcc))
}
pub fn with_cc(resend: ResendEmail, cc: List(String)) {
ResendEmail(..resend, cc: Some(cc))
}
pub fn with_reply_to(resend: ResendEmail, reply_to: List(String)) {
ResendEmail(..resend, reply_to: Some(reply_to))
}
pub fn with_html(resend: ResendEmail, html: String) {
ResendEmail(..resend, html: Some(html))
}
pub fn with_text(resend: ResendEmail, text: String) {
ResendEmail(..resend, text: Some(text))
}
pub fn create_email(
client client: Resend,
from from: String,
to to: List(String),
subject subject: String,
) {
ResendEmail(
client:,
from:,
to:,
subject:,
bcc: None,
cc: None,
reply_to: None,
html: None,
text: None,
)
}
pub type SendEmailError {
RequestError
BadRequestError
ParseResponseBodyError
}
pub type SuccessResponse {
SuccessResponse(id: String)
}
pub fn send_email(email: ResendEmail) {
let assert Ok(request) = request.to("https://api.resend.com/emails")
let body =
json.object(
list.concat([
[
#("from", json.string(email.from)),
#("to", json.array(email.to, fn(a) { json.string(a) })),
#("subject", json.string(email.from)),
],
case email.bcc {
Some(bcc) -> [#("bcc", json.array(bcc, fn(a) { json.string(a) }))]
None -> []
},
case email.cc {
Some(cc) -> [#("cc", json.array(cc, fn(a) { json.string(a) }))]
None -> []
},
case email.reply_to {
Some(reply_to) -> [
#("reply_to", json.array(reply_to, fn(a) { json.string(a) })),
]
None -> []
},
case email.html {
Some(html) -> [#("html", json.string(html))]
None -> []
},
case email.text {
Some(text) -> [#("text", json.string(text))]
None -> []
},
]),
)
use response <- try(
request
|> request.prepend_header("accept", "application/vnd.hmrc.1.0+json")
|> request.prepend_header("Content-Type", "application/json")
|> request.prepend_header(
"Authorization",
"Bearer " <> email.client.api_key,
)
|> request.set_method(Post)
|> request.set_body(
body
|> json.to_string,
)
|> hackney.send
|> result.replace_error(RequestError),
)
let body_decoder =
dynamic.decode1(SuccessResponse, dynamic.field("id", dynamic.string))
case response.status {
200 ->
case json.decode(response.body, body_decoder) {
Ok(body) -> Ok(body)
Error(_) -> Error(ParseResponseBodyError)
}
_ -> Error(BadRequestError)
}
}