Skip to main content

usesend_api/types/
email.rs

1use serde::{Deserialize, Serialize};
2use std::collections::HashMap;
3
4use super::{DomainId, EmailId, StringOrVec};
5
6// --- Enums ---
7
8#[derive(Debug, Clone, Serialize, Deserialize, PartialEq, Eq, Hash)]
9#[serde(rename_all = "SCREAMING_SNAKE_CASE")]
10pub enum EmailEventStatus {
11    Scheduled,
12    Queued,
13    Sent,
14    DeliveryDelayed,
15    Bounced,
16    Rejected,
17    RenderingFailure,
18    Delivered,
19    Opened,
20    Clicked,
21    Complained,
22    Failed,
23    Cancelled,
24    Suppressed,
25}
26
27// --- Types ---
28
29#[derive(Debug, Clone, Serialize, Deserialize)]
30pub struct Attachment {
31    pub filename: String,
32    pub content: String,
33}
34
35#[derive(Debug, Clone, Serialize, Deserialize)]
36#[serde(rename_all = "camelCase")]
37pub struct EmailEvent {
38    pub email_id: EmailId,
39    pub status: EmailEventStatus,
40    pub created_at: String,
41    #[serde(skip_serializing_if = "Option::is_none")]
42    pub data: Option<serde_json::Value>,
43}
44
45#[derive(Debug, Clone, Serialize, Deserialize)]
46#[serde(rename_all = "camelCase")]
47pub struct EmailListItem {
48    pub id: String,
49    pub to: StringOrVec,
50    pub from: String,
51    pub subject: String,
52    #[serde(skip_serializing_if = "Option::is_none")]
53    pub html: Option<String>,
54    #[serde(skip_serializing_if = "Option::is_none")]
55    pub text: Option<String>,
56    pub created_at: String,
57    pub updated_at: String,
58    pub latest_status: Option<EmailEventStatus>,
59    #[serde(skip_serializing_if = "Option::is_none")]
60    pub scheduled_at: Option<String>,
61    #[serde(skip_serializing_if = "Option::is_none")]
62    pub domain_id: Option<DomainId>,
63    #[serde(skip_serializing_if = "Option::is_none")]
64    pub reply_to: Option<StringOrVec>,
65    #[serde(skip_serializing_if = "Option::is_none")]
66    pub cc: Option<StringOrVec>,
67    #[serde(skip_serializing_if = "Option::is_none")]
68    pub bcc: Option<StringOrVec>,
69}
70
71#[derive(Debug, Clone, Serialize, Deserialize)]
72#[serde(rename_all = "camelCase")]
73pub struct EmailDetail {
74    pub id: EmailId,
75    pub team_id: i64,
76    pub to: StringOrVec,
77    pub from: String,
78    pub subject: String,
79    #[serde(skip_serializing_if = "Option::is_none")]
80    pub html: Option<String>,
81    #[serde(skip_serializing_if = "Option::is_none")]
82    pub text: Option<String>,
83    pub created_at: String,
84    pub updated_at: String,
85    #[serde(skip_serializing_if = "Option::is_none")]
86    pub reply_to: Option<StringOrVec>,
87    #[serde(skip_serializing_if = "Option::is_none")]
88    pub cc: Option<StringOrVec>,
89    #[serde(skip_serializing_if = "Option::is_none")]
90    pub bcc: Option<StringOrVec>,
91    pub email_events: Vec<EmailEvent>,
92}
93
94// --- Requests ---
95
96#[derive(Debug, Clone, Serialize, Deserialize)]
97#[serde(rename_all = "camelCase")]
98pub struct SendEmailRequest {
99    pub to: StringOrVec,
100    pub from: String,
101    #[serde(skip_serializing_if = "Option::is_none")]
102    pub subject: Option<String>,
103    #[serde(skip_serializing_if = "Option::is_none")]
104    pub template_id: Option<String>,
105    #[serde(skip_serializing_if = "Option::is_none")]
106    pub variables: Option<HashMap<String, String>>,
107    #[serde(skip_serializing_if = "Option::is_none")]
108    pub reply_to: Option<StringOrVec>,
109    #[serde(skip_serializing_if = "Option::is_none")]
110    pub cc: Option<StringOrVec>,
111    #[serde(skip_serializing_if = "Option::is_none")]
112    pub bcc: Option<StringOrVec>,
113    #[serde(skip_serializing_if = "Option::is_none")]
114    pub text: Option<String>,
115    #[serde(skip_serializing_if = "Option::is_none")]
116    pub html: Option<String>,
117    #[serde(skip_serializing_if = "Option::is_none")]
118    pub headers: Option<HashMap<String, String>>,
119    #[serde(skip_serializing_if = "Option::is_none")]
120    pub attachments: Option<Vec<Attachment>>,
121    #[serde(skip_serializing_if = "Option::is_none")]
122    pub scheduled_at: Option<String>,
123    #[serde(skip_serializing_if = "Option::is_none")]
124    pub in_reply_to_id: Option<String>,
125}
126
127#[derive(Debug, Clone, Serialize, Deserialize)]
128#[serde(rename_all = "camelCase")]
129pub struct RescheduleEmailRequest {
130    pub scheduled_at: String,
131}
132
133#[derive(Debug, Clone, Default, Serialize, Deserialize)]
134#[serde(rename_all = "camelCase")]
135pub struct ListEmailsParams {
136    #[serde(skip_serializing_if = "Option::is_none")]
137    pub page: Option<String>,
138    #[serde(skip_serializing_if = "Option::is_none")]
139    pub limit: Option<String>,
140    #[serde(skip_serializing_if = "Option::is_none")]
141    pub start_date: Option<String>,
142    #[serde(skip_serializing_if = "Option::is_none")]
143    pub end_date: Option<String>,
144    #[serde(skip_serializing_if = "Option::is_none")]
145    pub domain_id: Option<StringOrVec>,
146}
147
148// --- Responses ---
149
150#[derive(Debug, Clone, Serialize, Deserialize)]
151#[serde(rename_all = "camelCase")]
152pub struct SendEmailResponse {
153    pub email_id: EmailId,
154}
155
156#[derive(Debug, Clone, Serialize, Deserialize)]
157pub struct BatchSendResponse {
158    pub data: Vec<SendEmailResponse>,
159}
160
161#[derive(Debug, Clone, Serialize, Deserialize)]
162pub struct ListEmailsResponse {
163    pub data: Vec<EmailListItem>,
164    pub count: i64,
165}