1#[derive(Debug, Clone, PartialEq, Eq)]
5pub struct ParseEventHeaderError(pub String);
6
7impl std::fmt::Display for ParseEventHeaderError {
8 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
9 write!(f, "unknown event header: {}", self.0)
10 }
11}
12
13impl std::error::Error for ParseEventHeaderError {}
14
15sip_header::define_header_enum! {
16 error_type: ParseEventHeaderError,
17 pub enum EventHeader {
23 EventName => "Event-Name",
24 EventSubclass => "Event-Subclass",
25 UniqueId => "Unique-ID",
26 CallerUniqueId => "Caller-Unique-ID",
27 OtherLegUniqueId => "Other-Leg-Unique-ID",
28 ChannelCallUuid => "Channel-Call-UUID",
29 JobUuid => "Job-UUID",
30 ChannelName => "Channel-Name",
31 ChannelState => "Channel-State",
32 ChannelStateNumber => "Channel-State-Number",
33 ChannelCallState => "Channel-Call-State",
34 AnswerState => "Answer-State",
35 CallDirection => "Call-Direction",
36 HangupCause => "Hangup-Cause",
37 CallerCallerIdName => "Caller-Caller-ID-Name",
38 CallerCallerIdNumber => "Caller-Caller-ID-Number",
39 CallerOrigCallerIdName => "Caller-Orig-Caller-ID-Name",
40 CallerOrigCallerIdNumber => "Caller-Orig-Caller-ID-Number",
41 CallerCalleeIdName => "Caller-Callee-ID-Name",
42 CallerCalleeIdNumber => "Caller-Callee-ID-Number",
43 CallerDestinationNumber => "Caller-Destination-Number",
44 CallerContext => "Caller-Context",
45 CallerDirection => "Caller-Direction",
46 CallerNetworkAddr => "Caller-Network-Addr",
47 CoreUuid => "Core-UUID",
48 DtmfDigit => "DTMF-Digit",
49 Priority => "priority",
50 LogLevel => "Log-Level",
51 PlData => "pl_data",
53 SipEvent => "event",
55 SipContentType => "sip_content_type",
57 GatewayName => "gateway_name",
59
60 ChannelReadCodecName => "Channel-Read-Codec-Name",
63 ChannelReadCodecRate => "Channel-Read-Codec-Rate",
64 ChannelReadCodecBitRate => "Channel-Read-Codec-Bit-Rate",
65 ChannelReportedReadCodecRate => "Channel-Reported-Read-Codec-Rate",
67 ChannelWriteCodecName => "Channel-Write-Codec-Name",
69 ChannelWriteCodecRate => "Channel-Write-Codec-Rate",
70 ChannelWriteCodecBitRate => "Channel-Write-Codec-Bit-Rate",
71 ChannelReportedWriteCodecRate => "Channel-Reported-Write-Codec-Rate",
73 ChannelVideoReadCodecName => "Channel-Video-Read-Codec-Name",
75 ChannelVideoReadCodecRate => "Channel-Video-Read-Codec-Rate",
76 ChannelVideoWriteCodecName => "Channel-Video-Write-Codec-Name",
77 ChannelVideoWriteCodecRate => "Channel-Video-Write-Codec-Rate",
78 SessionCount => "Session-Count",
80 FreeswitchHostname => "FreeSWITCH-Hostname",
81 FreeswitchSwitchname => "FreeSWITCH-Switchname",
82 FreeswitchIpv4 => "FreeSWITCH-IPv4",
83 FreeswitchIpv6 => "FreeSWITCH-IPv6",
84 FreeswitchVersion => "FreeSWITCH-Version",
85 FreeswitchDomain => "FreeSWITCH-Domain",
86 FreeswitchUser => "FreeSWITCH-User",
87
88 Application => "Application",
90 ApplicationData => "Application-Data",
91 ApplicationResponse => "Application-Response",
92 ApplicationUuid => "Application-UUID",
93
94 EventDateLocal => "Event-Date-Local",
96 EventDateGmt => "Event-Date-GMT",
97 EventDateTimestamp => "Event-Date-Timestamp",
98 EventCallingFile => "Event-Calling-File",
99 EventCallingFunction => "Event-Calling-Function",
100 EventCallingLineNumber => "Event-Calling-Line-Number",
101 EventSequence => "Event-Sequence",
102
103 ChannelPresenceId => "Channel-Presence-ID",
105 ChannelPresenceData => "Channel-Presence-Data",
106 PresenceDataCols => "Presence-Data-Cols",
107 PresenceCallDirection => "Presence-Call-Direction",
108 ChannelHitDialplan => "Channel-HIT-Dialplan",
109 SessionExternalId => "Session-External-ID",
110 OtherType => "Other-Type",
112
113 ChannelCallStateNumber => "Channel-Call-State-Number",
115 OriginalChannelCallState => "Original-Channel-Call-State",
116
117 DtmfDuration => "DTMF-Duration",
119 DtmfSource => "DTMF-Source",
120
121 CallerLogicalDirection => "Caller-Logical-Direction",
123 CallerUsername => "Caller-Username",
124 CallerDialplan => "Caller-Dialplan",
125 CallerAni => "Caller-ANI",
126 CallerAniii => "Caller-ANI-II",
127 CallerSource => "Caller-Source",
128 CallerTransferSource => "Caller-Transfer-Source",
129 CallerRdnis => "Caller-RDNIS",
130 CallerChannelName => "Caller-Channel-Name",
131 CallerProfileIndex => "Caller-Profile-Index",
132 CallerScreenBit => "Caller-Screen-Bit",
133 CallerPrivacyHideName => "Caller-Privacy-Hide-Name",
134 CallerPrivacyHideNumber => "Caller-Privacy-Hide-Number",
135
136 OtherLegDirection => "Other-Leg-Direction",
138 OtherLegLogicalDirection => "Other-Leg-Logical-Direction",
139 OtherLegUsername => "Other-Leg-Username",
140 OtherLegDialplan => "Other-Leg-Dialplan",
141 OtherLegCallerIdName => "Other-Leg-Caller-ID-Name",
142 OtherLegCallerIdNumber => "Other-Leg-Caller-ID-Number",
143 OtherLegOrigCallerIdName => "Other-Leg-Orig-Caller-ID-Name",
144 OtherLegOrigCallerIdNumber => "Other-Leg-Orig-Caller-ID-Number",
145 OtherLegCalleeIdName => "Other-Leg-Callee-ID-Name",
146 OtherLegCalleeIdNumber => "Other-Leg-Callee-ID-Number",
147 OtherLegNetworkAddr => "Other-Leg-Network-Addr",
148 OtherLegAni => "Other-Leg-ANI",
149 OtherLegAniii => "Other-Leg-ANI-II",
150 OtherLegDestinationNumber => "Other-Leg-Destination-Number",
151 OtherLegSource => "Other-Leg-Source",
152 OtherLegTransferSource => "Other-Leg-Transfer-Source",
153 OtherLegContext => "Other-Leg-Context",
154 OtherLegRdnis => "Other-Leg-RDNIS",
155 OtherLegChannelName => "Other-Leg-Channel-Name",
156 OtherLegProfileIndex => "Other-Leg-Profile-Index",
157 OtherLegScreenBit => "Other-Leg-Screen-Bit",
158 OtherLegPrivacyHideName => "Other-Leg-Privacy-Hide-Name",
159 OtherLegPrivacyHideNumber => "Other-Leg-Privacy-Hide-Number",
160
161 UpTime => "Up-Time",
164 UptimeMsec => "Uptime-msec",
166 MaxSessions => "Max-Sessions",
167 SessionPeakMax => "Session-Peak-Max",
168 SessionPeakFiveMin => "Session-Peak-FiveMin",
169 SessionPerSec => "Session-Per-Sec",
170 SessionPerSecFiveMin => "Session-Per-Sec-FiveMin",
171 SessionPerSecMax => "Session-Per-Sec-Max",
172 SessionPerSecLast => "Session-Per-Sec-Last",
173 SessionSinceStartup => "Session-Since-Startup",
174 IdleCpu => "Idle-CPU",
175 HeartbeatInterval => "Heartbeat-Interval",
176 EventInfo => "Event-Info",
177
178 LogData => "Log-Data",
180 LogFile => "Log-File",
181 LogFunction => "Log-Function",
182 LogLine => "Log-Line",
183 UserData => "User-Data",
184
185 ApplicationUuidName => "Application-UUID-Name",
187 }
188}
189
190pub fn normalize_header_key(raw: &str) -> String {
207 if let Ok(eh) = raw.parse::<EventHeader>() {
208 return eh
209 .as_str()
210 .to_string();
211 }
212 if raw.contains('_') {
213 raw.to_string()
214 } else {
215 title_case_dashes(raw)
216 }
217}
218
219fn title_case_dashes(s: &str) -> String {
220 let mut result = String::with_capacity(s.len());
221 let mut capitalize_next = true;
222 for c in s.chars() {
223 if c == '-' {
224 result.push('-');
225 capitalize_next = true;
226 } else if capitalize_next {
227 result.push(c.to_ascii_uppercase());
228 capitalize_next = false;
229 } else {
230 result.push(c.to_ascii_lowercase());
231 }
232 }
233 result
234}
235
236#[cfg(test)]
237mod tests {
238 use super::*;
239
240 #[test]
241 fn display_round_trip() {
242 assert_eq!(EventHeader::UniqueId.to_string(), "Unique-ID");
243 assert_eq!(
244 EventHeader::ChannelCallState.to_string(),
245 "Channel-Call-State"
246 );
247 assert_eq!(
248 EventHeader::CallerCallerIdName.to_string(),
249 "Caller-Caller-ID-Name"
250 );
251 assert_eq!(EventHeader::Priority.to_string(), "priority");
252 }
253
254 #[test]
255 fn as_ref_str() {
256 let h: &str = EventHeader::UniqueId.as_ref();
257 assert_eq!(h, "Unique-ID");
258 }
259
260 #[test]
261 fn from_str_case_insensitive() {
262 assert_eq!(
263 "unique-id".parse::<EventHeader>(),
264 Ok(EventHeader::UniqueId)
265 );
266 assert_eq!(
267 "UNIQUE-ID".parse::<EventHeader>(),
268 Ok(EventHeader::UniqueId)
269 );
270 assert_eq!(
271 "Unique-ID".parse::<EventHeader>(),
272 Ok(EventHeader::UniqueId)
273 );
274 assert_eq!(
275 "channel-call-state".parse::<EventHeader>(),
276 Ok(EventHeader::ChannelCallState)
277 );
278 }
279
280 #[test]
281 fn from_str_unknown() {
282 let err = "X-Custom-Not-In-Enum".parse::<EventHeader>();
283 assert!(err.is_err());
284 assert_eq!(
285 err.unwrap_err()
286 .to_string(),
287 "unknown event header: X-Custom-Not-In-Enum"
288 );
289 }
290
291 #[test]
299 fn normalize_known_enum_variants_return_canonical_form() {
300 assert_eq!(normalize_header_key("unique-id"), "Unique-ID");
302 assert_eq!(normalize_header_key("UNIQUE-ID"), "Unique-ID");
303 assert_eq!(normalize_header_key("Unique-ID"), "Unique-ID");
304 assert_eq!(normalize_header_key("dtmf-digit"), "DTMF-Digit");
305 assert_eq!(normalize_header_key("DTMF-DIGIT"), "DTMF-Digit");
306 assert_eq!(
307 normalize_header_key("channel-call-uuid"),
308 "Channel-Call-UUID"
309 );
310 assert_eq!(normalize_header_key("event-name"), "Event-Name");
311 }
312
313 #[test]
314 fn normalize_known_underscore_variants_return_canonical_form() {
315 assert_eq!(normalize_header_key("priority"), "priority");
317 assert_eq!(normalize_header_key("PRIORITY"), "priority");
318 assert_eq!(normalize_header_key("pl_data"), "pl_data");
319 assert_eq!(normalize_header_key("PL_DATA"), "pl_data");
320 assert_eq!(normalize_header_key("sip_content_type"), "sip_content_type");
321 assert_eq!(normalize_header_key("gateway_name"), "gateway_name");
322 assert_eq!(normalize_header_key("event"), "event");
323 assert_eq!(normalize_header_key("EVENT"), "event");
324 }
325
326 #[test]
327 fn normalize_codec_headers_from_switch_core_codec() {
328 assert_eq!(
331 normalize_header_key("channel-read-codec-bit-rate"),
332 "Channel-Read-Codec-Bit-Rate"
333 );
334 assert_eq!(
335 normalize_header_key("Channel-Read-Codec-Bit-Rate"),
336 "Channel-Read-Codec-Bit-Rate"
337 );
338 assert_eq!(
340 normalize_header_key("Channel-Write-codec-bit-rate"),
341 "Channel-Write-Codec-Bit-Rate"
342 );
343 assert_eq!(
344 normalize_header_key("channel-video-read-codec-name"),
345 "Channel-Video-Read-Codec-Name"
346 );
347 }
348
349 #[test]
350 fn normalize_unknown_underscore_keys_passthrough() {
351 assert_eq!(
353 normalize_header_key("variable_sip_call_id"),
354 "variable_sip_call_id"
355 );
356 assert_eq!(
357 normalize_header_key("variable_sip_h_X-My-CUSTOM-Header"),
358 "variable_sip_h_X-My-CUSTOM-Header"
359 );
360 assert_eq!(
361 normalize_header_key("variable_sip_h_Diversion"),
362 "variable_sip_h_Diversion"
363 );
364 }
365
366 #[test]
367 fn normalize_unknown_dash_keys_title_case() {
368 assert_eq!(normalize_header_key("content-type"), "Content-Type");
370 assert_eq!(normalize_header_key("Content-Type"), "Content-Type");
371 assert_eq!(normalize_header_key("CONTENT-TYPE"), "Content-Type");
372 assert_eq!(normalize_header_key("x-custom-header"), "X-Custom-Header");
373 assert_eq!(
374 normalize_header_key("Content-Disposition"),
375 "Content-Disposition"
376 );
377 assert_eq!(normalize_header_key("reply-text"), "Reply-Text");
378 }
379
380 #[test]
381 fn normalize_idempotent_for_all_enum_variants() {
382 let variants = [
384 EventHeader::EventName,
385 EventHeader::UniqueId,
386 EventHeader::ChannelCallUuid,
387 EventHeader::DtmfDigit,
388 EventHeader::Priority,
389 EventHeader::PlData,
390 EventHeader::SipEvent,
391 EventHeader::GatewayName,
392 EventHeader::SipContentType,
393 EventHeader::ChannelReadCodecBitRate,
394 EventHeader::ChannelVideoWriteCodecRate,
395 EventHeader::LogLevel,
396 ];
397 for v in variants {
398 let canonical = v.as_str();
399 assert_eq!(
400 normalize_header_key(canonical),
401 canonical,
402 "normalization not idempotent for {canonical}"
403 );
404 }
405 }
406
407 #[test]
408 fn parse_missing_event_default_headers() {
409 assert!("Event-Date-Local"
411 .parse::<EventHeader>()
412 .is_ok());
413 assert!("Event-Date-GMT"
414 .parse::<EventHeader>()
415 .is_ok());
416 assert!("Event-Date-Timestamp"
417 .parse::<EventHeader>()
418 .is_ok());
419 assert!("Event-Calling-File"
420 .parse::<EventHeader>()
421 .is_ok());
422 assert!("Event-Calling-Function"
423 .parse::<EventHeader>()
424 .is_ok());
425 assert!("Event-Calling-Line-Number"
426 .parse::<EventHeader>()
427 .is_ok());
428 assert!("Event-Sequence"
429 .parse::<EventHeader>()
430 .is_ok());
431 }
432
433 #[test]
434 fn parse_missing_channel_basic_data_headers() {
435 assert!("Channel-Presence-ID"
437 .parse::<EventHeader>()
438 .is_ok());
439 assert!("Channel-Presence-Data"
440 .parse::<EventHeader>()
441 .is_ok());
442 assert!("Presence-Data-Cols"
443 .parse::<EventHeader>()
444 .is_ok());
445 assert!("Presence-Call-Direction"
446 .parse::<EventHeader>()
447 .is_ok());
448 assert!("Channel-HIT-Dialplan"
449 .parse::<EventHeader>()
450 .is_ok());
451 assert!("Session-External-ID"
452 .parse::<EventHeader>()
453 .is_ok());
454 assert!("Other-Type"
455 .parse::<EventHeader>()
456 .is_ok());
457 }
458
459 #[test]
460 fn parse_missing_callstate_and_dtmf_headers() {
461 assert!("Channel-Call-State-Number"
463 .parse::<EventHeader>()
464 .is_ok());
465 assert!("Original-Channel-Call-State"
466 .parse::<EventHeader>()
467 .is_ok());
468 assert!("DTMF-Duration"
470 .parse::<EventHeader>()
471 .is_ok());
472 assert!("DTMF-Source"
473 .parse::<EventHeader>()
474 .is_ok());
475 }
476
477 #[test]
478 fn parse_missing_caller_profile_headers() {
479 assert!("Caller-Logical-Direction"
481 .parse::<EventHeader>()
482 .is_ok());
483 assert!("Caller-Username"
484 .parse::<EventHeader>()
485 .is_ok());
486 assert!("Caller-Dialplan"
487 .parse::<EventHeader>()
488 .is_ok());
489 assert!("Caller-ANI"
490 .parse::<EventHeader>()
491 .is_ok());
492 assert!("Caller-ANI-II"
493 .parse::<EventHeader>()
494 .is_ok());
495 assert!("Caller-Source"
496 .parse::<EventHeader>()
497 .is_ok());
498 assert!("Caller-Transfer-Source"
499 .parse::<EventHeader>()
500 .is_ok());
501 assert!("Caller-RDNIS"
502 .parse::<EventHeader>()
503 .is_ok());
504 assert!("Caller-Channel-Name"
505 .parse::<EventHeader>()
506 .is_ok());
507 assert!("Caller-Profile-Index"
508 .parse::<EventHeader>()
509 .is_ok());
510 assert!("Caller-Screen-Bit"
511 .parse::<EventHeader>()
512 .is_ok());
513 assert!("Caller-Privacy-Hide-Name"
514 .parse::<EventHeader>()
515 .is_ok());
516 assert!("Caller-Privacy-Hide-Number"
517 .parse::<EventHeader>()
518 .is_ok());
519 }
520
521 #[test]
522 fn parse_heartbeat_headers() {
523 assert!("Up-Time"
524 .parse::<EventHeader>()
525 .is_ok());
526 assert!("Uptime-msec"
527 .parse::<EventHeader>()
528 .is_ok());
529 assert!("Max-Sessions"
530 .parse::<EventHeader>()
531 .is_ok());
532 assert!("Session-Peak-Max"
533 .parse::<EventHeader>()
534 .is_ok());
535 assert!("Session-Peak-FiveMin"
536 .parse::<EventHeader>()
537 .is_ok());
538 assert!("Session-Per-Sec"
539 .parse::<EventHeader>()
540 .is_ok());
541 assert!("Session-Per-Sec-FiveMin"
542 .parse::<EventHeader>()
543 .is_ok());
544 assert!("Session-Per-Sec-Max"
545 .parse::<EventHeader>()
546 .is_ok());
547 assert!("Session-Per-Sec-Last"
548 .parse::<EventHeader>()
549 .is_ok());
550 assert!("Session-Since-Startup"
551 .parse::<EventHeader>()
552 .is_ok());
553 assert!("Idle-CPU"
554 .parse::<EventHeader>()
555 .is_ok());
556 assert!("Heartbeat-Interval"
557 .parse::<EventHeader>()
558 .is_ok());
559 assert!("Event-Info"
560 .parse::<EventHeader>()
561 .is_ok());
562 }
563
564 #[test]
565 fn parse_log_headers() {
566 assert!("Log-Data"
567 .parse::<EventHeader>()
568 .is_ok());
569 assert!("Log-File"
570 .parse::<EventHeader>()
571 .is_ok());
572 assert!("Log-Function"
573 .parse::<EventHeader>()
574 .is_ok());
575 assert!("Log-Line"
576 .parse::<EventHeader>()
577 .is_ok());
578 assert!("User-Data"
579 .parse::<EventHeader>()
580 .is_ok());
581 }
582
583 #[test]
584 fn parse_application_uuid_name() {
585 assert!("Application-UUID-Name"
586 .parse::<EventHeader>()
587 .is_ok());
588 }
589
590 #[test]
591 fn parse_missing_other_leg_headers() {
592 assert!("Other-Leg-Direction"
594 .parse::<EventHeader>()
595 .is_ok());
596 assert!("Other-Leg-Logical-Direction"
597 .parse::<EventHeader>()
598 .is_ok());
599 assert!("Other-Leg-Username"
600 .parse::<EventHeader>()
601 .is_ok());
602 assert!("Other-Leg-Dialplan"
603 .parse::<EventHeader>()
604 .is_ok());
605 assert!("Other-Leg-Caller-ID-Name"
606 .parse::<EventHeader>()
607 .is_ok());
608 assert!("Other-Leg-Caller-ID-Number"
609 .parse::<EventHeader>()
610 .is_ok());
611 assert!("Other-Leg-Orig-Caller-ID-Name"
612 .parse::<EventHeader>()
613 .is_ok());
614 assert!("Other-Leg-Orig-Caller-ID-Number"
615 .parse::<EventHeader>()
616 .is_ok());
617 assert!("Other-Leg-Callee-ID-Name"
618 .parse::<EventHeader>()
619 .is_ok());
620 assert!("Other-Leg-Callee-ID-Number"
621 .parse::<EventHeader>()
622 .is_ok());
623 assert!("Other-Leg-Network-Addr"
624 .parse::<EventHeader>()
625 .is_ok());
626 assert!("Other-Leg-ANI"
627 .parse::<EventHeader>()
628 .is_ok());
629 assert!("Other-Leg-ANI-II"
630 .parse::<EventHeader>()
631 .is_ok());
632 assert!("Other-Leg-Destination-Number"
633 .parse::<EventHeader>()
634 .is_ok());
635 assert!("Other-Leg-Source"
636 .parse::<EventHeader>()
637 .is_ok());
638 assert!("Other-Leg-Transfer-Source"
639 .parse::<EventHeader>()
640 .is_ok());
641 assert!("Other-Leg-Context"
642 .parse::<EventHeader>()
643 .is_ok());
644 assert!("Other-Leg-RDNIS"
645 .parse::<EventHeader>()
646 .is_ok());
647 assert!("Other-Leg-Channel-Name"
648 .parse::<EventHeader>()
649 .is_ok());
650 assert!("Other-Leg-Profile-Index"
651 .parse::<EventHeader>()
652 .is_ok());
653 assert!("Other-Leg-Screen-Bit"
654 .parse::<EventHeader>()
655 .is_ok());
656 assert!("Other-Leg-Privacy-Hide-Name"
657 .parse::<EventHeader>()
658 .is_ok());
659 assert!("Other-Leg-Privacy-Hide-Number"
660 .parse::<EventHeader>()
661 .is_ok());
662 }
663
664 #[test]
665 fn from_str_round_trip_all_variants() {
666 let variants = [
667 EventHeader::EventName,
668 EventHeader::EventSubclass,
669 EventHeader::UniqueId,
670 EventHeader::CallerUniqueId,
671 EventHeader::OtherLegUniqueId,
672 EventHeader::ChannelCallUuid,
673 EventHeader::JobUuid,
674 EventHeader::ChannelName,
675 EventHeader::ChannelState,
676 EventHeader::ChannelStateNumber,
677 EventHeader::ChannelCallState,
678 EventHeader::AnswerState,
679 EventHeader::CallDirection,
680 EventHeader::HangupCause,
681 EventHeader::CallerCallerIdName,
682 EventHeader::CallerCallerIdNumber,
683 EventHeader::CallerOrigCallerIdName,
684 EventHeader::CallerOrigCallerIdNumber,
685 EventHeader::CallerCalleeIdName,
686 EventHeader::CallerCalleeIdNumber,
687 EventHeader::CallerDestinationNumber,
688 EventHeader::CallerContext,
689 EventHeader::CallerDirection,
690 EventHeader::CallerNetworkAddr,
691 EventHeader::CoreUuid,
692 EventHeader::DtmfDigit,
693 EventHeader::Priority,
694 EventHeader::LogLevel,
695 EventHeader::PlData,
696 EventHeader::SipEvent,
697 EventHeader::SipContentType,
698 EventHeader::GatewayName,
699 EventHeader::ChannelReadCodecName,
700 EventHeader::ChannelReadCodecRate,
701 EventHeader::ChannelReadCodecBitRate,
702 EventHeader::ChannelReportedReadCodecRate,
703 EventHeader::ChannelWriteCodecName,
704 EventHeader::ChannelWriteCodecRate,
705 EventHeader::ChannelWriteCodecBitRate,
706 EventHeader::ChannelReportedWriteCodecRate,
707 EventHeader::ChannelVideoReadCodecName,
708 EventHeader::ChannelVideoReadCodecRate,
709 EventHeader::ChannelVideoWriteCodecName,
710 EventHeader::ChannelVideoWriteCodecRate,
711 EventHeader::Application,
712 EventHeader::ApplicationData,
713 EventHeader::ApplicationResponse,
714 EventHeader::ApplicationUuid,
715 EventHeader::EventDateLocal,
716 EventHeader::EventDateGmt,
717 EventHeader::EventDateTimestamp,
718 EventHeader::EventCallingFile,
719 EventHeader::EventCallingFunction,
720 EventHeader::EventCallingLineNumber,
721 EventHeader::EventSequence,
722 EventHeader::ChannelPresenceId,
723 EventHeader::ChannelPresenceData,
724 EventHeader::PresenceDataCols,
725 EventHeader::PresenceCallDirection,
726 EventHeader::ChannelHitDialplan,
727 EventHeader::SessionExternalId,
728 EventHeader::OtherType,
729 EventHeader::ChannelCallStateNumber,
730 EventHeader::OriginalChannelCallState,
731 EventHeader::DtmfDuration,
732 EventHeader::DtmfSource,
733 EventHeader::CallerLogicalDirection,
734 EventHeader::CallerUsername,
735 EventHeader::CallerDialplan,
736 EventHeader::CallerAni,
737 EventHeader::CallerAniii,
738 EventHeader::CallerSource,
739 EventHeader::CallerTransferSource,
740 EventHeader::CallerRdnis,
741 EventHeader::CallerChannelName,
742 EventHeader::CallerProfileIndex,
743 EventHeader::CallerScreenBit,
744 EventHeader::CallerPrivacyHideName,
745 EventHeader::CallerPrivacyHideNumber,
746 EventHeader::OtherLegDirection,
747 EventHeader::OtherLegLogicalDirection,
748 EventHeader::OtherLegUsername,
749 EventHeader::OtherLegDialplan,
750 EventHeader::OtherLegCallerIdName,
751 EventHeader::OtherLegCallerIdNumber,
752 EventHeader::OtherLegOrigCallerIdName,
753 EventHeader::OtherLegOrigCallerIdNumber,
754 EventHeader::OtherLegCalleeIdName,
755 EventHeader::OtherLegCalleeIdNumber,
756 EventHeader::OtherLegNetworkAddr,
757 EventHeader::OtherLegAni,
758 EventHeader::OtherLegAniii,
759 EventHeader::OtherLegDestinationNumber,
760 EventHeader::OtherLegSource,
761 EventHeader::OtherLegTransferSource,
762 EventHeader::OtherLegContext,
763 EventHeader::OtherLegRdnis,
764 EventHeader::OtherLegChannelName,
765 EventHeader::OtherLegProfileIndex,
766 EventHeader::OtherLegScreenBit,
767 EventHeader::OtherLegPrivacyHideName,
768 EventHeader::OtherLegPrivacyHideNumber,
769 EventHeader::UpTime,
770 EventHeader::UptimeMsec,
771 EventHeader::MaxSessions,
772 EventHeader::SessionPeakMax,
773 EventHeader::SessionPeakFiveMin,
774 EventHeader::SessionPerSec,
775 EventHeader::SessionPerSecFiveMin,
776 EventHeader::SessionPerSecMax,
777 EventHeader::SessionPerSecLast,
778 EventHeader::SessionSinceStartup,
779 EventHeader::IdleCpu,
780 EventHeader::HeartbeatInterval,
781 EventHeader::EventInfo,
782 EventHeader::LogData,
783 EventHeader::LogFile,
784 EventHeader::LogFunction,
785 EventHeader::LogLine,
786 EventHeader::UserData,
787 EventHeader::ApplicationUuidName,
788 ];
789 for v in variants {
790 let wire = v.to_string();
791 let parsed: EventHeader = wire
792 .parse()
793 .unwrap();
794 assert_eq!(parsed, v, "round-trip failed for {wire}");
795 }
796 }
797}