use std::collections::HashMap;
pub mod composite;
pub mod text_map_propagator;
pub use composite::TextMapCompositePropagator;
pub use text_map_propagator::TextMapPropagator;
pub trait Injector {
fn set(&mut self, key: &str, value: String);
}
pub trait Extractor {
fn get(&self, key: &str) -> Option<&str>;
fn keys(&self) -> Vec<&str>;
fn get_all(&self, key: &str) -> Option<Vec<&str>> {
self.get(key).map(|value| vec![value])
}
}
impl<S: std::hash::BuildHasher> Injector for HashMap<String, String, S> {
fn set(&mut self, key: &str, value: String) {
self.insert(key.to_lowercase(), value);
}
}
impl<S: std::hash::BuildHasher> Extractor for HashMap<String, String, S> {
fn get(&self, key: &str) -> Option<&str> {
self.get(&key.to_lowercase()).map(|v| v.as_str())
}
fn keys(&self) -> Vec<&str> {
self.keys().map(|k| k.as_str()).collect::<Vec<_>>()
}
}
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn hash_map_get() {
let mut carrier = HashMap::new();
carrier.set("headerName", "value".to_string());
assert_eq!(
Extractor::get(&carrier, "HEADERNAME"),
Some("value"),
"case insensitive extraction"
);
}
#[test]
fn hash_map_get_all() {
let mut carrier = HashMap::new();
carrier.set("headerName", "value".to_string());
assert_eq!(
Extractor::get_all(&carrier, "HEADERNAME"),
Some(vec!["value"]),
"case insensitive get_all extraction"
);
}
#[test]
fn hash_map_get_all_missing_key() {
let mut carrier = HashMap::new();
carrier.set("headerName", "value".to_string());
assert_eq!(
Extractor::get_all(&carrier, "missing_key"),
None,
"case insensitive get_all extraction"
);
}
#[test]
fn hash_map_keys() {
let mut carrier = HashMap::new();
carrier.set("headerName1", "value1".to_string());
carrier.set("headerName2", "value2".to_string());
let got = Extractor::keys(&carrier);
assert_eq!(got.len(), 2);
assert!(got.contains(&"headername1"));
assert!(got.contains(&"headername2"));
}
}