Skip to main content

volo_grpc/metadata/
map.rs

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