1use super::AttachmentFlags;
2use crate::{
3 id::{Id, marker::AttachmentMarker},
4 util::is_false,
5};
6use serde::{Deserialize, Serialize};
7
8#[derive(Clone, Debug, Deserialize, PartialEq, Serialize)]
9pub struct Attachment {
10 pub content_type: Option<String>,
14 #[serde(default, skip_serializing_if = "is_false")]
20 pub ephemeral: bool,
21 #[serde(skip_serializing_if = "Option::is_none")]
23 pub duration_secs: Option<f64>,
24 pub filename: String,
25 #[serde(skip_serializing_if = "Option::is_none")]
27 pub flags: Option<AttachmentFlags>,
28 #[serde(skip_serializing_if = "Option::is_none")]
29 pub description: Option<String>,
30 #[serde(skip_serializing_if = "Option::is_none")]
31 pub height: Option<u64>,
32 pub id: Id<AttachmentMarker>,
33 #[serde(skip_serializing_if = "Option::is_none")]
36 pub placeholder: Option<String>,
37 #[serde(skip_serializing_if = "Option::is_none")]
39 pub placeholder_version: Option<u64>,
40 pub proxy_url: String,
41 pub size: u64,
42 #[serde(skip_serializing_if = "Option::is_none")]
44 pub title: Option<String>,
45 pub url: String,
46 #[serde(skip_serializing_if = "Option::is_none")]
48 pub waveform: Option<String>,
49 #[serde(skip_serializing_if = "Option::is_none")]
50 pub width: Option<u64>,
51}
52
53#[cfg(test)]
54mod tests {
55 use super::Attachment;
56 use crate::{channel::AttachmentFlags, id::Id};
57 use serde::{Deserialize, Serialize};
58 use serde_test::Token;
59 use static_assertions::{assert_fields, assert_impl_all};
60 use std::fmt::Debug;
61
62 assert_fields!(
63 Attachment: content_type,
64 ephemeral,
65 filename,
66 height,
67 id,
68 proxy_url,
69 size,
70 url,
71 width
72 );
73
74 assert_impl_all!(
75 Attachment: Clone,
76 Debug,
77 Deserialize<'static>,
78 PartialEq,
79 Serialize
80 );
81
82 #[test]
83 fn attachment() {
84 let value = Attachment {
85 content_type: Some("image/png".to_owned()),
86 ephemeral: false,
87 filename: "a.png".to_owned(),
88 flags: Some(AttachmentFlags::IS_SPOILER),
89 description: Some("a image".to_owned()),
90 duration_secs: Some(3.2),
91 height: Some(184),
92 id: Id::new(700_000_000_000_000_000),
93 placeholder: Some("zSeKDQIoCLiHeIKeiLyfrsBqCIaYaHJ2Vg".to_owned()),
95 placeholder_version: Some(1),
96 proxy_url: "https://cdn.example.com/1.png".to_owned(),
97 size: 13_593,
98 title: Some("a title".to_owned()),
99 url: "https://example.com/1.png".to_owned(),
100 waveform: Some(String::from("waveform")),
101 width: Some(184),
102 };
103
104 serde_test::assert_tokens(
105 &value,
106 &[
107 Token::Struct {
108 name: "Attachment",
109 len: 15,
110 },
111 Token::Str("content_type"),
112 Token::Some,
113 Token::Str("image/png"),
114 Token::Str("duration_secs"),
115 Token::Some,
116 Token::F64(3.2),
117 Token::Str("filename"),
118 Token::Str("a.png"),
119 Token::Str("flags"),
120 Token::Some,
121 Token::U64(8),
122 Token::Str("description"),
123 Token::Some,
124 Token::Str("a image"),
125 Token::Str("height"),
126 Token::Some,
127 Token::U64(184),
128 Token::Str("id"),
129 Token::NewtypeStruct { name: "Id" },
130 Token::Str("700000000000000000"),
131 Token::Str("placeholder"),
132 Token::Some,
133 Token::Str("zSeKDQIoCLiHeIKeiLyfrsBqCIaYaHJ2Vg"),
134 Token::Str("placeholder_version"),
135 Token::Some,
136 Token::U64(1),
137 Token::Str("proxy_url"),
138 Token::Str("https://cdn.example.com/1.png"),
139 Token::Str("size"),
140 Token::U64(13_593),
141 Token::Str("title"),
142 Token::Some,
143 Token::Str("a title"),
144 Token::Str("url"),
145 Token::Str("https://example.com/1.png"),
146 Token::Str("waveform"),
147 Token::Some,
148 Token::Str("waveform"),
149 Token::Str("width"),
150 Token::Some,
151 Token::U64(184),
152 Token::StructEnd,
153 ],
154 );
155 }
156}