headless_lms_models/
email_deliveries.rs1use lettre::transport::smtp::Error;
2
3use crate::prelude::*;
4
5#[derive(Debug, Serialize, Deserialize, PartialEq, Clone)]
6pub struct EmailDelivery {
7 pub id: Uuid,
8 pub created_at: DateTime<Utc>,
9 pub updated_at: DateTime<Utc>,
10 pub deleted_at: Option<DateTime<Utc>>,
11 pub email_template_id: Uuid,
12 pub error: Option<String>,
13 pub sent: bool,
14 pub user_id: Uuid,
15}
16
17pub struct Email {
18 pub id: Uuid,
19 pub to: Uuid,
21 pub subject: Option<String>,
22 pub body: Option<serde_json::Value>,
23}
24
25pub async fn fetch_emails(conn: &mut PgConnection) -> ModelResult<Vec<Email>> {
26 let emails = sqlx::query_as!(
27 Email,
28 "
29SELECT ed.id AS id,
30 u.id AS to,
31 et.subject AS subject,
32 et.content AS body
33FROM email_deliveries ed
34 JOIN email_templates et ON et.id = ed.email_template_id
35 JOIN users u ON u.id = ed.user_id
36WHERE ed.deleted_at IS NULL
37 AND ed.sent = FALSE
38 AND ed.error IS NULL
39LIMIT 10000;
40 ",
41 )
42 .fetch_all(conn)
43 .await?;
44
45 Ok(emails)
46}
47
48pub async fn mark_as_sent(email_id: Uuid, conn: &mut PgConnection) -> ModelResult<()> {
49 sqlx::query!(
50 "
51update email_deliveries
52set sent = TRUE
53where id = $1;
54 ",
55 email_id
56 )
57 .execute(conn)
58 .await?;
59
60 Ok(())
61}
62
63pub async fn save_err_to_email(
64 email_id: Uuid,
65 err: Error,
66 conn: &mut PgConnection,
67) -> ModelResult<()> {
68 sqlx::query!(
69 "
70update email_deliveries
71set sent = FALSE,
72 error = $1
73where id = $2;
74 ",
75 err.to_string(),
76 email_id
77 )
78 .execute(conn)
79 .await?;
80
81 Ok(())
82}