1#[cfg(feature = "serde")]
18use serde::{Deserialize, Serialize};
19
20#[derive(Debug, Clone)]
25#[cfg_attr(feature = "async-graphql", derive(async_graphql::SimpleObject))]
26pub struct EventType {
27 pub group: String,
30
31 pub name: String,
33
34 pub version: String,
36}
37
38#[cfg(feature = "serde")]
39impl Serialize for EventType {
40 fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
41 where
42 S: serde::Serializer,
43 {
44 let event_type = self.to_string();
45 serializer.serialize_str(&event_type)
46 }
47}
48
49#[cfg(feature = "serde")]
50impl<'de> Deserialize<'de> for EventType {
51 fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
52 where
53 D: serde::Deserializer<'de>,
54 {
55 let s = String::deserialize(deserializer)?;
56 let parts = s.split('/').collect::<Vec<&str>>();
57
58 if parts.len() != 3 {
59 return Err(serde::de::Error::custom(format!(
60 "invalid event type: {}",
61 s
62 )));
63 }
64
65 Ok(Self {
66 group: parts[0].to_string(),
67 name: parts[1].to_string(),
68 version: parts[2].to_string(),
69 })
70 }
71}
72
73impl std::str::FromStr for EventType {
74 type Err = String;
75
76 fn from_str(s: &str) -> Result<Self, Self::Err> {
77 let parts = s.split('/').collect::<Vec<&str>>();
78
79 if parts.len() != 3 {
80 return Err(format!("invalid event type: {}", s));
81 }
82
83 Ok(Self {
84 group: parts[0].to_string(),
85 name: parts[1].to_string(),
86 version: parts[2].to_string(),
87 })
88 }
89}
90
91impl std::fmt::Display for EventType {
92 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
93 write!(f, "{}/{}/{}", self.group, self.name, self.version)
94 }
95}
96
97pub fn timestamp_now() -> chrono::DateTime<chrono::Utc> {
100 chrono::Utc::now()
101}
102
103#[derive(Debug, Clone)]
104#[cfg_attr(feature = "serde", derive(Serialize, Deserialize))]
105#[cfg_attr(feature = "async-graphql", derive(async_graphql::SimpleObject))]
106pub struct Event {
107 #[cfg_attr(feature = "serde", serde(rename = "eventId"))]
108 pub event_id: String,
109
110 #[cfg_attr(feature = "serde", serde(rename = "objectId"))]
111 pub object_id: Option<String>,
112
113 #[cfg_attr(feature = "serde", serde(rename = "eventType"))]
114 pub event_type: EventType,
115
116 pub timestamp: chrono::DateTime<chrono::Utc>,
117
118 pub payload: std::collections::HashMap<String, String>,
119}
120
121#[cfg(test)]
122mod tests {
123 use super::*;
124
125 #[test]
126 fn test_event_type() {
127 let event_type = EventType {
128 group: "group".to_string(),
129 name: "name".to_string(),
130 version: "version".to_string(),
131 };
132
133 assert_eq!(event_type.group, "group");
134 assert_eq!(event_type.name, "name");
135 assert_eq!(event_type.version, "version");
136 }
137
138 #[test]
139 fn test_event() {
140 let event = Event {
141 event_id: "event_id".to_string(),
142 object_id: Some("object_id".to_string()),
143 event_type: EventType {
144 group: "group".to_string(),
145 name: "name".to_string(),
146 version: "version".to_string(),
147 },
148 timestamp: chrono::Utc::now(),
149 payload: std::collections::HashMap::new(),
150 };
151
152 assert_eq!(event.event_id, "event_id");
153 assert_eq!(event.object_id, Some("object_id".to_string()));
154 assert_eq!(event.event_type.group, "group");
155 assert_eq!(event.event_type.name, "name");
156 assert_eq!(event.event_type.version, "version");
157 }
158
159 #[test]
160 #[cfg(feature = "serde")]
161 fn test_serialization() {
162 let event = Event {
163 event_id: "event_id".to_string(),
164 object_id: Some("object_id".to_string()),
165 event_type: EventType {
166 group: "group".to_string(),
167 name: "name".to_string(),
168 version: "version".to_string(),
169 },
170 timestamp: chrono::Utc::now(),
171 payload: std::collections::HashMap::new(),
172 };
173
174 let serialized = serde_json::to_string(&event).unwrap();
175 let deserialized: Event = serde_json::from_str(&serialized).unwrap();
176
177 assert_eq!(event.event_id, deserialized.event_id);
178 assert_eq!(event.object_id, deserialized.object_id);
179 assert_eq!(event.event_type.group, deserialized.event_type.group);
180 assert_eq!(event.event_type.name, deserialized.event_type.name);
181 assert_eq!(event.event_type.version, deserialized.event_type.version);
182 }
183
184 #[test]
185 fn test_event_type_from_str() {
186 let event_type = "group/name/version".parse::<EventType>().unwrap();
187
188 assert_eq!(event_type.group, "group");
189 assert_eq!(event_type.name, "name");
190 assert_eq!(event_type.version, "version");
191 }
192
193 #[test]
194 fn test_event_type_from_str_invalid() {
195 let event_type = "group/name".parse::<EventType>();
196
197 assert!(event_type.is_err());
198 }
199}