typesafe_rs/types/
entry.rs1use std::borrow::Cow;
2
3use serde::{Deserialize, Serialize};
4
5#[derive(Clone, Debug, Default, PartialEq, Serialize, Deserialize)]
9#[serde(untagged)]
10pub enum Entry {
11 Text(Cow<'static, str>),
13 #[default]
15 Null,
16 Json(serde_json::Value),
18}
19
20impl From<&'static str> for Entry {
21 fn from(value: &'static str) -> Self {
22 Self::Text(Cow::Borrowed(value))
23 }
24}
25
26impl From<String> for Entry {
27 fn from(value: String) -> Self {
28 Self::Text(Cow::Owned(value))
29 }
30}
31
32impl From<&String> for Entry {
33 fn from(value: &String) -> Self {
34 Self::Text(Cow::Owned(value.clone()))
35 }
36}
37
38impl From<serde_json::Value> for Entry {
39 fn from(value: serde_json::Value) -> Self {
40 match value {
41 serde_json::Value::Null => Self::Null,
42 serde_json::Value::String(s) => Self::Text(Cow::Owned(s)),
43 other => Self::Json(other),
44 }
45 }
46}
47
48impl From<Option<String>> for Entry {
49 fn from(value: Option<String>) -> Self {
50 match value {
51 Some(s) => Self::from(s),
52 None => Self::Null,
53 }
54 }
55}
56
57#[cfg(test)]
58mod tests {
59 use super::*;
60 use serde_json::json;
61
62 #[test]
63 fn text_roundtrip() {
64 let entry = Entry::from("hello");
65 let value = serde_json::to_value(&entry).unwrap();
66 assert_eq!(value, json!("hello"));
67 let back: Entry = serde_json::from_value(value).unwrap();
68 assert_eq!(back, Entry::from("hello"));
69 }
70
71 #[test]
72 fn null_roundtrip() {
73 let value = serde_json::to_value(Entry::Null).unwrap();
74 assert_eq!(value, json!(null));
75 let back: Entry = serde_json::from_value(json!(null)).unwrap();
76 assert_eq!(back, Entry::Null);
77 }
78
79 #[test]
80 fn object_roundtrip() {
81 let entry = Entry::from(json!({"question": "urgent?"}));
82 let value = serde_json::to_value(&entry).unwrap();
83 assert_eq!(value, json!({"question": "urgent?"}));
84 }
85
86 #[test]
87 fn array_roundtrip() {
88 let entry = Entry::from(json!(["a", "b"]));
89 let value = serde_json::to_value(&entry).unwrap();
90 assert_eq!(value, json!(["a", "b"]));
91 }
92
93 #[test]
94 fn from_value_null_is_null_variant() {
95 assert_eq!(Entry::from(serde_json::Value::Null), Entry::Null);
96 }
97}