tonic/metadata/
map.rs

1use http::HeaderName;
2
3pub(crate) use self::as_encoding_agnostic_metadata_key::AsEncodingAgnosticMetadataKey;
4pub(crate) use self::as_metadata_key::AsMetadataKey;
5pub(crate) use self::into_metadata_key::IntoMetadataKey;
6
7use super::encoding::{Ascii, Binary, ValueEncoding};
8use super::key::{InvalidMetadataKey, MetadataKey};
9use super::value::MetadataValue;
10
11use std::marker::PhantomData;
12
13/// A set of gRPC custom metadata entries.
14///
15/// # Examples
16///
17/// Basic usage
18///
19/// ```
20/// # use tonic::metadata::*;
21/// let mut map = MetadataMap::new();
22///
23/// map.insert("x-host", "example.com".parse().unwrap());
24/// map.insert("x-number", "123".parse().unwrap());
25/// map.insert_bin("trace-proto-bin", MetadataValue::from_bytes(b"[binary data]"));
26///
27/// assert!(map.contains_key("x-host"));
28/// assert!(!map.contains_key("x-location"));
29///
30/// assert_eq!(map.get("x-host").unwrap(), "example.com");
31///
32/// map.remove("x-host");
33///
34/// assert!(!map.contains_key("x-host"));
35/// ```
36#[derive(Clone, Debug, Default)]
37pub struct MetadataMap {
38    headers: http::HeaderMap,
39}
40
41/// `MetadataMap` entry iterator.
42///
43/// Yields `KeyAndValueRef` values. The same header name may be yielded
44/// more than once if it has more than one associated value.
45#[derive(Debug)]
46pub struct Iter<'a> {
47    inner: http::header::Iter<'a, http::header::HeaderValue>,
48}
49
50/// Reference to a key and an associated value in a `MetadataMap`. It can point
51/// to either an ascii or a binary ("*-bin") key.
52#[derive(Debug)]
53pub enum KeyAndValueRef<'a> {
54    /// An ascii metadata key and value.
55    Ascii(&'a MetadataKey<Ascii>, &'a MetadataValue<Ascii>),
56    /// A binary metadata key and value.
57    Binary(&'a MetadataKey<Binary>, &'a MetadataValue<Binary>),
58}
59
60/// Reference to a key and an associated value in a `MetadataMap`. It can point
61/// to either an ascii or a binary ("*-bin") key.
62#[derive(Debug)]
63pub enum KeyAndMutValueRef<'a> {
64    /// An ascii metadata key and value.
65    Ascii(&'a MetadataKey<Ascii>, &'a mut MetadataValue<Ascii>),
66    /// A binary metadata key and value.
67    Binary(&'a MetadataKey<Binary>, &'a mut MetadataValue<Binary>),
68}
69
70/// `MetadataMap` entry iterator.
71///
72/// Yields `(&MetadataKey, &mut value)` tuples. The same header name may be yielded
73/// more than once if it has more than one associated value.
74#[derive(Debug)]
75pub struct IterMut<'a> {
76    inner: http::header::IterMut<'a, http::header::HeaderValue>,
77}
78
79/// A drain iterator of all values associated with a single metadata key.
80#[derive(Debug)]
81pub struct ValueDrain<'a, VE: ValueEncoding> {
82    inner: http::header::ValueDrain<'a, http::header::HeaderValue>,
83    phantom: PhantomData<VE>,
84}
85
86/// An iterator over `MetadataMap` keys.
87///
88/// Yields `KeyRef` values. Each header name is yielded only once, even if it
89/// has more than one associated value.
90#[derive(Debug)]
91pub struct Keys<'a> {
92    inner: http::header::Keys<'a, http::header::HeaderValue>,
93}
94
95/// Reference to a key in a `MetadataMap`. It can point
96/// to either an ascii or a binary ("*-bin") key.
97#[derive(Debug)]
98pub enum KeyRef<'a> {
99    /// An ascii metadata key and value.
100    Ascii(&'a MetadataKey<Ascii>),
101    /// A binary metadata key and value.
102    Binary(&'a MetadataKey<Binary>),
103}
104
105/// `MetadataMap` value iterator.
106///
107/// Yields `ValueRef` values. Each value contained in the `MetadataMap` will be
108/// yielded.
109#[derive(Debug)]
110pub struct Values<'a> {
111    // Need to use http::header::Iter and not http::header::Values to be able
112    // to know if a value is binary or not.
113    inner: http::header::Iter<'a, http::header::HeaderValue>,
114}
115
116/// Reference to a value in a `MetadataMap`. It can point
117/// to either an ascii or a binary ("*-bin" key) value.
118#[derive(Debug)]
119pub enum ValueRef<'a> {
120    /// An ascii metadata key and value.
121    Ascii(&'a MetadataValue<Ascii>),
122    /// A binary metadata key and value.
123    Binary(&'a MetadataValue<Binary>),
124}
125
126/// `MetadataMap` value iterator.
127///
128/// Each value contained in the `MetadataMap` will be yielded.
129#[derive(Debug)]
130pub struct ValuesMut<'a> {
131    // Need to use http::header::IterMut and not http::header::ValuesMut to be
132    // able to know if a value is binary or not.
133    inner: http::header::IterMut<'a, http::header::HeaderValue>,
134}
135
136/// Reference to a value in a `MetadataMap`. It can point
137/// to either an ascii or a binary ("*-bin" key) value.
138#[derive(Debug)]
139pub enum ValueRefMut<'a> {
140    /// An ascii metadata key and value.
141    Ascii(&'a mut MetadataValue<Ascii>),
142    /// A binary metadata key and value.
143    Binary(&'a mut MetadataValue<Binary>),
144}
145
146/// An iterator of all values associated with a single metadata key.
147#[derive(Debug)]
148pub struct ValueIter<'a, VE: ValueEncoding> {
149    inner: Option<http::header::ValueIter<'a, http::header::HeaderValue>>,
150    phantom: PhantomData<VE>,
151}
152
153/// An iterator of all values associated with a single metadata key.
154#[derive(Debug)]
155pub struct ValueIterMut<'a, VE: ValueEncoding> {
156    inner: http::header::ValueIterMut<'a, http::header::HeaderValue>,
157    phantom: PhantomData<VE>,
158}
159
160/// A view to all values stored in a single entry.
161///
162/// This struct is returned by `MetadataMap::get_all` and
163/// `MetadataMap::get_all_bin`.
164#[derive(Debug)]
165pub struct GetAll<'a, VE: ValueEncoding> {
166    inner: Option<http::header::GetAll<'a, http::header::HeaderValue>>,
167    phantom: PhantomData<VE>,
168}
169
170/// A view into a single location in a `MetadataMap`, which may be vacant or
171/// occupied.
172#[derive(Debug)]
173pub enum Entry<'a, VE: ValueEncoding> {
174    /// An occupied entry
175    Occupied(OccupiedEntry<'a, VE>),
176
177    /// A vacant entry
178    Vacant(VacantEntry<'a, VE>),
179}
180
181/// A view into a single empty location in a `MetadataMap`.
182///
183/// This struct is returned as part of the `Entry` enum.
184#[derive(Debug)]
185pub struct VacantEntry<'a, VE: ValueEncoding> {
186    inner: http::header::VacantEntry<'a, http::header::HeaderValue>,
187    phantom: PhantomData<VE>,
188}
189
190/// A view into a single occupied location in a `MetadataMap`.
191///
192/// This struct is returned as part of the `Entry` enum.
193#[derive(Debug)]
194pub struct OccupiedEntry<'a, VE: ValueEncoding> {
195    inner: http::header::OccupiedEntry<'a, http::header::HeaderValue>,
196    phantom: PhantomData<VE>,
197}
198
199pub(crate) const GRPC_TIMEOUT_HEADER: &str = "grpc-timeout";
200
201// ===== impl MetadataMap =====
202
203impl MetadataMap {
204    // Headers reserved by the gRPC protocol.
205    pub(crate) const GRPC_RESERVED_HEADERS: [HeaderName; 6] = [
206        HeaderName::from_static("te"),
207        HeaderName::from_static("user-agent"),
208        HeaderName::from_static("content-type"),
209        HeaderName::from_static("grpc-message"),
210        HeaderName::from_static("grpc-message-type"),
211        HeaderName::from_static("grpc-status"),
212    ];
213
214    /// Create an empty `MetadataMap`.
215    ///
216    /// The map will be created without any capacity. This function will not
217    /// allocate.
218    ///
219    /// # Examples
220    ///
221    /// ```
222    /// # use tonic::metadata::*;
223    /// let map = MetadataMap::new();
224    ///
225    /// assert!(map.is_empty());
226    /// assert_eq!(0, map.capacity());
227    /// ```
228    pub fn new() -> Self {
229        MetadataMap::with_capacity(0)
230    }
231
232    /// Convert an HTTP HeaderMap to a MetadataMap
233    pub fn from_headers(headers: http::HeaderMap) -> Self {
234        MetadataMap { headers }
235    }
236
237    /// Convert a MetadataMap into a HTTP HeaderMap
238    ///
239    /// # Examples
240    ///
241    /// ```
242    /// # use tonic::metadata::*;
243    /// let mut map = MetadataMap::new();
244    /// map.insert("x-host", "example.com".parse().unwrap());
245    ///
246    /// let http_map = map.into_headers();
247    ///
248    /// assert_eq!(http_map.get("x-host").unwrap(), "example.com");
249    /// ```
250    pub fn into_headers(self) -> http::HeaderMap {
251        self.headers
252    }
253
254    pub(crate) fn into_sanitized_headers(mut self) -> http::HeaderMap {
255        for r in &Self::GRPC_RESERVED_HEADERS {
256            self.headers.remove(r);
257        }
258        self.headers
259    }
260
261    /// Create an empty `MetadataMap` with the specified capacity.
262    ///
263    /// The returned map will allocate internal storage in order to hold about
264    /// `capacity` elements without reallocating. However, this is a "best
265    /// effort" as there are usage patterns that could cause additional
266    /// allocations before `capacity` metadata entries are stored in the map.
267    ///
268    /// More capacity than requested may be allocated.
269    ///
270    /// # Examples
271    ///
272    /// ```
273    /// # use tonic::metadata::*;
274    /// let map: MetadataMap = MetadataMap::with_capacity(10);
275    ///
276    /// assert!(map.is_empty());
277    /// assert!(map.capacity() >= 10);
278    /// ```
279    pub fn with_capacity(capacity: usize) -> MetadataMap {
280        MetadataMap {
281            headers: http::HeaderMap::with_capacity(capacity),
282        }
283    }
284
285    /// Returns the number of metadata entries (ascii and binary) stored in the
286    /// map.
287    ///
288    /// This number represents the total number of **values** stored in the map.
289    /// This number can be greater than or equal to the number of **keys**
290    /// stored given that a single key may have more than one associated value.
291    ///
292    /// # Examples
293    ///
294    /// ```
295    /// # use tonic::metadata::*;
296    /// let mut map = MetadataMap::new();
297    ///
298    /// assert_eq!(0, map.len());
299    ///
300    /// map.insert("x-host-ip", "127.0.0.1".parse().unwrap());
301    /// map.insert_bin("x-host-name-bin", MetadataValue::from_bytes(b"localhost"));
302    ///
303    /// assert_eq!(2, map.len());
304    ///
305    /// map.append("x-host-ip", "text/html".parse().unwrap());
306    ///
307    /// assert_eq!(3, map.len());
308    /// ```
309    pub fn len(&self) -> usize {
310        self.headers.len()
311    }
312
313    /// Returns the number of keys (ascii and binary) stored in the map.
314    ///
315    /// This number will be less than or equal to `len()` as each key may have
316    /// more than one associated value.
317    ///
318    /// # Examples
319    ///
320    /// ```
321    /// # use tonic::metadata::*;
322    /// let mut map = MetadataMap::new();
323    ///
324    /// assert_eq!(0, map.keys_len());
325    ///
326    /// map.insert("x-host-ip", "127.0.0.1".parse().unwrap());
327    /// map.insert_bin("x-host-name-bin", MetadataValue::from_bytes(b"localhost"));
328    ///
329    /// assert_eq!(2, map.keys_len());
330    ///
331    /// map.append("x-host-ip", "text/html".parse().unwrap());
332    ///
333    /// assert_eq!(2, map.keys_len());
334    /// ```
335    pub fn keys_len(&self) -> usize {
336        self.headers.keys_len()
337    }
338
339    /// Returns true if the map contains no elements.
340    ///
341    /// # Examples
342    ///
343    /// ```
344    /// # use tonic::metadata::*;
345    /// let mut map = MetadataMap::new();
346    ///
347    /// assert!(map.is_empty());
348    ///
349    /// map.insert("x-host", "hello.world".parse().unwrap());
350    ///
351    /// assert!(!map.is_empty());
352    /// ```
353    pub fn is_empty(&self) -> bool {
354        self.headers.is_empty()
355    }
356
357    /// Clears the map, removing all key-value pairs. Keeps the allocated memory
358    /// for reuse.
359    ///
360    /// # Examples
361    ///
362    /// ```
363    /// # use tonic::metadata::*;
364    /// let mut map = MetadataMap::new();
365    /// map.insert("x-host", "hello.world".parse().unwrap());
366    ///
367    /// map.clear();
368    /// assert!(map.is_empty());
369    /// assert!(map.capacity() > 0);
370    /// ```
371    pub fn clear(&mut self) {
372        self.headers.clear();
373    }
374
375    /// Returns the number of custom metadata entries the map can hold without
376    /// reallocating.
377    ///
378    /// This number is an approximation as certain usage patterns could cause
379    /// additional allocations before the returned capacity is filled.
380    ///
381    /// # Examples
382    ///
383    /// ```
384    /// # use tonic::metadata::*;
385    /// let mut map = MetadataMap::new();
386    ///
387    /// assert_eq!(0, map.capacity());
388    ///
389    /// map.insert("x-host", "hello.world".parse().unwrap());
390    /// assert_eq!(6, map.capacity());
391    /// ```
392    pub fn capacity(&self) -> usize {
393        self.headers.capacity()
394    }
395
396    /// Reserves capacity for at least `additional` more custom metadata to be
397    /// inserted into the `MetadataMap`.
398    ///
399    /// The metadata map may reserve more space to avoid frequent reallocations.
400    /// Like with `with_capacity`, this will be a "best effort" to avoid
401    /// allocations until `additional` more custom metadata is inserted. Certain
402    /// usage patterns could cause additional allocations before the number is
403    /// reached.
404    ///
405    /// # Panics
406    ///
407    /// Panics if the new allocation size overflows `usize`.
408    ///
409    /// # Examples
410    ///
411    /// ```
412    /// # use tonic::metadata::*;
413    /// let mut map = MetadataMap::new();
414    /// map.reserve(10);
415    /// # map.insert("x-host", "bar".parse().unwrap());
416    /// ```
417    pub fn reserve(&mut self, additional: usize) {
418        self.headers.reserve(additional);
419    }
420
421    /// Returns a reference to the value associated with the key. This method
422    /// is for ascii metadata entries (those whose names don't end with
423    /// "-bin"). For binary entries, use get_bin.
424    ///
425    /// If there are multiple values associated with the key, then the first one
426    /// is returned. Use `get_all` to get all values associated with a given
427    /// key. Returns `None` if there are no values associated with the key.
428    ///
429    /// # Examples
430    ///
431    /// ```
432    /// # use tonic::metadata::*;
433    /// let mut map = MetadataMap::new();
434    /// assert!(map.get("x-host").is_none());
435    ///
436    /// map.insert("x-host", "hello".parse().unwrap());
437    /// assert_eq!(map.get("x-host").unwrap(), &"hello");
438    /// assert_eq!(map.get("x-host").unwrap(), &"hello");
439    ///
440    /// map.append("x-host", "world".parse().unwrap());
441    /// assert_eq!(map.get("x-host").unwrap(), &"hello");
442    ///
443    /// // Attempting to read a key of the wrong type fails by not
444    /// // finding anything.
445    /// map.append_bin("host-bin", MetadataValue::from_bytes(b"world"));
446    /// assert!(map.get("host-bin").is_none());
447    /// assert!(map.get("host-bin".to_string()).is_none());
448    /// assert!(map.get(&("host-bin".to_string())).is_none());
449    ///
450    /// // Attempting to read an invalid key string fails by not
451    /// // finding anything.
452    /// assert!(map.get("host{}bin").is_none());
453    /// assert!(map.get("host{}bin".to_string()).is_none());
454    /// assert!(map.get(&("host{}bin".to_string())).is_none());
455    /// ```
456    pub fn get<K>(&self, key: K) -> Option<&MetadataValue<Ascii>>
457    where
458        K: AsMetadataKey<Ascii>,
459    {
460        key.get(self)
461    }
462
463    /// Like get, but for Binary keys (for example "trace-proto-bin").
464    ///
465    /// # Examples
466    ///
467    /// ```
468    /// # use tonic::metadata::*;
469    /// let mut map = MetadataMap::new();
470    /// assert!(map.get_bin("trace-proto-bin").is_none());
471    ///
472    /// map.insert_bin("trace-proto-bin", MetadataValue::from_bytes(b"hello"));
473    /// assert_eq!(map.get_bin("trace-proto-bin").unwrap(), &"hello");
474    /// assert_eq!(map.get_bin("trace-proto-bin").unwrap(), &"hello");
475    ///
476    /// map.append_bin("trace-proto-bin", MetadataValue::from_bytes(b"world"));
477    /// assert_eq!(map.get_bin("trace-proto-bin").unwrap(), &"hello");
478    ///
479    /// // Attempting to read a key of the wrong type fails by not
480    /// // finding anything.
481    /// map.append("host", "world".parse().unwrap());
482    /// assert!(map.get_bin("host").is_none());
483    /// assert!(map.get_bin("host".to_string()).is_none());
484    /// assert!(map.get_bin(&("host".to_string())).is_none());
485    ///
486    /// // Attempting to read an invalid key string fails by not
487    /// // finding anything.
488    /// assert!(map.get_bin("host{}-bin").is_none());
489    /// assert!(map.get_bin("host{}-bin".to_string()).is_none());
490    /// assert!(map.get_bin(&("host{}-bin".to_string())).is_none());
491    /// ```
492    pub fn get_bin<K>(&self, key: K) -> Option<&MetadataValue<Binary>>
493    where
494        K: AsMetadataKey<Binary>,
495    {
496        key.get(self)
497    }
498
499    /// Returns a mutable reference to the value associated with the key. This
500    /// method is for ascii metadata entries (those whose names don't end with
501    /// "-bin"). For binary entries, use get_mut_bin.
502    ///
503    /// If there are multiple values associated with the key, then the first one
504    /// is returned. Use `entry` to get all values associated with a given
505    /// key. Returns `None` if there are no values associated with the key.
506    ///
507    /// # Examples
508    ///
509    /// ```
510    /// # use tonic::metadata::*;
511    /// let mut map = MetadataMap::default();
512    /// map.insert("x-host", "hello".parse().unwrap());
513    /// map.get_mut("x-host").unwrap().set_sensitive(true);
514    ///
515    /// assert!(map.get("x-host").unwrap().is_sensitive());
516    ///
517    /// // Attempting to read a key of the wrong type fails by not
518    /// // finding anything.
519    /// map.append_bin("host-bin", MetadataValue::from_bytes(b"world"));
520    /// assert!(map.get_mut("host-bin").is_none());
521    /// assert!(map.get_mut("host-bin".to_string()).is_none());
522    /// assert!(map.get_mut(&("host-bin".to_string())).is_none());
523    ///
524    /// // Attempting to read an invalid key string fails by not
525    /// // finding anything.
526    /// assert!(map.get_mut("host{}").is_none());
527    /// assert!(map.get_mut("host{}".to_string()).is_none());
528    /// assert!(map.get_mut(&("host{}".to_string())).is_none());
529    /// ```
530    pub fn get_mut<K>(&mut self, key: K) -> Option<&mut MetadataValue<Ascii>>
531    where
532        K: AsMetadataKey<Ascii>,
533    {
534        key.get_mut(self)
535    }
536
537    /// Like get_mut, but for Binary keys (for example "trace-proto-bin").
538    ///
539    /// # Examples
540    ///
541    /// ```
542    /// # use tonic::metadata::*;
543    /// let mut map = MetadataMap::default();
544    /// map.insert_bin("trace-proto-bin", MetadataValue::from_bytes(b"hello"));
545    /// map.get_bin_mut("trace-proto-bin").unwrap().set_sensitive(true);
546    ///
547    /// assert!(map.get_bin("trace-proto-bin").unwrap().is_sensitive());
548    ///
549    /// // Attempting to read a key of the wrong type fails by not
550    /// // finding anything.
551    /// map.append("host", "world".parse().unwrap());
552    /// assert!(map.get_bin_mut("host").is_none());
553    /// assert!(map.get_bin_mut("host".to_string()).is_none());
554    /// assert!(map.get_bin_mut(&("host".to_string())).is_none());
555    ///
556    /// // Attempting to read an invalid key string fails by not
557    /// // finding anything.
558    /// assert!(map.get_bin_mut("host{}-bin").is_none());
559    /// assert!(map.get_bin_mut("host{}-bin".to_string()).is_none());
560    /// assert!(map.get_bin_mut(&("host{}-bin".to_string())).is_none());
561    /// ```
562    pub fn get_bin_mut<K>(&mut self, key: K) -> Option<&mut MetadataValue<Binary>>
563    where
564        K: AsMetadataKey<Binary>,
565    {
566        key.get_mut(self)
567    }
568
569    /// Returns a view of all values associated with a key. This method is for
570    /// ascii metadata entries (those whose names don't end with "-bin"). For
571    /// binary entries, use get_all_bin.
572    ///
573    /// The returned view does not incur any allocations and allows iterating
574    /// the values associated with the key.  See [`GetAll`] for more details.
575    /// Returns `None` if there are no values associated with the key.
576    ///
577    /// [`GetAll`]: struct.GetAll.html
578    ///
579    /// # Examples
580    ///
581    /// ```
582    /// # use tonic::metadata::*;
583    /// let mut map = MetadataMap::new();
584    ///
585    /// map.insert("x-host", "hello".parse().unwrap());
586    /// map.append("x-host", "goodbye".parse().unwrap());
587    ///
588    /// {
589    ///     let view = map.get_all("x-host");
590    ///
591    ///     let mut iter = view.iter();
592    ///     assert_eq!(&"hello", iter.next().unwrap());
593    ///     assert_eq!(&"goodbye", iter.next().unwrap());
594    ///     assert!(iter.next().is_none());
595    /// }
596    ///
597    /// // Attempting to read a key of the wrong type fails by not
598    /// // finding anything.
599    /// map.append_bin("host-bin", MetadataValue::from_bytes(b"world"));
600    /// assert!(map.get_all("host-bin").iter().next().is_none());
601    /// assert!(map.get_all("host-bin".to_string()).iter().next().is_none());
602    /// assert!(map.get_all(&("host-bin".to_string())).iter().next().is_none());
603    ///
604    /// // Attempting to read an invalid key string fails by not
605    /// // finding anything.
606    /// assert!(map.get_all("host{}").iter().next().is_none());
607    /// assert!(map.get_all("host{}".to_string()).iter().next().is_none());
608    /// assert!(map.get_all(&("host{}".to_string())).iter().next().is_none());
609    /// ```
610    pub fn get_all<K>(&self, key: K) -> GetAll<'_, Ascii>
611    where
612        K: AsMetadataKey<Ascii>,
613    {
614        GetAll {
615            inner: key.get_all(self),
616            phantom: PhantomData,
617        }
618    }
619
620    /// Like get_all, but for Binary keys (for example "trace-proto-bin").
621    ///
622    /// # Examples
623    ///
624    /// ```
625    /// # use tonic::metadata::*;
626    /// let mut map = MetadataMap::new();
627    ///
628    /// map.insert_bin("trace-proto-bin", MetadataValue::from_bytes(b"hello"));
629    /// map.append_bin("trace-proto-bin", MetadataValue::from_bytes(b"goodbye"));
630    ///
631    /// {
632    ///     let view = map.get_all_bin("trace-proto-bin");
633    ///
634    ///     let mut iter = view.iter();
635    ///     assert_eq!(&"hello", iter.next().unwrap());
636    ///     assert_eq!(&"goodbye", iter.next().unwrap());
637    ///     assert!(iter.next().is_none());
638    /// }
639    ///
640    /// // Attempting to read a key of the wrong type fails by not
641    /// // finding anything.
642    /// map.append("host", "world".parse().unwrap());
643    /// assert!(map.get_all_bin("host").iter().next().is_none());
644    /// assert!(map.get_all_bin("host".to_string()).iter().next().is_none());
645    /// assert!(map.get_all_bin(&("host".to_string())).iter().next().is_none());
646    ///
647    /// // Attempting to read an invalid key string fails by not
648    /// // finding anything.
649    /// assert!(map.get_all_bin("host{}-bin").iter().next().is_none());
650    /// assert!(map.get_all_bin("host{}-bin".to_string()).iter().next().is_none());
651    /// assert!(map.get_all_bin(&("host{}-bin".to_string())).iter().next().is_none());
652    /// ```
653    pub fn get_all_bin<K>(&self, key: K) -> GetAll<'_, Binary>
654    where
655        K: AsMetadataKey<Binary>,
656    {
657        GetAll {
658            inner: key.get_all(self),
659            phantom: PhantomData,
660        }
661    }
662
663    /// Returns true if the map contains a value for the specified key. This
664    /// method works for both ascii and binary entries.
665    ///
666    /// # Examples
667    ///
668    /// ```
669    /// # use tonic::metadata::*;
670    /// let mut map = MetadataMap::new();
671    /// assert!(!map.contains_key("x-host"));
672    ///
673    /// map.append_bin("host-bin", MetadataValue::from_bytes(b"world"));
674    /// map.insert("x-host", "world".parse().unwrap());
675    ///
676    /// // contains_key works for both Binary and Ascii keys:
677    /// assert!(map.contains_key("x-host"));
678    /// assert!(map.contains_key("host-bin"));
679    ///
680    /// // contains_key returns false for invalid keys:
681    /// assert!(!map.contains_key("x{}host"));
682    /// ```
683    pub fn contains_key<K>(&self, key: K) -> bool
684    where
685        K: AsEncodingAgnosticMetadataKey,
686    {
687        key.contains_key(self)
688    }
689
690    /// An iterator visiting all key-value pairs (both ascii and binary).
691    ///
692    /// The iteration order is arbitrary, but consistent across platforms for
693    /// the same crate version. Each key will be yielded once per associated
694    /// value. So, if a key has 3 associated values, it will be yielded 3 times.
695    ///
696    /// # Examples
697    ///
698    /// ```
699    /// # use tonic::metadata::*;
700    /// let mut map = MetadataMap::new();
701    ///
702    /// map.insert("x-word", "hello".parse().unwrap());
703    /// map.append("x-word", "goodbye".parse().unwrap());
704    /// map.insert("x-number", "123".parse().unwrap());
705    ///
706    /// for key_and_value in map.iter() {
707    ///     match key_and_value {
708    ///         KeyAndValueRef::Ascii(ref key, ref value) =>
709    ///             println!("Ascii: {:?}: {:?}", key, value),
710    ///         KeyAndValueRef::Binary(ref key, ref value) =>
711    ///             println!("Binary: {:?}: {:?}", key, value),
712    ///     }
713    /// }
714    /// ```
715    pub fn iter(&self) -> Iter<'_> {
716        Iter {
717            inner: self.headers.iter(),
718        }
719    }
720
721    /// An iterator visiting all key-value pairs, with mutable value references.
722    ///
723    /// The iterator order is arbitrary, but consistent across platforms for the
724    /// same crate version. Each key will be yielded once per associated value,
725    /// so if a key has 3 associated values, it will be yielded 3 times.
726    ///
727    /// # Examples
728    ///
729    /// ```
730    /// # use tonic::metadata::*;
731    /// let mut map = MetadataMap::new();
732    ///
733    /// map.insert("x-word", "hello".parse().unwrap());
734    /// map.append("x-word", "goodbye".parse().unwrap());
735    /// map.insert("x-number", "123".parse().unwrap());
736    ///
737    /// for key_and_value in map.iter_mut() {
738    ///     match key_and_value {
739    ///         KeyAndMutValueRef::Ascii(key, mut value) =>
740    ///             value.set_sensitive(true),
741    ///         KeyAndMutValueRef::Binary(key, mut value) =>
742    ///             value.set_sensitive(false),
743    ///     }
744    /// }
745    /// ```
746    pub fn iter_mut(&mut self) -> IterMut<'_> {
747        IterMut {
748            inner: self.headers.iter_mut(),
749        }
750    }
751
752    /// An iterator visiting all keys.
753    ///
754    /// The iteration order is arbitrary, but consistent across platforms for
755    /// the same crate version. Each key will be yielded only once even if it
756    /// has multiple associated values.
757    ///
758    /// # Examples
759    ///
760    /// ```
761    /// # use tonic::metadata::*;
762    /// let mut map = MetadataMap::new();
763    ///
764    /// map.insert("x-word", "hello".parse().unwrap());
765    /// map.append("x-word", "goodbye".parse().unwrap());
766    /// map.insert_bin("x-number-bin", MetadataValue::from_bytes(b"123"));
767    ///
768    /// for key in map.keys() {
769    ///     match key {
770    ///         KeyRef::Ascii(ref key) =>
771    ///             println!("Ascii key: {:?}", key),
772    ///         KeyRef::Binary(ref key) =>
773    ///             println!("Binary key: {:?}", key),
774    ///     }
775    ///     println!("{:?}", key);
776    /// }
777    /// ```
778    pub fn keys(&self) -> Keys<'_> {
779        Keys {
780            inner: self.headers.keys(),
781        }
782    }
783
784    /// An iterator visiting all values (both ascii and binary).
785    ///
786    /// The iteration order is arbitrary, but consistent across platforms for
787    /// the same crate version.
788    ///
789    /// # Examples
790    ///
791    /// ```
792    /// # use tonic::metadata::*;
793    /// let mut map = MetadataMap::new();
794    ///
795    /// map.insert("x-word", "hello".parse().unwrap());
796    /// map.append("x-word", "goodbye".parse().unwrap());
797    /// map.insert_bin("x-number-bin", MetadataValue::from_bytes(b"123"));
798    ///
799    /// for value in map.values() {
800    ///     match value {
801    ///         ValueRef::Ascii(ref value) =>
802    ///             println!("Ascii value: {:?}", value),
803    ///         ValueRef::Binary(ref value) =>
804    ///             println!("Binary value: {:?}", value),
805    ///     }
806    ///     println!("{:?}", value);
807    /// }
808    /// ```
809    pub fn values(&self) -> Values<'_> {
810        Values {
811            inner: self.headers.iter(),
812        }
813    }
814
815    /// An iterator visiting all values mutably.
816    ///
817    /// The iteration order is arbitrary, but consistent across platforms for
818    /// the same crate version.
819    ///
820    /// # Examples
821    ///
822    /// ```
823    /// # use tonic::metadata::*;
824    /// let mut map = MetadataMap::default();
825    ///
826    /// map.insert("x-word", "hello".parse().unwrap());
827    /// map.append("x-word", "goodbye".parse().unwrap());
828    /// map.insert("x-number", "123".parse().unwrap());
829    ///
830    /// for value in map.values_mut() {
831    ///     match value {
832    ///         ValueRefMut::Ascii(mut value) =>
833    ///             value.set_sensitive(true),
834    ///         ValueRefMut::Binary(mut value) =>
835    ///             value.set_sensitive(false),
836    ///     }
837    /// }
838    /// ```
839    pub fn values_mut(&mut self) -> ValuesMut<'_> {
840        ValuesMut {
841            inner: self.headers.iter_mut(),
842        }
843    }
844
845    /// Gets the given ascii key's corresponding entry in the map for in-place
846    /// manipulation. For binary keys, use `entry_bin`.
847    ///
848    /// # Examples
849    ///
850    /// ```
851    /// # use tonic::metadata::*;
852    /// let mut map = MetadataMap::default();
853    ///
854    /// let headers = &[
855    ///     "content-length",
856    ///     "x-hello",
857    ///     "Content-Length",
858    ///     "x-world",
859    /// ];
860    ///
861    /// for &header in headers {
862    ///     let counter = map.entry(header).unwrap().or_insert("".parse().unwrap());
863    ///     *counter = format!("{}{}", counter.to_str().unwrap(), "1").parse().unwrap();
864    /// }
865    ///
866    /// assert_eq!(map.get("content-length").unwrap(), "11");
867    /// assert_eq!(map.get("x-hello").unwrap(), "1");
868    ///
869    /// // Gracefully handles parting invalid key strings
870    /// assert!(!map.entry("a{}b").is_ok());
871    ///
872    /// // Attempting to read a key of the wrong type fails by not
873    /// // finding anything.
874    /// map.append_bin("host-bin", MetadataValue::from_bytes(b"world"));
875    /// assert!(!map.entry("host-bin").is_ok());
876    /// assert!(!map.entry("host-bin".to_string()).is_ok());
877    /// assert!(!map.entry(&("host-bin".to_string())).is_ok());
878    ///
879    /// // Attempting to read an invalid key string fails by not
880    /// // finding anything.
881    /// assert!(!map.entry("host{}").is_ok());
882    /// assert!(!map.entry("host{}".to_string()).is_ok());
883    /// assert!(!map.entry(&("host{}".to_string())).is_ok());
884    /// ```
885    pub fn entry<K>(&mut self, key: K) -> Result<Entry<'_, Ascii>, InvalidMetadataKey>
886    where
887        K: AsMetadataKey<Ascii>,
888    {
889        self.generic_entry::<Ascii, K>(key)
890    }
891
892    /// Gets the given Binary key's corresponding entry in the map for in-place
893    /// manipulation.
894    ///
895    /// # Examples
896    ///
897    /// ```
898    /// # use tonic::metadata::*;
899    /// # use std::str;
900    /// let mut map = MetadataMap::default();
901    ///
902    /// let headers = &[
903    ///     "content-length-bin",
904    ///     "x-hello-bin",
905    ///     "Content-Length-bin",
906    ///     "x-world-bin",
907    /// ];
908    ///
909    /// for &header in headers {
910    ///     let counter = map.entry_bin(header).unwrap().or_insert(MetadataValue::from_bytes(b""));
911    ///     *counter = MetadataValue::from_bytes(format!("{}{}", str::from_utf8(counter.to_bytes().unwrap().as_ref()).unwrap(), "1").as_bytes());
912    /// }
913    ///
914    /// assert_eq!(map.get_bin("content-length-bin").unwrap(), "11");
915    /// assert_eq!(map.get_bin("x-hello-bin").unwrap(), "1");
916    ///
917    /// // Attempting to read a key of the wrong type fails by not
918    /// // finding anything.
919    /// map.append("host", "world".parse().unwrap());
920    /// assert!(!map.entry_bin("host").is_ok());
921    /// assert!(!map.entry_bin("host".to_string()).is_ok());
922    /// assert!(!map.entry_bin(&("host".to_string())).is_ok());
923    ///
924    /// // Attempting to read an invalid key string fails by not
925    /// // finding anything.
926    /// assert!(!map.entry_bin("host{}-bin").is_ok());
927    /// assert!(!map.entry_bin("host{}-bin".to_string()).is_ok());
928    /// assert!(!map.entry_bin(&("host{}-bin".to_string())).is_ok());
929    /// ```
930    pub fn entry_bin<K>(&mut self, key: K) -> Result<Entry<'_, Binary>, InvalidMetadataKey>
931    where
932        K: AsMetadataKey<Binary>,
933    {
934        self.generic_entry::<Binary, K>(key)
935    }
936
937    fn generic_entry<VE: ValueEncoding, K>(
938        &mut self,
939        key: K,
940    ) -> Result<Entry<'_, VE>, InvalidMetadataKey>
941    where
942        K: AsMetadataKey<VE>,
943    {
944        match key.entry(self) {
945            Ok(entry) => Ok(match entry {
946                http::header::Entry::Occupied(e) => Entry::Occupied(OccupiedEntry {
947                    inner: e,
948                    phantom: PhantomData,
949                }),
950                http::header::Entry::Vacant(e) => Entry::Vacant(VacantEntry {
951                    inner: e,
952                    phantom: PhantomData,
953                }),
954            }),
955            Err(err) => Err(err),
956        }
957    }
958
959    /// Inserts an ascii key-value pair into the map. To insert a binary entry,
960    /// use `insert_bin`.
961    ///
962    /// This method panics when the given key is a string and it cannot be
963    /// converted to a `MetadataKey<Ascii>`.
964    ///
965    /// If the map did not previously have this key present, then `None` is
966    /// returned.
967    ///
968    /// If the map did have this key present, the new value is associated with
969    /// the key and all previous values are removed. **Note** that only a single
970    /// one of the previous values is returned. If there are multiple values
971    /// that have been previously associated with the key, then the first one is
972    /// returned. See `insert_mult` on `OccupiedEntry` for an API that returns
973    /// all values.
974    ///
975    /// The key is not updated, though; this matters for types that can be `==`
976    /// without being identical.
977    ///
978    /// # Examples
979    ///
980    /// ```
981    /// # use tonic::metadata::*;
982    /// let mut map = MetadataMap::new();
983    /// assert!(map.insert("x-host", "world".parse().unwrap()).is_none());
984    /// assert!(!map.is_empty());
985    ///
986    /// let mut prev = map.insert("x-host", "earth".parse().unwrap()).unwrap();
987    /// assert_eq!("world", prev);
988    /// ```
989    ///
990    /// ```should_panic
991    /// # use tonic::metadata::*;
992    /// let mut map = MetadataMap::new();
993    /// // Trying to insert a key that is not valid panics.
994    /// map.insert("x{}host", "world".parse().unwrap());
995    /// ```
996    ///
997    /// ```should_panic
998    /// # use tonic::metadata::*;
999    /// let mut map = MetadataMap::new();
1000    /// // Trying to insert a key that is binary panics (use insert_bin).
1001    /// map.insert("x-host-bin", "world".parse().unwrap());
1002    /// ```
1003    pub fn insert<K>(&mut self, key: K, val: MetadataValue<Ascii>) -> Option<MetadataValue<Ascii>>
1004    where
1005        K: IntoMetadataKey<Ascii>,
1006    {
1007        key.insert(self, val)
1008    }
1009
1010    /// Like insert, but for Binary keys (for example "trace-proto-bin").
1011    ///
1012    /// This method panics when the given key is a string and it cannot be
1013    /// converted to a `MetadataKey<Binary>`.
1014    ///
1015    /// # Examples
1016    ///
1017    /// ```
1018    /// # use tonic::metadata::*;
1019    /// let mut map = MetadataMap::new();
1020    /// assert!(map.insert_bin("trace-proto-bin", MetadataValue::from_bytes(b"world")).is_none());
1021    /// assert!(!map.is_empty());
1022    ///
1023    /// let mut prev = map.insert_bin("trace-proto-bin", MetadataValue::from_bytes(b"earth")).unwrap();
1024    /// assert_eq!("world", prev);
1025    /// ```
1026    ///
1027    /// ```should_panic
1028    /// # use tonic::metadata::*;
1029    /// let mut map = MetadataMap::default();
1030    /// // Attempting to add a binary metadata entry with an invalid name
1031    /// map.insert_bin("trace-proto", MetadataValue::from_bytes(b"hello")); // This line panics!
1032    /// ```
1033    ///
1034    /// ```should_panic
1035    /// # use tonic::metadata::*;
1036    /// let mut map = MetadataMap::new();
1037    /// // Trying to insert a key that is not valid panics.
1038    /// map.insert_bin("x{}host-bin", MetadataValue::from_bytes(b"world")); // This line panics!
1039    /// ```
1040    pub fn insert_bin<K>(
1041        &mut self,
1042        key: K,
1043        val: MetadataValue<Binary>,
1044    ) -> Option<MetadataValue<Binary>>
1045    where
1046        K: IntoMetadataKey<Binary>,
1047    {
1048        key.insert(self, val)
1049    }
1050
1051    /// Inserts an ascii key-value pair into the map. To insert a binary entry,
1052    /// use `append_bin`.
1053    ///
1054    /// This method panics when the given key is a string and it cannot be
1055    /// converted to a `MetadataKey<Ascii>`.
1056    ///
1057    /// If the map did not previously have this key present, then `false` is
1058    /// returned.
1059    ///
1060    /// If the map did have this key present, the new value is pushed to the end
1061    /// of the list of values currently associated with the key. The key is not
1062    /// updated, though; this matters for types that can be `==` without being
1063    /// identical.
1064    ///
1065    /// # Examples
1066    ///
1067    /// ```
1068    /// # use tonic::metadata::*;
1069    /// let mut map = MetadataMap::new();
1070    /// assert!(map.insert("x-host", "world".parse().unwrap()).is_none());
1071    /// assert!(!map.is_empty());
1072    ///
1073    /// map.append("x-host", "earth".parse().unwrap());
1074    ///
1075    /// let values = map.get_all("x-host");
1076    /// let mut i = values.iter();
1077    /// assert_eq!("world", *i.next().unwrap());
1078    /// assert_eq!("earth", *i.next().unwrap());
1079    /// ```
1080    ///
1081    /// ```should_panic
1082    /// # use tonic::metadata::*;
1083    /// let mut map = MetadataMap::new();
1084    /// // Trying to append a key that is not valid panics.
1085    /// map.append("x{}host", "world".parse().unwrap()); // This line panics!
1086    /// ```
1087    ///
1088    /// ```should_panic
1089    /// # use tonic::metadata::*;
1090    /// let mut map = MetadataMap::new();
1091    /// // Trying to append a key that is binary panics (use append_bin).
1092    /// map.append("x-host-bin", "world".parse().unwrap()); // This line panics!
1093    /// ```
1094    pub fn append<K>(&mut self, key: K, value: MetadataValue<Ascii>) -> bool
1095    where
1096        K: IntoMetadataKey<Ascii>,
1097    {
1098        key.append(self, value)
1099    }
1100
1101    /// Like append, but for binary keys (for example "trace-proto-bin").
1102    ///
1103    /// This method panics when the given key is a string and it cannot be
1104    /// converted to a `MetadataKey<Binary>`.
1105    ///
1106    /// # Examples
1107    ///
1108    /// ```
1109    /// # use tonic::metadata::*;
1110    /// let mut map = MetadataMap::new();
1111    /// assert!(map.insert_bin("trace-proto-bin", MetadataValue::from_bytes(b"world")).is_none());
1112    /// assert!(!map.is_empty());
1113    ///
1114    /// map.append_bin("trace-proto-bin", MetadataValue::from_bytes(b"earth"));
1115    ///
1116    /// let values = map.get_all_bin("trace-proto-bin");
1117    /// let mut i = values.iter();
1118    /// assert_eq!("world", *i.next().unwrap());
1119    /// assert_eq!("earth", *i.next().unwrap());
1120    /// ```
1121    ///
1122    /// ```should_panic
1123    /// # use tonic::metadata::*;
1124    /// let mut map = MetadataMap::new();
1125    /// // Trying to append a key that is not valid panics.
1126    /// map.append_bin("x{}host-bin", MetadataValue::from_bytes(b"world")); // This line panics!
1127    /// ```
1128    ///
1129    /// ```should_panic
1130    /// # use tonic::metadata::*;
1131    /// let mut map = MetadataMap::new();
1132    /// // Trying to append a key that is ascii panics (use append).
1133    /// map.append_bin("x-host", MetadataValue::from_bytes(b"world")); // This line panics!
1134    /// ```
1135    pub fn append_bin<K>(&mut self, key: K, value: MetadataValue<Binary>) -> bool
1136    where
1137        K: IntoMetadataKey<Binary>,
1138    {
1139        key.append(self, value)
1140    }
1141
1142    /// Removes an ascii key from the map, returning the value associated with
1143    /// the key. To remove a binary key, use `remove_bin`.
1144    ///
1145    /// Returns `None` if the map does not contain the key. If there are
1146    /// multiple values associated with the key, then the first one is returned.
1147    /// See `remove_entry_mult` on `OccupiedEntry` for an API that yields all
1148    /// values.
1149    ///
1150    /// # Examples
1151    ///
1152    /// ```
1153    /// # use tonic::metadata::*;
1154    /// let mut map = MetadataMap::new();
1155    /// map.insert("x-host", "hello.world".parse().unwrap());
1156    ///
1157    /// let prev = map.remove("x-host").unwrap();
1158    /// assert_eq!("hello.world", prev);
1159    ///
1160    /// assert!(map.remove("x-host").is_none());
1161    ///
1162    /// // Attempting to remove a key of the wrong type fails by not
1163    /// // finding anything.
1164    /// map.append_bin("host-bin", MetadataValue::from_bytes(b"world"));
1165    /// assert!(map.remove("host-bin").is_none());
1166    /// assert!(map.remove("host-bin".to_string()).is_none());
1167    /// assert!(map.remove(&("host-bin".to_string())).is_none());
1168    ///
1169    /// // Attempting to remove an invalid key string fails by not
1170    /// // finding anything.
1171    /// assert!(map.remove("host{}").is_none());
1172    /// assert!(map.remove("host{}".to_string()).is_none());
1173    /// assert!(map.remove(&("host{}".to_string())).is_none());
1174    /// ```
1175    pub fn remove<K>(&mut self, key: K) -> Option<MetadataValue<Ascii>>
1176    where
1177        K: AsMetadataKey<Ascii>,
1178    {
1179        key.remove(self)
1180    }
1181
1182    /// Like remove, but for Binary keys (for example "trace-proto-bin").
1183    ///
1184    /// # Examples
1185    ///
1186    /// ```
1187    /// # use tonic::metadata::*;
1188    /// let mut map = MetadataMap::new();
1189    /// map.insert_bin("trace-proto-bin", MetadataValue::from_bytes(b"hello.world"));
1190    ///
1191    /// let prev = map.remove_bin("trace-proto-bin").unwrap();
1192    /// assert_eq!("hello.world", prev);
1193    ///
1194    /// assert!(map.remove_bin("trace-proto-bin").is_none());
1195    ///
1196    /// // Attempting to remove a key of the wrong type fails by not
1197    /// // finding anything.
1198    /// map.append("host", "world".parse().unwrap());
1199    /// assert!(map.remove_bin("host").is_none());
1200    /// assert!(map.remove_bin("host".to_string()).is_none());
1201    /// assert!(map.remove_bin(&("host".to_string())).is_none());
1202    ///
1203    /// // Attempting to remove an invalid key string fails by not
1204    /// // finding anything.
1205    /// assert!(map.remove_bin("host{}-bin").is_none());
1206    /// assert!(map.remove_bin("host{}-bin".to_string()).is_none());
1207    /// assert!(map.remove_bin(&("host{}-bin".to_string())).is_none());
1208    /// ```
1209    pub fn remove_bin<K>(&mut self, key: K) -> Option<MetadataValue<Binary>>
1210    where
1211        K: AsMetadataKey<Binary>,
1212    {
1213        key.remove(self)
1214    }
1215
1216    pub(crate) fn merge(&mut self, other: MetadataMap) {
1217        self.headers.extend(other.headers);
1218    }
1219}
1220
1221// ===== impl Iter =====
1222
1223impl<'a> Iterator for Iter<'a> {
1224    type Item = KeyAndValueRef<'a>;
1225
1226    fn next(&mut self) -> Option<Self::Item> {
1227        self.inner.next().map(|item| {
1228            let (name, value) = item;
1229            if Ascii::is_valid_key(name.as_str()) {
1230                KeyAndValueRef::Ascii(
1231                    MetadataKey::unchecked_from_header_name_ref(name),
1232                    MetadataValue::unchecked_from_header_value_ref(value),
1233                )
1234            } else {
1235                KeyAndValueRef::Binary(
1236                    MetadataKey::unchecked_from_header_name_ref(name),
1237                    MetadataValue::unchecked_from_header_value_ref(value),
1238                )
1239            }
1240        })
1241    }
1242
1243    fn size_hint(&self) -> (usize, Option<usize>) {
1244        self.inner.size_hint()
1245    }
1246}
1247
1248// ===== impl IterMut =====
1249
1250impl<'a> Iterator for IterMut<'a> {
1251    type Item = KeyAndMutValueRef<'a>;
1252
1253    fn next(&mut self) -> Option<Self::Item> {
1254        self.inner.next().map(|item| {
1255            let (name, value) = item;
1256            if Ascii::is_valid_key(name.as_str()) {
1257                KeyAndMutValueRef::Ascii(
1258                    MetadataKey::unchecked_from_header_name_ref(name),
1259                    MetadataValue::unchecked_from_mut_header_value_ref(value),
1260                )
1261            } else {
1262                KeyAndMutValueRef::Binary(
1263                    MetadataKey::unchecked_from_header_name_ref(name),
1264                    MetadataValue::unchecked_from_mut_header_value_ref(value),
1265                )
1266            }
1267        })
1268    }
1269
1270    fn size_hint(&self) -> (usize, Option<usize>) {
1271        self.inner.size_hint()
1272    }
1273}
1274
1275// ===== impl ValueDrain =====
1276
1277impl<'a, VE: ValueEncoding> Iterator for ValueDrain<'a, VE> {
1278    type Item = MetadataValue<VE>;
1279
1280    fn next(&mut self) -> Option<Self::Item> {
1281        self.inner
1282            .next()
1283            .map(MetadataValue::unchecked_from_header_value)
1284    }
1285
1286    fn size_hint(&self) -> (usize, Option<usize>) {
1287        self.inner.size_hint()
1288    }
1289}
1290
1291// ===== impl Keys =====
1292
1293impl<'a> Iterator for Keys<'a> {
1294    type Item = KeyRef<'a>;
1295
1296    fn next(&mut self) -> Option<Self::Item> {
1297        self.inner.next().map(|key| {
1298            if Ascii::is_valid_key(key.as_str()) {
1299                KeyRef::Ascii(MetadataKey::unchecked_from_header_name_ref(key))
1300            } else {
1301                KeyRef::Binary(MetadataKey::unchecked_from_header_name_ref(key))
1302            }
1303        })
1304    }
1305
1306    fn size_hint(&self) -> (usize, Option<usize>) {
1307        self.inner.size_hint()
1308    }
1309}
1310
1311impl<'a> ExactSizeIterator for Keys<'a> {}
1312
1313// ===== impl Values ====
1314
1315impl<'a> Iterator for Values<'a> {
1316    type Item = ValueRef<'a>;
1317
1318    fn next(&mut self) -> Option<Self::Item> {
1319        self.inner.next().map(|item| {
1320            let (name, value) = item;
1321            if Ascii::is_valid_key(name.as_str()) {
1322                ValueRef::Ascii(MetadataValue::unchecked_from_header_value_ref(value))
1323            } else {
1324                ValueRef::Binary(MetadataValue::unchecked_from_header_value_ref(value))
1325            }
1326        })
1327    }
1328
1329    fn size_hint(&self) -> (usize, Option<usize>) {
1330        self.inner.size_hint()
1331    }
1332}
1333
1334// ===== impl Values ====
1335
1336impl<'a> Iterator for ValuesMut<'a> {
1337    type Item = ValueRefMut<'a>;
1338
1339    fn next(&mut self) -> Option<Self::Item> {
1340        self.inner.next().map(|item| {
1341            let (name, value) = item;
1342            if Ascii::is_valid_key(name.as_str()) {
1343                ValueRefMut::Ascii(MetadataValue::unchecked_from_mut_header_value_ref(value))
1344            } else {
1345                ValueRefMut::Binary(MetadataValue::unchecked_from_mut_header_value_ref(value))
1346            }
1347        })
1348    }
1349
1350    fn size_hint(&self) -> (usize, Option<usize>) {
1351        self.inner.size_hint()
1352    }
1353}
1354
1355// ===== impl ValueIter =====
1356
1357impl<'a, VE: ValueEncoding> Iterator for ValueIter<'a, VE>
1358where
1359    VE: 'a,
1360{
1361    type Item = &'a MetadataValue<VE>;
1362
1363    fn next(&mut self) -> Option<Self::Item> {
1364        match self.inner {
1365            Some(ref mut inner) => inner
1366                .next()
1367                .map(MetadataValue::unchecked_from_header_value_ref),
1368            None => None,
1369        }
1370    }
1371
1372    fn size_hint(&self) -> (usize, Option<usize>) {
1373        match self.inner {
1374            Some(ref inner) => inner.size_hint(),
1375            None => (0, Some(0)),
1376        }
1377    }
1378}
1379
1380impl<'a, VE: ValueEncoding> DoubleEndedIterator for ValueIter<'a, VE>
1381where
1382    VE: 'a,
1383{
1384    fn next_back(&mut self) -> Option<Self::Item> {
1385        match self.inner {
1386            Some(ref mut inner) => inner
1387                .next_back()
1388                .map(MetadataValue::unchecked_from_header_value_ref),
1389            None => None,
1390        }
1391    }
1392}
1393
1394// ===== impl ValueIterMut =====
1395
1396impl<'a, VE: ValueEncoding> Iterator for ValueIterMut<'a, VE>
1397where
1398    VE: 'a,
1399{
1400    type Item = &'a mut MetadataValue<VE>;
1401
1402    fn next(&mut self) -> Option<Self::Item> {
1403        self.inner
1404            .next()
1405            .map(MetadataValue::unchecked_from_mut_header_value_ref)
1406    }
1407}
1408
1409impl<'a, VE: ValueEncoding> DoubleEndedIterator for ValueIterMut<'a, VE>
1410where
1411    VE: 'a,
1412{
1413    fn next_back(&mut self) -> Option<Self::Item> {
1414        self.inner
1415            .next_back()
1416            .map(MetadataValue::unchecked_from_mut_header_value_ref)
1417    }
1418}
1419
1420// ===== impl Entry =====
1421
1422impl<'a, VE: ValueEncoding> Entry<'a, VE> {
1423    /// Ensures a value is in the entry by inserting the default if empty.
1424    ///
1425    /// Returns a mutable reference to the **first** value in the entry.
1426    ///
1427    /// # Examples
1428    ///
1429    /// ```
1430    /// # use tonic::metadata::*;
1431    /// let mut map: MetadataMap = MetadataMap::default();
1432    ///
1433    /// let keys = &[
1434    ///     "content-length",
1435    ///     "x-hello",
1436    ///     "Content-Length",
1437    ///     "x-world",
1438    /// ];
1439    ///
1440    /// for &key in keys {
1441    ///     let counter = map.entry(key)
1442    ///         .expect("valid key names")
1443    ///         .or_insert("".parse().unwrap());
1444    ///     *counter = format!("{}{}", counter.to_str().unwrap(), "1").parse().unwrap();
1445    /// }
1446    ///
1447    /// assert_eq!(map.get("content-length").unwrap(), "11");
1448    /// assert_eq!(map.get("x-hello").unwrap(), "1");
1449    /// ```
1450    pub fn or_insert(self, default: MetadataValue<VE>) -> &'a mut MetadataValue<VE> {
1451        use self::Entry::*;
1452
1453        match self {
1454            Occupied(e) => e.into_mut(),
1455            Vacant(e) => e.insert(default),
1456        }
1457    }
1458
1459    /// Ensures a value is in the entry by inserting the result of the default
1460    /// function if empty.
1461    ///
1462    /// The default function is not called if the entry exists in the map.
1463    /// Returns a mutable reference to the **first** value in the entry.
1464    ///
1465    /// # Examples
1466    ///
1467    /// Basic usage.
1468    ///
1469    /// ```
1470    /// # use tonic::metadata::*;
1471    /// let mut map = MetadataMap::new();
1472    ///
1473    /// let res = map.entry("x-hello").unwrap()
1474    ///     .or_insert_with(|| "world".parse().unwrap());
1475    ///
1476    /// assert_eq!(res, "world");
1477    /// ```
1478    ///
1479    /// The default function is not called if the entry exists in the map.
1480    ///
1481    /// ```
1482    /// # use tonic::metadata::*;
1483    /// let mut map = MetadataMap::new();
1484    /// map.insert("host", "world".parse().unwrap());
1485    ///
1486    /// let res = map.entry("host")
1487    ///     .expect("host is a valid string")
1488    ///     .or_insert_with(|| unreachable!());
1489    ///
1490    ///
1491    /// assert_eq!(res, "world");
1492    /// ```
1493    pub fn or_insert_with<F: FnOnce() -> MetadataValue<VE>>(
1494        self,
1495        default: F,
1496    ) -> &'a mut MetadataValue<VE> {
1497        use self::Entry::*;
1498
1499        match self {
1500            Occupied(e) => e.into_mut(),
1501            Vacant(e) => e.insert(default()),
1502        }
1503    }
1504
1505    /// Returns a reference to the entry's key
1506    ///
1507    /// # Examples
1508    ///
1509    /// ```
1510    /// # use tonic::metadata::*;
1511    /// let mut map = MetadataMap::new();
1512    ///
1513    /// assert_eq!(map.entry("x-hello").unwrap().key(), "x-hello");
1514    /// ```
1515    pub fn key(&self) -> &MetadataKey<VE> {
1516        use self::Entry::*;
1517
1518        MetadataKey::unchecked_from_header_name_ref(match *self {
1519            Vacant(ref e) => e.inner.key(),
1520            Occupied(ref e) => e.inner.key(),
1521        })
1522    }
1523}
1524
1525// ===== impl VacantEntry =====
1526
1527impl<'a, VE: ValueEncoding> VacantEntry<'a, VE> {
1528    /// Returns a reference to the entry's key
1529    ///
1530    /// # Examples
1531    ///
1532    /// ```
1533    /// # use tonic::metadata::*;
1534    /// let mut map = MetadataMap::new();
1535    ///
1536    /// assert_eq!(map.entry("x-hello").unwrap().key(), "x-hello");
1537    /// ```
1538    pub fn key(&self) -> &MetadataKey<VE> {
1539        MetadataKey::unchecked_from_header_name_ref(self.inner.key())
1540    }
1541
1542    /// Take ownership of the key
1543    ///
1544    /// # Examples
1545    ///
1546    /// ```
1547    /// # use tonic::metadata::*;
1548    /// let mut map = MetadataMap::new();
1549    ///
1550    /// if let Entry::Vacant(v) = map.entry("x-hello").unwrap() {
1551    ///     assert_eq!(v.into_key().as_str(), "x-hello");
1552    /// }
1553    /// ```
1554    pub fn into_key(self) -> MetadataKey<VE> {
1555        MetadataKey::unchecked_from_header_name(self.inner.into_key())
1556    }
1557
1558    /// Insert the value into the entry.
1559    ///
1560    /// The value will be associated with this entry's key. A mutable reference
1561    /// to the inserted value will be returned.
1562    ///
1563    /// # Examples
1564    ///
1565    /// ```
1566    /// # use tonic::metadata::*;
1567    /// let mut map = MetadataMap::new();
1568    ///
1569    /// if let Entry::Vacant(v) = map.entry("x-hello").unwrap() {
1570    ///     v.insert("world".parse().unwrap());
1571    /// }
1572    ///
1573    /// assert_eq!(map.get("x-hello").unwrap(), "world");
1574    /// ```
1575    pub fn insert(self, value: MetadataValue<VE>) -> &'a mut MetadataValue<VE> {
1576        MetadataValue::unchecked_from_mut_header_value_ref(self.inner.insert(value.inner))
1577    }
1578
1579    /// Insert the value into the entry.
1580    ///
1581    /// The value will be associated with this entry's key. The new
1582    /// `OccupiedEntry` is returned, allowing for further manipulation.
1583    ///
1584    /// # Examples
1585    ///
1586    /// ```
1587    /// # use tonic::metadata::*;
1588    /// let mut map = MetadataMap::new();
1589    ///
1590    /// if let Entry::Vacant(v) = map.entry("x-hello").unwrap() {
1591    ///     let mut e = v.insert_entry("world".parse().unwrap());
1592    ///     e.insert("world2".parse().unwrap());
1593    /// }
1594    ///
1595    /// assert_eq!(map.get("x-hello").unwrap(), "world2");
1596    /// ```
1597    pub fn insert_entry(self, value: MetadataValue<VE>) -> OccupiedEntry<'a, Ascii> {
1598        OccupiedEntry {
1599            inner: self.inner.insert_entry(value.inner),
1600            phantom: PhantomData,
1601        }
1602    }
1603}
1604
1605// ===== impl OccupiedEntry =====
1606
1607impl<'a, VE: ValueEncoding> OccupiedEntry<'a, VE> {
1608    /// Returns a reference to the entry's key.
1609    ///
1610    /// # Examples
1611    ///
1612    /// ```
1613    /// # use tonic::metadata::*;
1614    /// let mut map = MetadataMap::new();
1615    /// map.insert("host", "world".parse().unwrap());
1616    ///
1617    /// if let Entry::Occupied(e) = map.entry("host").unwrap() {
1618    ///     assert_eq!("host", e.key());
1619    /// }
1620    /// ```
1621    pub fn key(&self) -> &MetadataKey<VE> {
1622        MetadataKey::unchecked_from_header_name_ref(self.inner.key())
1623    }
1624
1625    /// Get a reference to the first value in the entry.
1626    ///
1627    /// Values are stored in insertion order.
1628    ///
1629    /// # Panics
1630    ///
1631    /// `get` panics if there are no values associated with the entry.
1632    ///
1633    /// # Examples
1634    ///
1635    /// ```
1636    /// # use tonic::metadata::*;
1637    /// let mut map = MetadataMap::new();
1638    /// map.insert("host", "hello.world".parse().unwrap());
1639    ///
1640    /// if let Entry::Occupied(mut e) = map.entry("host").unwrap() {
1641    ///     assert_eq!(e.get(), &"hello.world");
1642    ///
1643    ///     e.append("hello.earth".parse().unwrap());
1644    ///
1645    ///     assert_eq!(e.get(), &"hello.world");
1646    /// }
1647    /// ```
1648    pub fn get(&self) -> &MetadataValue<VE> {
1649        MetadataValue::unchecked_from_header_value_ref(self.inner.get())
1650    }
1651
1652    /// Get a mutable reference to the first value in the entry.
1653    ///
1654    /// Values are stored in insertion order.
1655    ///
1656    /// # Panics
1657    ///
1658    /// `get_mut` panics if there are no values associated with the entry.
1659    ///
1660    /// # Examples
1661    ///
1662    /// ```
1663    /// # use tonic::metadata::*;
1664    /// let mut map = MetadataMap::default();
1665    /// map.insert("host", "hello.world".parse().unwrap());
1666    ///
1667    /// if let Entry::Occupied(mut e) = map.entry("host").unwrap() {
1668    ///     e.get_mut().set_sensitive(true);
1669    ///     assert_eq!(e.get(), &"hello.world");
1670    ///     assert!(e.get().is_sensitive());
1671    /// }
1672    /// ```
1673    pub fn get_mut(&mut self) -> &mut MetadataValue<VE> {
1674        MetadataValue::unchecked_from_mut_header_value_ref(self.inner.get_mut())
1675    }
1676
1677    /// Converts the `OccupiedEntry` into a mutable reference to the **first**
1678    /// value.
1679    ///
1680    /// The lifetime of the returned reference is bound to the original map.
1681    ///
1682    /// # Panics
1683    ///
1684    /// `into_mut` panics if there are no values associated with the entry.
1685    ///
1686    /// # Examples
1687    ///
1688    /// ```
1689    /// # use tonic::metadata::*;
1690    /// let mut map = MetadataMap::default();
1691    /// map.insert("host", "hello.world".parse().unwrap());
1692    /// map.append("host", "hello.earth".parse().unwrap());
1693    ///
1694    /// if let Entry::Occupied(e) = map.entry("host").unwrap() {
1695    ///     e.into_mut().set_sensitive(true);
1696    /// }
1697    ///
1698    /// assert!(map.get("host").unwrap().is_sensitive());
1699    /// ```
1700    pub fn into_mut(self) -> &'a mut MetadataValue<VE> {
1701        MetadataValue::unchecked_from_mut_header_value_ref(self.inner.into_mut())
1702    }
1703
1704    /// Sets the value of the entry.
1705    ///
1706    /// All previous values associated with the entry are removed and the first
1707    /// one is returned. See `insert_mult` for an API that returns all values.
1708    ///
1709    /// # Examples
1710    ///
1711    /// ```
1712    /// # use tonic::metadata::*;
1713    /// let mut map = MetadataMap::new();
1714    /// map.insert("host", "hello.world".parse().unwrap());
1715    ///
1716    /// if let Entry::Occupied(mut e) = map.entry("host").unwrap() {
1717    ///     let mut prev = e.insert("earth".parse().unwrap());
1718    ///     assert_eq!("hello.world", prev);
1719    /// }
1720    ///
1721    /// assert_eq!("earth", map.get("host").unwrap());
1722    /// ```
1723    pub fn insert(&mut self, value: MetadataValue<VE>) -> MetadataValue<VE> {
1724        let header_value = self.inner.insert(value.inner);
1725        MetadataValue::unchecked_from_header_value(header_value)
1726    }
1727
1728    /// Sets the value of the entry.
1729    ///
1730    /// This function does the same as `insert` except it returns an iterator
1731    /// that yields all values previously associated with the key.
1732    ///
1733    /// # Examples
1734    ///
1735    /// ```
1736    /// # use tonic::metadata::*;
1737    /// let mut map = MetadataMap::new();
1738    /// map.insert("host", "world".parse().unwrap());
1739    /// map.append("host", "world2".parse().unwrap());
1740    ///
1741    /// if let Entry::Occupied(mut e) = map.entry("host").unwrap() {
1742    ///     let mut prev = e.insert_mult("earth".parse().unwrap());
1743    ///     assert_eq!("world", prev.next().unwrap());
1744    ///     assert_eq!("world2", prev.next().unwrap());
1745    ///     assert!(prev.next().is_none());
1746    /// }
1747    ///
1748    /// assert_eq!("earth", map.get("host").unwrap());
1749    /// ```
1750    pub fn insert_mult(&mut self, value: MetadataValue<VE>) -> ValueDrain<'_, VE> {
1751        ValueDrain {
1752            inner: self.inner.insert_mult(value.inner),
1753            phantom: PhantomData,
1754        }
1755    }
1756
1757    /// Insert the value into the entry.
1758    ///
1759    /// The new value is appended to the end of the entry's value list. All
1760    /// previous values associated with the entry are retained.
1761    ///
1762    /// # Examples
1763    ///
1764    /// ```
1765    /// # use tonic::metadata::*;
1766    /// let mut map = MetadataMap::new();
1767    /// map.insert("host", "world".parse().unwrap());
1768    ///
1769    /// if let Entry::Occupied(mut e) = map.entry("host").unwrap() {
1770    ///     e.append("earth".parse().unwrap());
1771    /// }
1772    ///
1773    /// let values = map.get_all("host");
1774    /// let mut i = values.iter();
1775    /// assert_eq!("world", *i.next().unwrap());
1776    /// assert_eq!("earth", *i.next().unwrap());
1777    /// ```
1778    pub fn append(&mut self, value: MetadataValue<VE>) {
1779        self.inner.append(value.inner)
1780    }
1781
1782    /// Remove the entry from the map.
1783    ///
1784    /// All values associated with the entry are removed and the first one is
1785    /// returned. See `remove_entry_mult` for an API that returns all values.
1786    ///
1787    /// # Examples
1788    ///
1789    /// ```
1790    /// # use tonic::metadata::*;
1791    /// let mut map = MetadataMap::new();
1792    /// map.insert("host", "world".parse().unwrap());
1793    ///
1794    /// if let Entry::Occupied(e) = map.entry("host").unwrap() {
1795    ///     let mut prev = e.remove();
1796    ///     assert_eq!("world", prev);
1797    /// }
1798    ///
1799    /// assert!(!map.contains_key("host"));
1800    /// ```
1801    pub fn remove(self) -> MetadataValue<VE> {
1802        let value = self.inner.remove();
1803        MetadataValue::unchecked_from_header_value(value)
1804    }
1805
1806    /// Remove the entry from the map.
1807    ///
1808    /// The key and all values associated with the entry are removed and the
1809    /// first one is returned. See `remove_entry_mult` for an API that returns
1810    /// all values.
1811    ///
1812    /// # Examples
1813    ///
1814    /// ```
1815    /// # use tonic::metadata::*;
1816    /// let mut map = MetadataMap::new();
1817    /// map.insert("host", "world".parse().unwrap());
1818    ///
1819    /// if let Entry::Occupied(e) = map.entry("host").unwrap() {
1820    ///     let (key, mut prev) = e.remove_entry();
1821    ///     assert_eq!("host", key.as_str());
1822    ///     assert_eq!("world", prev);
1823    /// }
1824    ///
1825    /// assert!(!map.contains_key("host"));
1826    /// ```
1827    pub fn remove_entry(self) -> (MetadataKey<VE>, MetadataValue<VE>) {
1828        let (name, value) = self.inner.remove_entry();
1829        (
1830            MetadataKey::unchecked_from_header_name(name),
1831            MetadataValue::unchecked_from_header_value(value),
1832        )
1833    }
1834
1835    /// Remove the entry from the map.
1836    ///
1837    /// The key and all values associated with the entry are removed and
1838    /// returned.
1839    pub fn remove_entry_mult(self) -> (MetadataKey<VE>, ValueDrain<'a, VE>) {
1840        let (name, value_drain) = self.inner.remove_entry_mult();
1841        (
1842            MetadataKey::unchecked_from_header_name(name),
1843            ValueDrain {
1844                inner: value_drain,
1845                phantom: PhantomData,
1846            },
1847        )
1848    }
1849
1850    /// Returns an iterator visiting all values associated with the entry.
1851    ///
1852    /// Values are iterated in insertion order.
1853    ///
1854    /// # Examples
1855    ///
1856    /// ```
1857    /// # use tonic::metadata::*;
1858    /// let mut map = MetadataMap::new();
1859    /// map.insert("host", "world".parse().unwrap());
1860    /// map.append("host", "earth".parse().unwrap());
1861    ///
1862    /// if let Entry::Occupied(e) = map.entry("host").unwrap() {
1863    ///     let mut iter = e.iter();
1864    ///     assert_eq!(&"world", iter.next().unwrap());
1865    ///     assert_eq!(&"earth", iter.next().unwrap());
1866    ///     assert!(iter.next().is_none());
1867    /// }
1868    /// ```
1869    pub fn iter(&self) -> ValueIter<'_, VE> {
1870        ValueIter {
1871            inner: Some(self.inner.iter()),
1872            phantom: PhantomData,
1873        }
1874    }
1875
1876    /// Returns an iterator mutably visiting all values associated with the
1877    /// entry.
1878    ///
1879    /// Values are iterated in insertion order.
1880    ///
1881    /// # Examples
1882    ///
1883    /// ```
1884    /// # use tonic::metadata::*;
1885    /// let mut map = MetadataMap::default();
1886    /// map.insert("host", "world".parse().unwrap());
1887    /// map.append("host", "earth".parse().unwrap());
1888    ///
1889    /// if let Entry::Occupied(mut e) = map.entry("host").unwrap() {
1890    ///     for e in e.iter_mut() {
1891    ///         e.set_sensitive(true);
1892    ///     }
1893    /// }
1894    ///
1895    /// let mut values = map.get_all("host");
1896    /// let mut i = values.iter();
1897    /// assert!(i.next().unwrap().is_sensitive());
1898    /// assert!(i.next().unwrap().is_sensitive());
1899    /// ```
1900    pub fn iter_mut(&mut self) -> ValueIterMut<'_, VE> {
1901        ValueIterMut {
1902            inner: self.inner.iter_mut(),
1903            phantom: PhantomData,
1904        }
1905    }
1906}
1907
1908impl<'a, VE: ValueEncoding> IntoIterator for OccupiedEntry<'a, VE>
1909where
1910    VE: 'a,
1911{
1912    type Item = &'a mut MetadataValue<VE>;
1913    type IntoIter = ValueIterMut<'a, VE>;
1914
1915    fn into_iter(self) -> ValueIterMut<'a, VE> {
1916        ValueIterMut {
1917            inner: self.inner.into_iter(),
1918            phantom: PhantomData,
1919        }
1920    }
1921}
1922
1923impl<'a, 'b: 'a, VE: ValueEncoding> IntoIterator for &'b OccupiedEntry<'a, VE> {
1924    type Item = &'a MetadataValue<VE>;
1925    type IntoIter = ValueIter<'a, VE>;
1926
1927    fn into_iter(self) -> ValueIter<'a, VE> {
1928        self.iter()
1929    }
1930}
1931
1932impl<'a, 'b: 'a, VE: ValueEncoding> IntoIterator for &'b mut OccupiedEntry<'a, VE> {
1933    type Item = &'a mut MetadataValue<VE>;
1934    type IntoIter = ValueIterMut<'a, VE>;
1935
1936    fn into_iter(self) -> ValueIterMut<'a, VE> {
1937        self.iter_mut()
1938    }
1939}
1940
1941// ===== impl GetAll =====
1942
1943impl<'a, VE: ValueEncoding> GetAll<'a, VE> {
1944    /// Returns an iterator visiting all values associated with the entry.
1945    ///
1946    /// Values are iterated in insertion order.
1947    ///
1948    /// # Examples
1949    ///
1950    /// ```
1951    /// # use tonic::metadata::*;
1952    /// let mut map = MetadataMap::new();
1953    /// map.insert("x-host", "hello.world".parse().unwrap());
1954    /// map.append("x-host", "hello.earth".parse().unwrap());
1955    ///
1956    /// let values = map.get_all("x-host");
1957    /// let mut iter = values.iter();
1958    /// assert_eq!(&"hello.world", iter.next().unwrap());
1959    /// assert_eq!(&"hello.earth", iter.next().unwrap());
1960    /// assert!(iter.next().is_none());
1961    /// ```
1962    pub fn iter(&self) -> ValueIter<'a, VE> {
1963        ValueIter {
1964            inner: self.inner.as_ref().map(|inner| inner.iter()),
1965            phantom: PhantomData,
1966        }
1967    }
1968}
1969
1970impl<'a, VE: ValueEncoding> PartialEq for GetAll<'a, VE> {
1971    fn eq(&self, other: &Self) -> bool {
1972        self.inner.iter().eq(other.inner.iter())
1973    }
1974}
1975
1976impl<'a, VE: ValueEncoding> IntoIterator for GetAll<'a, VE>
1977where
1978    VE: 'a,
1979{
1980    type Item = &'a MetadataValue<VE>;
1981    type IntoIter = ValueIter<'a, VE>;
1982
1983    fn into_iter(self) -> ValueIter<'a, VE> {
1984        ValueIter {
1985            inner: self.inner.map(|inner| inner.into_iter()),
1986            phantom: PhantomData,
1987        }
1988    }
1989}
1990
1991impl<'a, 'b: 'a, VE: ValueEncoding> IntoIterator for &'b GetAll<'a, VE> {
1992    type Item = &'a MetadataValue<VE>;
1993    type IntoIter = ValueIter<'a, VE>;
1994
1995    fn into_iter(self) -> ValueIter<'a, VE> {
1996        ValueIter {
1997            inner: self.inner.as_ref().map(|inner| inner.into_iter()),
1998            phantom: PhantomData,
1999        }
2000    }
2001}
2002
2003// ===== impl IntoMetadataKey / AsMetadataKey =====
2004
2005mod into_metadata_key {
2006    use super::{MetadataMap, MetadataValue, ValueEncoding};
2007    use crate::metadata::key::MetadataKey;
2008
2009    /// A marker trait used to identify values that can be used as insert keys
2010    /// to a `MetadataMap`.
2011    pub trait IntoMetadataKey<VE: ValueEncoding>: Sealed<VE> {}
2012
2013    // All methods are on this pub(super) trait, instead of `IntoMetadataKey`,
2014    // so that they aren't publicly exposed to the world.
2015    //
2016    // Being on the `IntoMetadataKey` trait would mean users could call
2017    // `"host".insert(&mut map, "localhost")`.
2018    //
2019    // Ultimately, this allows us to adjust the signatures of these methods
2020    // without breaking any external crate.
2021    pub trait Sealed<VE: ValueEncoding> {
2022        #[doc(hidden)]
2023        fn insert(self, map: &mut MetadataMap, val: MetadataValue<VE>)
2024            -> Option<MetadataValue<VE>>;
2025
2026        #[doc(hidden)]
2027        fn append(self, map: &mut MetadataMap, val: MetadataValue<VE>) -> bool;
2028    }
2029
2030    // ==== impls ====
2031
2032    impl<VE: ValueEncoding> Sealed<VE> for MetadataKey<VE> {
2033        #[doc(hidden)]
2034        #[inline]
2035        fn insert(
2036            self,
2037            map: &mut MetadataMap,
2038            val: MetadataValue<VE>,
2039        ) -> Option<MetadataValue<VE>> {
2040            map.headers
2041                .insert(self.inner, val.inner)
2042                .map(MetadataValue::unchecked_from_header_value)
2043        }
2044
2045        #[doc(hidden)]
2046        #[inline]
2047        fn append(self, map: &mut MetadataMap, val: MetadataValue<VE>) -> bool {
2048            map.headers.append(self.inner, val.inner)
2049        }
2050    }
2051
2052    impl<VE: ValueEncoding> IntoMetadataKey<VE> for MetadataKey<VE> {}
2053
2054    impl<'a, VE: ValueEncoding> Sealed<VE> for &'a MetadataKey<VE> {
2055        #[doc(hidden)]
2056        #[inline]
2057        fn insert(
2058            self,
2059            map: &mut MetadataMap,
2060            val: MetadataValue<VE>,
2061        ) -> Option<MetadataValue<VE>> {
2062            map.headers
2063                .insert(&self.inner, val.inner)
2064                .map(MetadataValue::unchecked_from_header_value)
2065        }
2066        #[doc(hidden)]
2067        #[inline]
2068        fn append(self, map: &mut MetadataMap, val: MetadataValue<VE>) -> bool {
2069            map.headers.append(&self.inner, val.inner)
2070        }
2071    }
2072
2073    impl<'a, VE: ValueEncoding> IntoMetadataKey<VE> for &'a MetadataKey<VE> {}
2074
2075    impl<VE: ValueEncoding> Sealed<VE> for &'static str {
2076        #[doc(hidden)]
2077        #[inline]
2078        fn insert(
2079            self,
2080            map: &mut MetadataMap,
2081            val: MetadataValue<VE>,
2082        ) -> Option<MetadataValue<VE>> {
2083            // Perform name validation
2084            let key = MetadataKey::<VE>::from_static(self);
2085
2086            map.headers
2087                .insert(key.inner, val.inner)
2088                .map(MetadataValue::unchecked_from_header_value)
2089        }
2090        #[doc(hidden)]
2091        #[inline]
2092        fn append(self, map: &mut MetadataMap, val: MetadataValue<VE>) -> bool {
2093            // Perform name validation
2094            let key = MetadataKey::<VE>::from_static(self);
2095
2096            map.headers.append(key.inner, val.inner)
2097        }
2098    }
2099
2100    impl<VE: ValueEncoding> IntoMetadataKey<VE> for &'static str {}
2101}
2102
2103mod as_metadata_key {
2104    use super::{MetadataMap, MetadataValue, ValueEncoding};
2105    use crate::metadata::key::{InvalidMetadataKey, MetadataKey};
2106    use http::header::{Entry, GetAll, HeaderValue};
2107
2108    /// A marker trait used to identify values that can be used as search keys
2109    /// to a `MetadataMap`.
2110    pub trait AsMetadataKey<VE: ValueEncoding>: Sealed<VE> {}
2111
2112    // All methods are on this pub(super) trait, instead of `AsMetadataKey`,
2113    // so that they aren't publicly exposed to the world.
2114    //
2115    // Being on the `AsMetadataKey` trait would mean users could call
2116    // `"host".find(&map)`.
2117    //
2118    // Ultimately, this allows us to adjust the signatures of these methods
2119    // without breaking any external crate.
2120    pub trait Sealed<VE: ValueEncoding> {
2121        #[doc(hidden)]
2122        fn get(self, map: &MetadataMap) -> Option<&MetadataValue<VE>>;
2123
2124        #[doc(hidden)]
2125        fn get_mut(self, map: &mut MetadataMap) -> Option<&mut MetadataValue<VE>>;
2126
2127        #[doc(hidden)]
2128        fn get_all(self, map: &MetadataMap) -> Option<GetAll<'_, HeaderValue>>;
2129
2130        #[doc(hidden)]
2131        fn entry(self, map: &mut MetadataMap)
2132            -> Result<Entry<'_, HeaderValue>, InvalidMetadataKey>;
2133
2134        #[doc(hidden)]
2135        fn remove(self, map: &mut MetadataMap) -> Option<MetadataValue<VE>>;
2136    }
2137
2138    // ==== impls ====
2139
2140    impl<VE: ValueEncoding> Sealed<VE> for MetadataKey<VE> {
2141        #[doc(hidden)]
2142        #[inline]
2143        fn get(self, map: &MetadataMap) -> Option<&MetadataValue<VE>> {
2144            map.headers
2145                .get(self.inner)
2146                .map(MetadataValue::unchecked_from_header_value_ref)
2147        }
2148
2149        #[doc(hidden)]
2150        #[inline]
2151        fn get_mut(self, map: &mut MetadataMap) -> Option<&mut MetadataValue<VE>> {
2152            map.headers
2153                .get_mut(self.inner)
2154                .map(MetadataValue::unchecked_from_mut_header_value_ref)
2155        }
2156
2157        #[doc(hidden)]
2158        #[inline]
2159        fn get_all(self, map: &MetadataMap) -> Option<GetAll<'_, HeaderValue>> {
2160            Some(map.headers.get_all(self.inner))
2161        }
2162
2163        #[doc(hidden)]
2164        #[inline]
2165        fn entry(
2166            self,
2167            map: &mut MetadataMap,
2168        ) -> Result<Entry<'_, HeaderValue>, InvalidMetadataKey> {
2169            Ok(map.headers.entry(self.inner))
2170        }
2171
2172        #[doc(hidden)]
2173        #[inline]
2174        fn remove(self, map: &mut MetadataMap) -> Option<MetadataValue<VE>> {
2175            map.headers
2176                .remove(self.inner)
2177                .map(MetadataValue::unchecked_from_header_value)
2178        }
2179    }
2180
2181    impl<VE: ValueEncoding> AsMetadataKey<VE> for MetadataKey<VE> {}
2182
2183    impl<'a, VE: ValueEncoding> Sealed<VE> for &'a MetadataKey<VE> {
2184        #[doc(hidden)]
2185        #[inline]
2186        fn get(self, map: &MetadataMap) -> Option<&MetadataValue<VE>> {
2187            map.headers
2188                .get(&self.inner)
2189                .map(MetadataValue::unchecked_from_header_value_ref)
2190        }
2191
2192        #[doc(hidden)]
2193        #[inline]
2194        fn get_mut(self, map: &mut MetadataMap) -> Option<&mut MetadataValue<VE>> {
2195            map.headers
2196                .get_mut(&self.inner)
2197                .map(MetadataValue::unchecked_from_mut_header_value_ref)
2198        }
2199
2200        #[doc(hidden)]
2201        #[inline]
2202        fn get_all(self, map: &MetadataMap) -> Option<GetAll<'_, HeaderValue>> {
2203            Some(map.headers.get_all(&self.inner))
2204        }
2205
2206        #[doc(hidden)]
2207        #[inline]
2208        fn entry(
2209            self,
2210            map: &mut MetadataMap,
2211        ) -> Result<Entry<'_, HeaderValue>, InvalidMetadataKey> {
2212            Ok(map.headers.entry(&self.inner))
2213        }
2214
2215        #[doc(hidden)]
2216        #[inline]
2217        fn remove(self, map: &mut MetadataMap) -> Option<MetadataValue<VE>> {
2218            map.headers
2219                .remove(&self.inner)
2220                .map(MetadataValue::unchecked_from_header_value)
2221        }
2222    }
2223
2224    impl<'a, VE: ValueEncoding> AsMetadataKey<VE> for &'a MetadataKey<VE> {}
2225
2226    impl<'a, VE: ValueEncoding> Sealed<VE> for &'a str {
2227        #[doc(hidden)]
2228        #[inline]
2229        fn get(self, map: &MetadataMap) -> Option<&MetadataValue<VE>> {
2230            if !VE::is_valid_key(self) {
2231                return None;
2232            }
2233            map.headers
2234                .get(self)
2235                .map(MetadataValue::unchecked_from_header_value_ref)
2236        }
2237
2238        #[doc(hidden)]
2239        #[inline]
2240        fn get_mut(self, map: &mut MetadataMap) -> Option<&mut MetadataValue<VE>> {
2241            if !VE::is_valid_key(self) {
2242                return None;
2243            }
2244            map.headers
2245                .get_mut(self)
2246                .map(MetadataValue::unchecked_from_mut_header_value_ref)
2247        }
2248
2249        #[doc(hidden)]
2250        #[inline]
2251        fn get_all(self, map: &MetadataMap) -> Option<GetAll<'_, HeaderValue>> {
2252            if !VE::is_valid_key(self) {
2253                return None;
2254            }
2255            Some(map.headers.get_all(self))
2256        }
2257
2258        #[doc(hidden)]
2259        #[inline]
2260        fn entry(
2261            self,
2262            map: &mut MetadataMap,
2263        ) -> Result<Entry<'_, HeaderValue>, InvalidMetadataKey> {
2264            if !VE::is_valid_key(self) {
2265                return Err(InvalidMetadataKey::new());
2266            }
2267
2268            let key = http::header::HeaderName::from_bytes(self.as_bytes())
2269                .map_err(|_| InvalidMetadataKey::new())?;
2270            let entry = map.headers.entry(key);
2271            Ok(entry)
2272        }
2273
2274        #[doc(hidden)]
2275        #[inline]
2276        fn remove(self, map: &mut MetadataMap) -> Option<MetadataValue<VE>> {
2277            if !VE::is_valid_key(self) {
2278                return None;
2279            }
2280            map.headers
2281                .remove(self)
2282                .map(MetadataValue::unchecked_from_header_value)
2283        }
2284    }
2285
2286    impl<'a, VE: ValueEncoding> AsMetadataKey<VE> for &'a str {}
2287
2288    impl<VE: ValueEncoding> Sealed<VE> for String {
2289        #[doc(hidden)]
2290        #[inline]
2291        fn get(self, map: &MetadataMap) -> Option<&MetadataValue<VE>> {
2292            if !VE::is_valid_key(self.as_str()) {
2293                return None;
2294            }
2295            map.headers
2296                .get(self.as_str())
2297                .map(MetadataValue::unchecked_from_header_value_ref)
2298        }
2299
2300        #[doc(hidden)]
2301        #[inline]
2302        fn get_mut(self, map: &mut MetadataMap) -> Option<&mut MetadataValue<VE>> {
2303            if !VE::is_valid_key(self.as_str()) {
2304                return None;
2305            }
2306            map.headers
2307                .get_mut(self.as_str())
2308                .map(MetadataValue::unchecked_from_mut_header_value_ref)
2309        }
2310
2311        #[doc(hidden)]
2312        #[inline]
2313        fn get_all(self, map: &MetadataMap) -> Option<GetAll<'_, HeaderValue>> {
2314            if !VE::is_valid_key(self.as_str()) {
2315                return None;
2316            }
2317            Some(map.headers.get_all(self.as_str()))
2318        }
2319
2320        #[doc(hidden)]
2321        #[inline]
2322        fn entry(
2323            self,
2324            map: &mut MetadataMap,
2325        ) -> Result<Entry<'_, HeaderValue>, InvalidMetadataKey> {
2326            if !VE::is_valid_key(self.as_str()) {
2327                return Err(InvalidMetadataKey::new());
2328            }
2329
2330            let key = http::header::HeaderName::from_bytes(self.as_bytes())
2331                .map_err(|_| InvalidMetadataKey::new())?;
2332            Ok(map.headers.entry(key))
2333        }
2334
2335        #[doc(hidden)]
2336        #[inline]
2337        fn remove(self, map: &mut MetadataMap) -> Option<MetadataValue<VE>> {
2338            if !VE::is_valid_key(self.as_str()) {
2339                return None;
2340            }
2341            map.headers
2342                .remove(self.as_str())
2343                .map(MetadataValue::unchecked_from_header_value)
2344        }
2345    }
2346
2347    impl<VE: ValueEncoding> AsMetadataKey<VE> for String {}
2348
2349    impl<'a, VE: ValueEncoding> Sealed<VE> for &'a String {
2350        #[doc(hidden)]
2351        #[inline]
2352        fn get(self, map: &MetadataMap) -> Option<&MetadataValue<VE>> {
2353            if !VE::is_valid_key(self) {
2354                return None;
2355            }
2356            map.headers
2357                .get(self.as_str())
2358                .map(MetadataValue::unchecked_from_header_value_ref)
2359        }
2360
2361        #[doc(hidden)]
2362        #[inline]
2363        fn get_mut(self, map: &mut MetadataMap) -> Option<&mut MetadataValue<VE>> {
2364            if !VE::is_valid_key(self) {
2365                return None;
2366            }
2367            map.headers
2368                .get_mut(self.as_str())
2369                .map(MetadataValue::unchecked_from_mut_header_value_ref)
2370        }
2371
2372        #[doc(hidden)]
2373        #[inline]
2374        fn get_all(self, map: &MetadataMap) -> Option<GetAll<'_, HeaderValue>> {
2375            if !VE::is_valid_key(self) {
2376                return None;
2377            }
2378            Some(map.headers.get_all(self.as_str()))
2379        }
2380
2381        #[doc(hidden)]
2382        #[inline]
2383        fn entry(
2384            self,
2385            map: &mut MetadataMap,
2386        ) -> Result<Entry<'_, HeaderValue>, InvalidMetadataKey> {
2387            if !VE::is_valid_key(self) {
2388                return Err(InvalidMetadataKey::new());
2389            }
2390
2391            let key = http::header::HeaderName::from_bytes(self.as_bytes())
2392                .map_err(|_| InvalidMetadataKey::new())?;
2393            Ok(map.headers.entry(key))
2394        }
2395
2396        #[doc(hidden)]
2397        #[inline]
2398        fn remove(self, map: &mut MetadataMap) -> Option<MetadataValue<VE>> {
2399            if !VE::is_valid_key(self) {
2400                return None;
2401            }
2402            map.headers
2403                .remove(self.as_str())
2404                .map(MetadataValue::unchecked_from_header_value)
2405        }
2406    }
2407
2408    impl<'a, VE: ValueEncoding> AsMetadataKey<VE> for &'a String {}
2409}
2410
2411mod as_encoding_agnostic_metadata_key {
2412    use super::{MetadataMap, ValueEncoding};
2413    use crate::metadata::key::MetadataKey;
2414
2415    /// A marker trait used to identify values that can be used as search keys
2416    /// to a `MetadataMap`, for operations that don't expose the actual value.
2417    pub trait AsEncodingAgnosticMetadataKey: Sealed {}
2418
2419    // All methods are on this pub(super) trait, instead of
2420    // `AsEncodingAgnosticMetadataKey`, so that they aren't publicly exposed to
2421    // the world.
2422    //
2423    // Being on the `AsEncodingAgnosticMetadataKey` trait would mean users could
2424    // call `"host".contains_key(&map)`.
2425    //
2426    // Ultimately, this allows us to adjust the signatures of these methods
2427    // without breaking any external crate.
2428    pub trait Sealed {
2429        #[doc(hidden)]
2430        fn contains_key(&self, map: &MetadataMap) -> bool;
2431    }
2432
2433    // ==== impls ====
2434
2435    impl<VE: ValueEncoding> Sealed for MetadataKey<VE> {
2436        #[doc(hidden)]
2437        #[inline]
2438        fn contains_key(&self, map: &MetadataMap) -> bool {
2439            map.headers.contains_key(&self.inner)
2440        }
2441    }
2442
2443    impl<VE: ValueEncoding> AsEncodingAgnosticMetadataKey for MetadataKey<VE> {}
2444
2445    impl<'a, VE: ValueEncoding> Sealed for &'a MetadataKey<VE> {
2446        #[doc(hidden)]
2447        #[inline]
2448        fn contains_key(&self, map: &MetadataMap) -> bool {
2449            map.headers.contains_key(&self.inner)
2450        }
2451    }
2452
2453    impl<'a, VE: ValueEncoding> AsEncodingAgnosticMetadataKey for &'a MetadataKey<VE> {}
2454
2455    impl<'a> Sealed for &'a str {
2456        #[doc(hidden)]
2457        #[inline]
2458        fn contains_key(&self, map: &MetadataMap) -> bool {
2459            map.headers.contains_key(*self)
2460        }
2461    }
2462
2463    impl<'a> AsEncodingAgnosticMetadataKey for &'a str {}
2464
2465    impl Sealed for String {
2466        #[doc(hidden)]
2467        #[inline]
2468        fn contains_key(&self, map: &MetadataMap) -> bool {
2469            map.headers.contains_key(self.as_str())
2470        }
2471    }
2472
2473    impl AsEncodingAgnosticMetadataKey for String {}
2474
2475    impl<'a> Sealed for &'a String {
2476        #[doc(hidden)]
2477        #[inline]
2478        fn contains_key(&self, map: &MetadataMap) -> bool {
2479            map.headers.contains_key(self.as_str())
2480        }
2481    }
2482
2483    impl<'a> AsEncodingAgnosticMetadataKey for &'a String {}
2484}
2485
2486#[cfg(test)]
2487mod tests {
2488    use super::*;
2489
2490    #[test]
2491    fn test_from_headers_takes_http_headers() {
2492        let mut http_map = http::HeaderMap::new();
2493        http_map.insert("x-host", "example.com".parse().unwrap());
2494
2495        let map = MetadataMap::from_headers(http_map);
2496
2497        assert_eq!(map.get("x-host").unwrap(), "example.com");
2498    }
2499
2500    #[test]
2501    fn test_to_headers_encoding() {
2502        use crate::Status;
2503        let special_char_message = "Beyond ascii \t\n\ršŸŒ¶ļøšŸ’‰šŸ’§šŸ®šŸŗ";
2504        let s1 = Status::unknown(special_char_message);
2505
2506        assert_eq!(s1.message(), special_char_message);
2507
2508        let s1_map = s1.to_header_map().unwrap();
2509        let s2 = Status::from_header_map(&s1_map).unwrap();
2510
2511        assert_eq!(s1.message(), s2.message());
2512    }
2513
2514    #[test]
2515    fn test_iter_categorizes_ascii_entries() {
2516        let mut map = MetadataMap::new();
2517
2518        map.insert("x-word", "hello".parse().unwrap());
2519        map.append_bin("x-word-bin", MetadataValue::from_bytes(b"goodbye"));
2520        map.insert_bin("x-number-bin", MetadataValue::from_bytes(b"123"));
2521
2522        let mut found_x_word = false;
2523        for key_and_value in map.iter() {
2524            if let KeyAndValueRef::Ascii(key, _value) = key_and_value {
2525                if key.as_str() == "x-word" {
2526                    found_x_word = true;
2527                } else {
2528                    panic!("Unexpected key");
2529                }
2530            }
2531        }
2532        assert!(found_x_word);
2533    }
2534
2535    #[test]
2536    fn test_iter_categorizes_binary_entries() {
2537        let mut map = MetadataMap::new();
2538
2539        map.insert("x-word", "hello".parse().unwrap());
2540        map.append_bin("x-word-bin", MetadataValue::from_bytes(b"goodbye"));
2541
2542        let mut found_x_word_bin = false;
2543        for key_and_value in map.iter() {
2544            if let KeyAndValueRef::Binary(key, _value) = key_and_value {
2545                if key.as_str() == "x-word-bin" {
2546                    found_x_word_bin = true;
2547                } else {
2548                    panic!("Unexpected key");
2549                }
2550            }
2551        }
2552        assert!(found_x_word_bin);
2553    }
2554
2555    #[test]
2556    fn test_iter_mut_categorizes_ascii_entries() {
2557        let mut map = MetadataMap::new();
2558
2559        map.insert("x-word", "hello".parse().unwrap());
2560        map.append_bin("x-word-bin", MetadataValue::from_bytes(b"goodbye"));
2561        map.insert_bin("x-number-bin", MetadataValue::from_bytes(b"123"));
2562
2563        let mut found_x_word = false;
2564        for key_and_value in map.iter_mut() {
2565            if let KeyAndMutValueRef::Ascii(key, _value) = key_and_value {
2566                if key.as_str() == "x-word" {
2567                    found_x_word = true;
2568                } else {
2569                    panic!("Unexpected key");
2570                }
2571            }
2572        }
2573        assert!(found_x_word);
2574    }
2575
2576    #[test]
2577    fn test_iter_mut_categorizes_binary_entries() {
2578        let mut map = MetadataMap::new();
2579
2580        map.insert("x-word", "hello".parse().unwrap());
2581        map.append_bin("x-word-bin", MetadataValue::from_bytes(b"goodbye"));
2582
2583        let mut found_x_word_bin = false;
2584        for key_and_value in map.iter_mut() {
2585            if let KeyAndMutValueRef::Binary(key, _value) = key_and_value {
2586                if key.as_str() == "x-word-bin" {
2587                    found_x_word_bin = true;
2588                } else {
2589                    panic!("Unexpected key");
2590                }
2591            }
2592        }
2593        assert!(found_x_word_bin);
2594    }
2595
2596    #[test]
2597    fn test_keys_categorizes_ascii_entries() {
2598        let mut map = MetadataMap::new();
2599
2600        map.insert("x-word", "hello".parse().unwrap());
2601        map.append_bin("x-word-bin", MetadataValue::from_bytes(b"goodbye"));
2602        map.insert_bin("x-number-bin", MetadataValue::from_bytes(b"123"));
2603
2604        let mut found_x_word = false;
2605        for key in map.keys() {
2606            if let KeyRef::Ascii(key) = key {
2607                if key.as_str() == "x-word" {
2608                    found_x_word = true;
2609                } else {
2610                    panic!("Unexpected key");
2611                }
2612            }
2613        }
2614        assert!(found_x_word);
2615    }
2616
2617    #[test]
2618    fn test_keys_categorizes_binary_entries() {
2619        let mut map = MetadataMap::new();
2620
2621        map.insert("x-word", "hello".parse().unwrap());
2622        map.insert_bin("x-number-bin", MetadataValue::from_bytes(b"123"));
2623
2624        let mut found_x_number_bin = false;
2625        for key in map.keys() {
2626            if let KeyRef::Binary(key) = key {
2627                if key.as_str() == "x-number-bin" {
2628                    found_x_number_bin = true;
2629                } else {
2630                    panic!("Unexpected key");
2631                }
2632            }
2633        }
2634        assert!(found_x_number_bin);
2635    }
2636
2637    #[test]
2638    fn test_values_categorizes_ascii_entries() {
2639        let mut map = MetadataMap::new();
2640
2641        map.insert("x-word", "hello".parse().unwrap());
2642        map.append_bin("x-word-bin", MetadataValue::from_bytes(b"goodbye"));
2643        map.insert_bin("x-number-bin", MetadataValue::from_bytes(b"123"));
2644
2645        let mut found_x_word = false;
2646        for value in map.values() {
2647            if let ValueRef::Ascii(value) = value {
2648                if *value == "hello" {
2649                    found_x_word = true;
2650                } else {
2651                    panic!("Unexpected key");
2652                }
2653            }
2654        }
2655        assert!(found_x_word);
2656    }
2657
2658    #[test]
2659    fn test_values_categorizes_binary_entries() {
2660        let mut map = MetadataMap::new();
2661
2662        map.insert("x-word", "hello".parse().unwrap());
2663        map.append_bin("x-word-bin", MetadataValue::from_bytes(b"goodbye"));
2664
2665        let mut found_x_word_bin = false;
2666        for value_ref in map.values() {
2667            if let ValueRef::Binary(value) = value_ref {
2668                assert_eq!(*value, "goodbye");
2669                found_x_word_bin = true;
2670            }
2671        }
2672        assert!(found_x_word_bin);
2673    }
2674
2675    #[test]
2676    fn test_values_mut_categorizes_ascii_entries() {
2677        let mut map = MetadataMap::new();
2678
2679        map.insert("x-word", "hello".parse().unwrap());
2680        map.append_bin("x-word-bin", MetadataValue::from_bytes(b"goodbye"));
2681        map.insert_bin("x-number-bin", MetadataValue::from_bytes(b"123"));
2682
2683        let mut found_x_word = false;
2684        for value_ref in map.values_mut() {
2685            if let ValueRefMut::Ascii(value) = value_ref {
2686                assert_eq!(*value, "hello");
2687                found_x_word = true;
2688            }
2689        }
2690        assert!(found_x_word);
2691    }
2692
2693    #[test]
2694    fn test_values_mut_categorizes_binary_entries() {
2695        let mut map = MetadataMap::new();
2696
2697        map.insert("x-word", "hello".parse().unwrap());
2698        map.append_bin("x-word-bin", MetadataValue::from_bytes(b"goodbye"));
2699
2700        let mut found_x_word_bin = false;
2701        for value in map.values_mut() {
2702            if let ValueRefMut::Binary(value) = value {
2703                assert_eq!(*value, "goodbye");
2704                found_x_word_bin = true;
2705            }
2706        }
2707        assert!(found_x_word_bin);
2708    }
2709
2710    #[allow(dead_code)]
2711    fn value_drain_is_send_sync() {
2712        fn is_send_sync<T: Send + Sync>() {}
2713
2714        is_send_sync::<Iter<'_>>();
2715        is_send_sync::<IterMut<'_>>();
2716
2717        is_send_sync::<ValueDrain<'_, Ascii>>();
2718        is_send_sync::<ValueDrain<'_, Binary>>();
2719
2720        is_send_sync::<ValueIterMut<'_, Ascii>>();
2721        is_send_sync::<ValueIterMut<'_, Binary>>();
2722    }
2723}