rama_http/layer/dns/dns_resolve/
mod.rs1use crate::HeaderValue;
9use rama_core::error::{ErrorExt, OpaqueError};
10use rama_core::username::{ComposeError, Composer, UsernameLabelWriter};
11use rama_utils::macros::match_ignore_ascii_case_str;
12use std::fmt;
13
14mod service;
15#[doc(inline)]
16pub use service::DnsResolveModeService;
17
18mod layer;
19#[doc(inline)]
20pub use layer::DnsResolveModeLayer;
21
22mod username_parser;
23#[doc(inline)]
24pub use username_parser::DnsResolveModeUsernameParser;
25
26#[derive(Debug, Clone, Default, Copy, PartialEq, Eq, PartialOrd, Ord, Hash)]
27pub struct DnsResolveMode(ResolveMode);
31
32impl fmt::Display for DnsResolveMode {
33 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
34 match self.0 {
35 ResolveMode::Eager => write!(f, "eager"),
36 ResolveMode::Lazy => write!(f, "lazy"),
37 }
38 }
39}
40
41impl DnsResolveMode {
42 pub const fn eager() -> Self {
44 Self(ResolveMode::Eager)
45 }
46
47 pub const fn lazy() -> Self {
49 Self(ResolveMode::Lazy)
50 }
51
52 pub fn is_eager(&self) -> bool {
54 match self.0 {
55 ResolveMode::Eager => true,
56 ResolveMode::Lazy => false,
57 }
58 }
59
60 pub fn is_lazy(&self) -> bool {
62 match self.0 {
63 ResolveMode::Eager => false,
64 ResolveMode::Lazy => true,
65 }
66 }
67}
68
69impl std::str::FromStr for DnsResolveMode {
70 type Err = OpaqueError;
71
72 fn from_str(value: &str) -> Result<Self, Self::Err> {
73 Self::try_from(value)
74 }
75}
76
77impl TryFrom<&str> for DnsResolveMode {
78 type Error = OpaqueError;
79
80 fn try_from(value: &str) -> Result<Self, Self::Error> {
81 match_ignore_ascii_case_str! {
82 match (value) {
83 "eager" => Ok(DnsResolveMode::eager()),
84 "lazy" => Ok(DnsResolveMode::lazy()),
85 _ => Err(OpaqueError::from_display("Invalid DNS resolve mode: unknown str")),
86 }
87 }
88 }
89}
90
91impl TryFrom<&HeaderValue> for DnsResolveMode {
92 type Error = OpaqueError;
93
94 fn try_from(value: &HeaderValue) -> Result<Self, Self::Error> {
95 match value.to_str() {
96 Ok(value) => Self::try_from(value),
97 Err(err) => Err(err.context("Invalid DNS resolve mode")),
98 }
99 }
100}
101
102#[derive(Debug, Clone, Default, Copy, PartialEq, Eq, PartialOrd, Ord, Hash)]
103enum ResolveMode {
104 Eager,
105 #[default]
106 Lazy,
107}
108
109impl<const SEPARATOR: char> UsernameLabelWriter<SEPARATOR> for DnsResolveMode {
110 fn write_labels(&self, composer: &mut Composer<SEPARATOR>) -> Result<(), ComposeError> {
111 composer.write_label("dns")?;
112 match self.0 {
113 ResolveMode::Eager => composer.write_label("eager"),
114 ResolveMode::Lazy => composer.write_label("lazy"),
115 }
116 }
117}
118
119#[cfg(test)]
120mod tests {
121 use super::*;
122 use rama_core::context::Extensions;
123 use rama_core::username::{compose_username, parse_username};
124
125 #[test]
126 fn parse_username_label_compose_parse_dns_resolve_mode() {
127 let test_cases = [DnsResolveMode::eager(), DnsResolveMode::lazy()];
128 for test_case in test_cases {
129 let fmt_username = compose_username("john".to_owned(), test_case).unwrap();
130 let mut ext = Extensions::new();
131 let username = parse_username(
132 &mut ext,
133 DnsResolveModeUsernameParser::default(),
134 fmt_username,
135 )
136 .unwrap();
137 assert_eq!("john", username);
138 let result = ext.get::<DnsResolveMode>().unwrap();
139 assert_eq!(test_case, *result);
140 }
141 }
142}