1use serde::{
4 Serialize,
5 ser::{SerializeMap, Serializer},
6};
7
8use super::Block;
9use super::anchor::Anchor;
10use super::inlines::{CalloutRef, InlineNode};
11use super::location::Location;
12use super::metadata::BlockMetadata;
13use super::title::Title;
14
15pub type ListLevel = u8;
16
17#[derive(Clone, Debug, PartialEq)]
19#[non_exhaustive]
20pub enum ListItemCheckedStatus {
21 Checked,
22 Unchecked,
23}
24
25#[derive(Clone, Debug, PartialEq)]
32#[non_exhaustive]
33pub struct ListItem<'a> {
34 pub level: ListLevel,
35 pub marker: &'a str,
36 pub checked: Option<ListItemCheckedStatus>,
37 pub principal: Vec<InlineNode<'a>>,
39 pub blocks: Vec<Block<'a>>,
41 pub location: Location,
42}
43
44#[derive(Clone, Debug, PartialEq)]
46#[non_exhaustive]
47pub struct DescriptionList<'a> {
48 pub title: Title<'a>,
49 pub metadata: BlockMetadata<'a>,
50 pub items: Vec<DescriptionListItem<'a>>,
51 pub location: Location,
52}
53
54#[derive(Clone, Debug, PartialEq, Serialize)]
76#[non_exhaustive]
77pub struct DescriptionListItem<'a> {
78 #[serde(default, skip_serializing_if = "Vec::is_empty")]
80 pub anchors: Vec<Anchor<'a>>,
81 #[serde(default, skip_serializing_if = "Vec::is_empty")]
83 pub term: Vec<InlineNode<'a>>,
84 pub delimiter: &'a str,
86 #[serde(skip)]
88 pub delimiter_location: Option<Location>,
89 #[serde(default, skip_serializing_if = "Vec::is_empty")]
91 pub principal_text: Vec<InlineNode<'a>>,
92 pub description: Vec<Block<'a>>,
94 pub location: Location,
95}
96
97#[derive(Clone, Debug, PartialEq)]
99#[non_exhaustive]
100pub struct UnorderedList<'a> {
101 pub title: Title<'a>,
102 pub metadata: BlockMetadata<'a>,
103 pub items: Vec<ListItem<'a>>,
104 pub marker: &'a str,
105 pub location: Location,
106}
107
108#[derive(Clone, Debug, PartialEq)]
110#[non_exhaustive]
111pub struct OrderedList<'a> {
112 pub title: Title<'a>,
113 pub metadata: BlockMetadata<'a>,
114 pub items: Vec<ListItem<'a>>,
115 pub marker: &'a str,
116 pub location: Location,
117}
118
119#[derive(Clone, Debug, PartialEq)]
123#[non_exhaustive]
124pub struct CalloutList<'a> {
125 pub title: Title<'a>,
126 pub metadata: BlockMetadata<'a>,
127 pub items: Vec<CalloutListItem<'a>>,
128 pub location: Location,
129}
130
131#[derive(Clone, Debug, PartialEq)]
143#[non_exhaustive]
144pub struct CalloutListItem<'a> {
145 pub callout: CalloutRef,
147 pub principal: Vec<InlineNode<'a>>,
149 pub blocks: Vec<Block<'a>>,
151 pub location: Location,
153}
154
155impl Serialize for UnorderedList<'_> {
160 fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
161 where
162 S: Serializer,
163 {
164 let mut state = serializer.serialize_map(None)?;
165 state.serialize_entry("name", "list")?;
166 state.serialize_entry("type", "block")?;
167 state.serialize_entry("variant", "unordered")?;
168 state.serialize_entry("marker", &self.marker)?;
169 if !self.title.is_empty() {
170 state.serialize_entry("title", &self.title)?;
171 }
172 if !self.metadata.is_default() {
173 state.serialize_entry("metadata", &self.metadata)?;
174 }
175 state.serialize_entry("items", &self.items)?;
176 state.serialize_entry("location", &self.location)?;
177 state.end()
178 }
179}
180
181impl Serialize for OrderedList<'_> {
182 fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
183 where
184 S: Serializer,
185 {
186 let mut state = serializer.serialize_map(None)?;
187 state.serialize_entry("name", "list")?;
188 state.serialize_entry("type", "block")?;
189 state.serialize_entry("variant", "ordered")?;
190 state.serialize_entry("marker", &self.marker)?;
191 if !self.title.is_empty() {
192 state.serialize_entry("title", &self.title)?;
193 }
194 if !self.metadata.is_default() {
195 state.serialize_entry("metadata", &self.metadata)?;
196 }
197 state.serialize_entry("items", &self.items)?;
198 state.serialize_entry("location", &self.location)?;
199 state.end()
200 }
201}
202
203impl Serialize for CalloutList<'_> {
204 fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
205 where
206 S: Serializer,
207 {
208 let mut state = serializer.serialize_map(None)?;
209 state.serialize_entry("name", "list")?;
210 state.serialize_entry("type", "block")?;
211 state.serialize_entry("variant", "callout")?;
212 if !self.title.is_empty() {
213 state.serialize_entry("title", &self.title)?;
214 }
215 if !self.metadata.is_default() {
216 state.serialize_entry("metadata", &self.metadata)?;
217 }
218 state.serialize_entry("items", &self.items)?;
219 state.serialize_entry("location", &self.location)?;
220 state.end()
221 }
222}
223
224impl Serialize for DescriptionList<'_> {
225 fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
226 where
227 S: Serializer,
228 {
229 let mut state = serializer.serialize_map(None)?;
230 state.serialize_entry("name", "dlist")?;
231 state.serialize_entry("type", "block")?;
232 if !self.title.is_empty() {
233 state.serialize_entry("title", &self.title)?;
234 }
235 if !self.metadata.is_default() {
236 state.serialize_entry("metadata", &self.metadata)?;
237 }
238 state.serialize_entry("items", &self.items)?;
239 state.serialize_entry("location", &self.location)?;
240 state.end()
241 }
242}
243
244impl Serialize for ListItem<'_> {
245 fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
246 where
247 S: Serializer,
248 {
249 let mut state = serializer.serialize_map(None)?;
250 state.serialize_entry("name", "listItem")?;
251 state.serialize_entry("type", "block")?;
252 state.serialize_entry("marker", &self.marker)?;
253 if let Some(checked) = &self.checked {
254 state.serialize_entry("checked", checked)?;
255 }
256 state.serialize_entry("principal", &self.principal)?;
263 if !self.blocks.is_empty() {
264 state.serialize_entry("blocks", &self.blocks)?;
265 }
266 state.serialize_entry("location", &self.location)?;
267 state.end()
268 }
269}
270
271impl Serialize for ListItemCheckedStatus {
272 fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
273 where
274 S: Serializer,
275 {
276 match &self {
277 ListItemCheckedStatus::Checked => serializer.serialize_bool(true),
278 ListItemCheckedStatus::Unchecked => serializer.serialize_bool(false),
279 }
280 }
281}
282
283impl Serialize for CalloutListItem<'_> {
284 fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
285 where
286 S: Serializer,
287 {
288 let mut state = serializer.serialize_map(None)?;
289 state.serialize_entry("name", "listItem")?;
290 state.serialize_entry("type", "block")?;
291 state.serialize_entry("callout", &self.callout)?;
292 state.serialize_entry("principal", &self.principal)?;
293 if !self.blocks.is_empty() {
294 state.serialize_entry("blocks", &self.blocks)?;
295 }
296 state.serialize_entry("location", &self.location)?;
297 state.end()
298 }
299}