Skip to main content

axene_mailer/resources/
contacts.rs

1//! The `contacts` resource: subscriber lists, contacts, CSV imports, bulk sends.
2
3use reqwest::Method;
4
5use super::{query, urlencode};
6use crate::error::Result;
7use crate::http::HttpTransport;
8use crate::models::{
9    AddContact, BulkSend, BulkSendResult, Contact, ContactList, ContactListDetail, CreateList,
10    CsvImportResult, UpdateList,
11};
12
13/// Accessed as `client.contacts()`.
14#[derive(Debug, Clone)]
15pub struct Contacts {
16    http: HttpTransport,
17}
18
19impl Contacts {
20    pub(crate) fn new(http: HttpTransport) -> Self {
21        Self { http }
22    }
23
24    /// List all subscriber lists in the active workspace.
25    pub async fn list_lists(&self) -> Result<Vec<ContactList>> {
26        self.http.request(Method::GET, "/v1/contacts/").await
27    }
28
29    /// Create a subscriber list.
30    pub async fn create_list(&self, params: &CreateList) -> Result<ContactList> {
31        self.http
32            .request_json(Method::POST, "/v1/contacts/", params)
33            .await
34    }
35
36    /// Get a list with a page of its contacts (zero-based `page`).
37    pub async fn get_list(
38        &self,
39        id: &str,
40        page: Option<u64>,
41        limit: Option<u64>,
42    ) -> Result<ContactListDetail> {
43        let q = query(&[
44            ("page", page.map(|p| p.to_string())),
45            ("limit", limit.map(|l| l.to_string())),
46        ]);
47        self.http
48            .request(Method::GET, &format!("/v1/contacts/{}{q}", urlencode(id)))
49            .await
50    }
51
52    /// Update a list's name, description, or icon (partial).
53    pub async fn update_list(&self, id: &str, params: &UpdateList) -> Result<ContactList> {
54        self.http
55            .request_json(
56                Method::PATCH,
57                &format!("/v1/contacts/{}", urlencode(id)),
58                params,
59            )
60            .await
61    }
62
63    /// Delete a list and all of its contacts.
64    pub async fn delete_list(&self, id: &str) -> Result<()> {
65        self.http
66            .request_empty(Method::DELETE, &format!("/v1/contacts/{}", urlencode(id)))
67            .await
68    }
69
70    /// Add a single contact to a list.
71    pub async fn add_contact(&self, list_id: &str, params: &AddContact) -> Result<Contact> {
72        self.http
73            .request_json(
74                Method::POST,
75                &format!("/v1/contacts/{}/contacts", urlencode(list_id)),
76                params,
77            )
78            .await
79    }
80
81    /// Remove a contact from a list.
82    pub async fn remove_contact(&self, list_id: &str, contact_id: &str) -> Result<()> {
83        self.http
84            .request_empty(
85                Method::DELETE,
86                &format!(
87                    "/v1/contacts/{}/contacts/{}",
88                    urlencode(list_id),
89                    urlencode(contact_id)
90                ),
91            )
92            .await
93    }
94
95    /// Import contacts from a CSV file (header row required). Sent as
96    /// `multipart/form-data` under the field `file`.
97    pub async fn upload_csv(
98        &self,
99        list_id: &str,
100        file: Vec<u8>,
101        filename: &str,
102    ) -> Result<CsvImportResult> {
103        self.http
104            .upload(
105                &format!("/v1/contacts/{}/upload", urlencode(list_id)),
106                file,
107                filename,
108            )
109            .await
110    }
111
112    /// Send a templated email to every contact in a list. The `contact_list_id`
113    /// field is set automatically to `list_id`.
114    pub async fn bulk_send(&self, list_id: &str, params: &BulkSend) -> Result<BulkSendResult> {
115        let mut body = params.clone();
116        body.contact_list_id = list_id.to_string();
117        self.http
118            .request_json(
119                Method::POST,
120                &format!("/v1/contacts/{}/send", urlencode(list_id)),
121                &body,
122            )
123            .await
124    }
125}