<commit_before>//! Headers container, and common header fields.
//!
//! hyper has the opinion that Headers should be strongly-typed, because that's
//! why we're using Rust in the first place. To set or get any header, an object
//! must implement the `Header` trait from this module. Several common headers
//! are already provided, such as `Host`, `ContentType`, `UserAgent`, and others.
//!
//! # Why Typed?
//!
//! Or, why not stringly-typed? Types give the following advantages:
//!
//! - More difficult to typo, since typos in types should be caught by the compiler
//! - Parsing to a proper type by default
//!
//! # Defining Custom Headers
//!
//! Hyper provides many of the most commonly used headers in HTTP. If
//! you need to define a custom header, it's easy to do while still taking
//! advantage of the type system. Hyper includes a `header!` macro for defining
//! many wrapper-style headers.
//!
//! ```
//! #[macro_use] extern crate hyper;
//! use hyper::header::Headers;
//! header! { (XRequestGuid, "X-Request-Guid") => [String] }
//!
//! fn main () {
//!     let mut headers = Headers::new();
//!
//!     headers.set(XRequestGuid("a proper guid".to_owned()))
//! }
//! ```
//!
//! This works well for simple "string" headers.  If you need more control,
//! you can implement the trait directly.
//!
//! ## Implementing the `Header` trait
//!
//! Consider a Do Not Track header. It can be true or false, but it represents
//! that via the numerals `1` and `0`.
//!
//! ```
//! use std::fmt;
//! use hyper::header::{self, Header, Raw};
//!
//! #[derive(Debug, Clone, Copy)]
//! struct Dnt(bool);
//!
//! impl Header for Dnt {
//!     fn header_name() -> &'static str {
//!         "DNT"
//!     }
//!
//!     fn parse_header(raw: &Raw) -> hyper::Result<Dnt> {
//!         if raw.len() == 1 {
//!             let line = &raw[0];
//!             if line.len() == 1 {
//!                 let byte = line[0];
//!                 match byte {
//!                     b'0' => return Ok(Dnt(true)),
//!                     b'1' => return Ok(Dnt(false)),
//!                     _ => ()
//!                 }
//!             }
//!         }
//!         Err(hyper::Error::Header)
//!     }
//!
//!     fn fmt_header(&self, f: &mut header::Formatter) -> fmt::Result {
//!         let value = if self.0 {
//!             "1"
//!         } else {
//!             "0"
//!         };
//!         f.fmt_line(&value)
//!     }
//! }
//! ```
use std::borrow::{Cow, ToOwned};
use std::iter::{FromIterator, IntoIterator};
use std::{mem, fmt};

use unicase::Ascii;

use self::internals::{Item, VecMap, Entry};
use self::sealed::{GetType, HeaderClone};

pub use self::shared::*;
pub use self::common::*;
pub use self::raw::Raw;
use bytes::Bytes;

mod common;
mod internals;
mod raw;
mod shared;
pub mod parsing;


/// A trait for any object that will represent a header field and value.
///
/// This trait represents the construction and identification of headers,
/// and contains trait-object unsafe methods.
pub trait Header: HeaderClone + GetType + Send + Sync {
    /// Returns the name of the header field this belongs to.
    ///
    /// This will become an associated constant once available.
    fn header_name() -> &'static str where Self: Sized;
    /// Parse a header from a raw stream of bytes.
    ///
    /// It's possible that a request can include a header field more than once,
    /// and in that case, the slice will have a length greater than 1. However,
    /// it's not necessarily the case that a Header is *allowed* to have more
    /// than one field value. If that's the case, you **should** return `None`
    /// if `raw.len() > 1`.
    fn parse_header(raw: &Raw) -> ::Result<Self> where Self: Sized;
    /// Format a header to outgoing stream.
    ///
    /// Most headers should be formatted on one line, and so a common pattern
    /// would be to implement `std::fmt::Display` for this type as well, and
    /// then just call `f.fmt_line(self)`.
    ///
    /// ## Note
    ///
    /// This has the ability to format a header over multiple lines.
    ///
    /// The main example here is `Set-Cookie`, which requires that every
    /// cookie being set be specified in a separate line. Almost every other
    /// case should only format as 1 single line.
    #[inline]
    fn fmt_header(&self, f: &mut Formatter) -> fmt::Result;
}

mod sealed {
    use std::any::{Any, TypeId};
    use super::Header;

    #[doc(hidden)]
    pub trait GetType: Any {
        #[inline(always)]
        fn get_type(&self) -> TypeId {
            TypeId::of::<Self>()
        }
    }

    impl<T: Any> GetType for T {}

    #[doc(hidden)]
    pub trait HeaderClone {
        fn clone_box(&self) -> Box<Header + Send + Sync>;
    }

    impl<T: Header + Clone> HeaderClone for T {
        #[inline]
        fn clone_box(&self) -> Box<Header + Send + Sync> {
            Box::new(self.clone())
        }
    }

    #[test]
    fn test_get_type() {
        use ::header::{ContentLength, UserAgent};

        let len = ContentLength(5);
        let agent = UserAgent::new("hyper");

        assert_eq!(TypeId::of::<ContentLength>(), len.get_type());
        assert_eq!(TypeId::of::<UserAgent>(), agent.get_type());

        let len: Box<Header + Send + Sync> = Box::new(len);
        let agent: Box<Header + Send + Sync> = Box::new(agent);

        assert_eq!(TypeId::of::<ContentLength>(), (*len).get_type());
        assert_eq!(TypeId::of::<UserAgent>(), (*agent).get_type());
    }
}


/// A formatter used to serialize headers to an output stream.
#[allow(missing_debug_implementations)]
pub struct Formatter<'a, 'b: 'a>(Multi<'a, 'b>);

enum Multi<'a, 'b: 'a> {<commit_msg>refactor(header): remove GetType trait<commit_after>//! Headers container, and common header fields.
//!
//! hyper has the opinion that Headers should be strongly-typed, because that's
//! why we're using Rust in the first place. To set or get any header, an object
//! must implement the `Header` trait from this module. Several common headers
//! are already provided, such as `Host`, `ContentType`, `UserAgent`, and others.
//!
//! # Why Typed?
//!
//! Or, why not stringly-typed? Types give the following advantages:
//!
//! - More difficult to typo, since typos in types should be caught by the compiler
//! - Parsing to a proper type by default
//!
//! # Defining Custom Headers
//!
//! Hyper provides many of the most commonly used headers in HTTP. If
//! you need to define a custom header, it's easy to do while still taking
//! advantage of the type system. Hyper includes a `header!` macro for defining
//! many wrapper-style headers.
//!
//! ```
//! #[macro_use] extern crate hyper;
//! use hyper::header::Headers;
//! header! { (XRequestGuid, "X-Request-Guid") => [String] }
//!
//! fn main () {
//!     let mut headers = Headers::new();
//!
//!     headers.set(XRequestGuid("a proper guid".to_owned()))
//! }
//! ```
//!
//! This works well for simple "string" headers.  If you need more control,
//! you can implement the trait directly.
//!
//! ## Implementing the `Header` trait
//!
//! Consider a Do Not Track header. It can be true or false, but it represents
//! that via the numerals `1` and `0`.
//!
//! ```
//! use std::fmt;
//! use hyper::header::{self, Header, Raw};
//!
//! #[derive(Debug, Clone, Copy)]
//! struct Dnt(bool);
//!
//! impl Header for Dnt {
//!     fn header_name() -> &'static str {
//!         "DNT"
//!     }
//!
//!     fn parse_header(raw: &Raw) -> hyper::Result<Dnt> {
//!         if raw.len() == 1 {
//!             let line = &raw[0];
//!             if line.len() == 1 {
//!                 let byte = line[0];
//!                 match byte {
//!                     b'0' => return Ok(Dnt(true)),
//!                     b'1' => return Ok(Dnt(false)),
//!                     _ => ()
//!                 }
//!             }
//!         }
//!         Err(hyper::Error::Header)
//!     }
//!
//!     fn fmt_header(&self, f: &mut header::Formatter) -> fmt::Result {
//!         let value = if self.0 {
//!             "1"
//!         } else {
//!             "0"
//!         };
//!         f.fmt_line(&value)
//!     }
//! }
//! ```
use std::borrow::{Cow, ToOwned};
use std::iter::{FromIterator, IntoIterator};
use std::{mem, fmt};

use unicase::Ascii;

use self::internals::{Item, VecMap, Entry};
use self::sealed::HeaderClone;

pub use self::shared::*;
pub use self::common::*;
pub use self::raw::Raw;
use bytes::Bytes;

mod common;
mod internals;
mod raw;
mod shared;
pub mod parsing;


/// A trait for any object that will represent a header field and value.
///
/// This trait represents the construction and identification of headers,
/// and contains trait-object unsafe methods.
pub trait Header: 'static + HeaderClone + Send + Sync {
    /// Returns the name of the header field this belongs to.
    ///
    /// This will become an associated constant once available.
    fn header_name() -> &'static str where Self: Sized;
    /// Parse a header from a raw stream of bytes.
    ///
    /// It's possible that a request can include a header field more than once,
    /// and in that case, the slice will have a length greater than 1. However,
    /// it's not necessarily the case that a Header is *allowed* to have more
    /// than one field value. If that's the case, you **should** return `None`
    /// if `raw.len() > 1`.
    fn parse_header(raw: &Raw) -> ::Result<Self> where Self: Sized;
    /// Format a header to outgoing stream.
    ///
    /// Most headers should be formatted on one line, and so a common pattern
    /// would be to implement `std::fmt::Display` for this type as well, and
    /// then just call `f.fmt_line(self)`.
    ///
    /// ## Note
    ///
    /// This has the ability to format a header over multiple lines.
    ///
    /// The main example here is `Set-Cookie`, which requires that every
    /// cookie being set be specified in a separate line. Almost every other
    /// case should only format as 1 single line.
    #[inline]
    fn fmt_header(&self, f: &mut Formatter) -> fmt::Result;
}

mod sealed {
    use super::Header;

    #[doc(hidden)]
    pub trait HeaderClone {
        fn clone_box(&self) -> Box<Header + Send + Sync>;
    }

    impl<T: Header + Clone> HeaderClone for T {
        #[inline]
        fn clone_box(&self) -> Box<Header + Send + Sync> {
            Box::new(self.clone())
        }
    }
}


/// A formatter used to serialize headers to an output stream.
#[allow(missing_debug_implementations)]
pub struct Formatter<'a, 'b: 'a>(Multi<'a, 'b>);

enum Multi<'a, 'b: 'a> {
{'fraction_non_alphanumeric': 0.1666351606805293, 'fraction_numerical': 0.0027410207939508506, 'mean_word_length': 2.338908172925213, 'pattern_counts': {'":': 0, '<': 27, '<?xml version=': 0, '>': 54, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '7512204', 'n_tokens_mistral': 3281, 'n_tokens_neox': 3126, 'n_words': 1158}