Skip to main content

agentmail/types/
lists.rs

1use serde::{Deserialize, Serialize};
2
3/// Which traffic direction a list governs. A path input only (there is no
4/// wire value to decode), so it has no unknown variant.
5#[derive(Clone, Copy, Debug, PartialEq, Eq)]
6pub enum ListDirection {
7    /// Applied to outbound (sent) mail.
8    Send,
9    /// Applied to inbound (received) mail.
10    Receive,
11    /// Applied to replies.
12    Reply,
13}
14
15impl ListDirection {
16    /// The path segment for this direction.
17    pub(crate) fn as_path(self) -> &'static str {
18        match self {
19            ListDirection::Send => "send",
20            ListDirection::Receive => "receive",
21            ListDirection::Reply => "reply",
22        }
23    }
24}
25
26/// Whether a list allows or blocks its entries. A path input only, so it has
27/// no unknown variant.
28#[derive(Clone, Copy, Debug, PartialEq, Eq)]
29pub enum ListKind {
30    /// An allow list.
31    Allow,
32    /// A block list.
33    Block,
34}
35
36impl ListKind {
37    /// The path segment for this kind.
38    pub(crate) fn as_path(self) -> &'static str {
39        match self {
40            ListKind::Allow => "allow",
41            ListKind::Block => "block",
42        }
43    }
44}
45
46/// Whether a list entry is an address or a whole domain.
47#[derive(Clone, Copy, Debug, PartialEq, Eq, Deserialize)]
48#[serde(rename_all = "lowercase")]
49pub enum EntryType {
50    /// A single email address.
51    Email,
52    /// A whole domain.
53    Domain,
54    /// An entry type this client version does not recognize.
55    #[serde(other)]
56    Unknown,
57}
58
59/// A single allow/block list entry.
60#[derive(Clone, Debug, Deserialize)]
61pub struct ListEntry {
62    /// The address or domain.
63    pub entry: String,
64    /// Free-text reason recorded with the entry.
65    #[serde(default)]
66    pub reason: Option<String>,
67    /// Whether the entry is an address or a domain.
68    #[serde(default = "unknown_entry_type")]
69    pub entry_type: EntryType,
70    /// The organization the entry belongs to.
71    #[serde(default)]
72    pub organization_id: Option<String>,
73    /// Whether the entry is read-only (system-managed).
74    #[serde(default)]
75    pub read_only: bool,
76    /// Timestamp the entry was created (RFC 3339).
77    #[serde(default)]
78    pub created_at: Option<String>,
79}
80
81fn unknown_entry_type() -> EntryType {
82    EntryType::Unknown
83}
84
85/// Request body for `create_list_entry`.
86#[derive(Clone, Debug, Default, Serialize)]
87pub struct CreateListEntry {
88    /// The address or domain to add.
89    pub entry: String,
90    /// An optional reason to record with the entry.
91    #[serde(skip_serializing_if = "Option::is_none")]
92    pub reason: Option<String>,
93}
94
95/// One page of list entries from `list_list_entries_page`.
96#[derive(Clone, Debug, Deserialize)]
97pub struct ListEntries {
98    /// Total entries in the list (not just this page).
99    pub count: u64,
100    /// This page of entries.
101    #[serde(default)]
102    pub entries: Vec<ListEntry>,
103    /// Cursor for the next page; `None` on the last page.
104    #[serde(default)]
105    pub next_page_token: Option<String>,
106}