#![allow(clippy::upper_case_acronyms)]

use super::encoding::{
    Ascii, Binary, InvalidMetadataValue, InvalidMetadataValueBytes, ValueEncoding,
};
use super::key::MetadataKey;

use bytes::Bytes;
use http::header::HeaderValue;
use std::error::Error;
use std::hash::{Hash, Hasher};
use std::marker::PhantomData;
use std::str::FromStr;
use std::{cmp, fmt};

/// Represents a custom metadata field value.
///
/// `MetadataValue` is used as the [`MetadataMap`] value.
///
/// [`HeaderMap`]: struct.HeaderMap.html
/// [`MetadataMap`]: struct.MetadataMap.html
#[derive(Clone)]
#[repr(transparent)]
pub struct MetadataValue<VE: ValueEncoding> {
    // Note: There are unsafe transmutes that assume that the memory layout
    // of MetadataValue is identical to HeaderValue
    pub(crate) inner: HeaderValue,
    phantom: PhantomData<VE>,
}

/// A possible error when converting a `MetadataValue` to a string representation.
///
/// Metadata field values may contain opaque bytes, in which case it is not
/// possible to represent the value as a string.
#[derive(Debug)]
pub struct ToStrError {
    _priv: (),
}

/// An ascii metadata value.
pub type AsciiMetadataValue = MetadataValue<Ascii>;
/// A binary metadata value.
pub type BinaryMetadataValue = MetadataValue<Binary>;

impl<VE: ValueEncoding> MetadataValue<VE> {
    /// Convert a static string to a `MetadataValue`.
    ///
    /// This function will not perform any copying, however the string is
    /// checked to ensure that no invalid characters are present.
    ///
    /// For Ascii values, only visible ASCII characters (32-127) are permitted.
    /// For Binary values, the string must be valid base64.
    ///
    /// # Panics
    ///
    /// This function panics if the argument contains invalid metadata value
    /// characters.
    ///
    /// # Examples
    ///
    /// ```
    /// # use tonic::metadata::*;
    /// let val = AsciiMetadataValue::from_static("hello");
    /// assert_eq!(val, "hello");
    /// ```
    ///
    /// ```
    /// # use tonic::metadata::*;
    /// let val = BinaryMetadataValue::from_static("SGVsbG8hIQ==");
    /// assert_eq!(val, "Hello!!");
    /// ```
    #[inline]
    pub fn from_static(src: &'static str) -> Self {
        MetadataValue {
            inner: VE::from_static(src),
            phantom: PhantomData,
        }
    }

    /// Convert a `Bytes` directly into a `MetadataValue` without validating.
    /// For `MetadataValue<Binary>` the provided parameter must be base64
    /// encoded without padding bytes at the end.
    ///
    /// # Safety
    ///
    /// This function does NOT validate that illegal bytes are not contained
    /// within the buffer.
    #[inline]
    pub unsafe fn from_shared_unchecked(src: Bytes) -> Self {
        MetadataValue {
            inner: HeaderValue::from_maybe_shared_unchecked(src),
            phantom: PhantomData,
        }
    }

    /// Returns true if the `MetadataValue` has a length of zero bytes.
    ///
    /// # Examples
    ///
    /// ```
    /// # use tonic::metadata::*;
    /// let val = AsciiMetadataValue::from_static("");
    /// assert!(val.is_empty());
    ///
    /// let val = AsciiMetadataValue::from_static("hello");
    /// assert!(!val.is_empty());
    /// ```
    #[inline]
    pub fn is_empty(&self) -> bool {
        VE::is_empty(self.inner.as_bytes())
    }

    /// Converts a `MetadataValue` to a Bytes buffer. This method cannot
    /// fail for Ascii values. For Ascii values, `as_bytes` is more convenient
    /// to use.
    ///
    /// # Examples
    ///
    /// ```
    /// # use tonic::metadata::*;
    /// let val = AsciiMetadataValue::from_static("hello");
    /// assert_eq!(val.to_bytes().unwrap().as_ref(), b"hello");
    /// ```
    ///
    /// ```
    /// # use tonic::metadata::*;
    /// let val = BinaryMetadataValue::from_bytes(b"hello");
    /// assert_eq!(val.to_bytes().unwrap().as_ref(), b"hello");
    /// ```
    #[inline]
    pub fn to_bytes(&self) -> Result<Bytes, InvalidMetadataValueBytes> {
        VE::decode(self.inner.as_bytes())
    }

    /// Mark that the metadata value represents sensitive information.
    ///
    /// # Examples
    ///
    /// ```
    /// # use tonic::metadata::*;
    /// let mut val = AsciiMetadataValue::from_static("my secret");
    ///
    /// val.set_sensitive(true);
    /// assert!(val.is_sensitive());
    ///
    /// val.set_sensitive(false);
    /// assert!(!val.is_sensitive());
    /// ```
    #[inline]
    pub fn set_sensitive(&mut self, val: bool) {
        self.inner.set_sensitive(val);
    }

    /// Returns `true` if the value represents sensitive data.
    ///
    /// Sensitive data could represent passwords or other data that should not
    /// be stored on disk or in memory. This setting can be used by components
    /// like caches to avoid storing the value. HPACK encoders must set the
    /// metadata field to never index when `is_sensitive` returns true.
    ///
    /// Note that sensitivity is not factored into equality or ordering.
    ///
    /// # Examples
    ///
    /// ```
    /// # use tonic::metadata::*;
    /// let mut val = AsciiMetadataValue::from_static("my secret");
    ///
    /// val.set_sensitive(true);
    /// assert!(val.is_sensitive());
    ///
    /// val.set_sensitive(false);
    /// assert!(!val.is_sensitive());
    /// ```
    #[inline]
    pub fn is_sensitive(&self) -> bool {
        self.inner.is_sensitive()
    }

    /// Converts a `MetadataValue` to a byte slice. For Binary values, the
    /// return value is base64 encoded.
    ///
    /// # Examples
    ///
    /// ```
    /// # use tonic::metadata::*;
    /// let val = AsciiMetadataValue::from_static("hello");
    /// assert_eq!(val.as_encoded_bytes(), b"hello");
    /// ```
    ///
    /// ```
    /// # use tonic::metadata::*;
    /// let val = BinaryMetadataValue::from_bytes(b"Hello!");
    /// assert_eq!(val.as_encoded_bytes(), b"SGVsbG8h");
    /// ```
    #[inline]
    pub fn as_encoded_bytes(&self) -> &[u8] {
        self.inner.as_bytes()
    }

    /// Converts a HeaderValue to a MetadataValue. This method assumes that the
    /// caller has made sure that the value is of the correct Ascii or Binary
    /// value encoding.
    #[inline]
    pub(crate) fn unchecked_from_header_value(value: HeaderValue) -> Self {
        MetadataValue {
            inner: value,
            phantom: PhantomData,
        }
    }

    /// Converts a HeaderValue reference to a MetadataValue. This method assumes
    /// that the caller has made sure that the value is of the correct Ascii or
    /// Binary value encoding.
    #[inline]
    pub(crate) fn unchecked_from_header_value_ref(header_value: &HeaderValue) -> &Self {
        unsafe { &*(header_value as *const HeaderValue as *const Self) }
    }

    /// Converts a HeaderValue reference to a MetadataValue. This method assumes
    /// that the caller has made sure that the value is of the correct Ascii or
    /// Binary value encoding.
    #[inline]
    pub(crate) fn unchecked_from_mut_header_value_ref(header_value: &mut HeaderValue) -> &mut Self {
        unsafe { &mut *(header_value as *mut HeaderValue as *mut Self) }
    }
}

/// Attempt to convert a byte slice to a `MetadataValue`.
///
/// For Ascii metadata values, If the argument contains invalid metadata
/// value bytes, an error is returned. Only byte values between 32 and 255
/// (inclusive) are permitted, excluding byte 127 (DEL).
///
/// For Binary metadata values this method cannot fail. See also the Binary
/// only version of this method `from_bytes`.
///
/// # Examples
///
/// ```
/// # use tonic::metadata::*;
/// let val = AsciiMetadataValue::try_from(b"hello\xfa").unwrap();
/// assert_eq!(val, &b"hello\xfa"[..]);
/// ```
///
/// An invalid value
///
/// ```
/// # use tonic::metadata::*;
/// let val = AsciiMetadataValue::try_from(b"\n");
/// assert!(val.is_err());
/// ```
impl<'a, VE: ValueEncoding> TryFrom<&'a [u8]> for MetadataValue<VE> {
    type Error = InvalidMetadataValueBytes;

    #[inline]
    fn try_from(src: &[u8]) -> Result<Self, Self::Error> {
        VE::from_bytes(src).map(|value| MetadataValue {
            inner: value,
            phantom: PhantomData,
        })
    }
}

/// Attempt to convert a byte slice to a `MetadataValue`.
///
/// For Ascii metadata values, If the argument contains invalid metadata
/// value bytes, an error is returned. Only byte values between 32 and 255
/// (inclusive) are permitted, excluding byte 127 (DEL).
///
/// For Binary metadata values this method cannot fail. See also the Binary
/// only version of this method `from_bytes`.
///
/// # Examples
///
/// ```
/// # use tonic::metadata::*;
/// let val = AsciiMetadataValue::try_from(b"hello\xfa").unwrap();
/// assert_eq!(val, &b"hello\xfa"[..]);
/// ```
///
/// An invalid value
///
/// ```
/// # use tonic::metadata::*;
/// let val = AsciiMetadataValue::try_from(b"\n");
/// assert!(val.is_err());
/// ```
impl<'a, VE: ValueEncoding, const N: usize> TryFrom<&'a [u8; N]> for MetadataValue<VE> {
    type Error = InvalidMetadataValueBytes;

    #[inline]
    fn try_from(src: &[u8; N]) -> Result<Self, Self::Error> {
        Self::try_from(src.as_ref())
    }
}

/// Attempt to convert a `Bytes` buffer to a `MetadataValue`.
///
/// For `MetadataValue<Ascii>`, if the argument contains invalid metadata
/// value bytes, an error is returned. Only byte values between 32 and 255
/// (inclusive) are permitted, excluding byte 127 (DEL).
///
/// For `MetadataValue<Binary>`, if the argument is not valid base64, an
/// error is returned. In use cases where the input is not base64 encoded,
/// use `from_bytes`; if the value has to be encoded it's not possible to
/// share the memory anyways.
impl<VE: ValueEncoding> TryFrom<Bytes> for MetadataValue<VE> {
    type Error = InvalidMetadataValueBytes;

    #[inline]
    fn try_from(src: Bytes) -> Result<Self, Self::Error> {
        VE::from_shared(src).map(|value| MetadataValue {
            inner: value,
            phantom: PhantomData,
        })
    }
}

/// Attempt to convert a Vec of bytes to a `MetadataValue`.
///
/// For `MetadataValue<Ascii>`, if the argument contains invalid metadata
/// value bytes, an error is returned. Only byte values between 32 and 255
/// (inclusive) are permitted, excluding byte 127 (DEL).
///
/// For `MetadataValue<Binary>`, if the argument is not valid base64, an
/// error is returned. In use cases where the input is not base64 encoded,
/// use `from_bytes`; if the value has to be encoded it's not possible to
/// share the memory anyways.
impl<VE: ValueEncoding> TryFrom<Vec<u8>> for MetadataValue<VE> {
    type Error = InvalidMetadataValueBytes;

    #[inline]
    fn try_from(src: Vec<u8>) -> Result<Self, Self::Error> {
        Self::try_from(src.as_slice())
    }
}

/// Attempt to convert a string to a `MetadataValue<Ascii>`.
///
/// If the argument contains invalid metadata value characters, an error is
/// returned. Only visible ASCII characters (32-127) are permitted. Use
/// `from_bytes` to create a `MetadataValue` that includes opaque octets
/// (128-255).
impl<'a> TryFrom<&'a str> for MetadataValue<Ascii> {
    type Error = InvalidMetadataValue;

    #[inline]
    fn try_from(s: &'a str) -> Result<Self, Self::Error> {
        s.parse()
    }
}

/// Attempt to convert a string to a `MetadataValue<Ascii>`.
///
/// If the argument contains invalid metadata value characters, an error is
/// returned. Only visible ASCII characters (32-127) are permitted. Use
/// `from_bytes` to create a `MetadataValue` that includes opaque octets
/// (128-255).
impl<'a> TryFrom<&'a String> for MetadataValue<Ascii> {
    type Error = InvalidMetadataValue;

    #[inline]
    fn try_from(s: &'a String) -> Result<Self, Self::Error> {
        s.parse()
    }
}

/// Attempt to convert a string to a `MetadataValue<Ascii>`.
///
/// If the argument contains invalid metadata value characters, an error is
/// returned. Only visible ASCII characters (32-127) are permitted. Use
/// `from_bytes` to create a `MetadataValue` that includes opaque octets
/// (128-255).
impl TryFrom<String> for MetadataValue<Ascii> {
    type Error = InvalidMetadataValue;

    #[inline]
    fn try_from(s: String) -> Result<Self, Self::Error> {
        s.parse()
    }
}

// is_empty is defined in the generic impl block above
#[allow(clippy::len_without_is_empty)]
impl MetadataValue<Ascii> {
    /// Converts a MetadataKey into a `MetadataValue<Ascii>`.
    ///
    /// Since every valid MetadataKey is a valid MetadataValue this is done
    /// infallibly.
    ///
    /// # Examples
    ///
    /// ```
    /// # use tonic::metadata::*;
    /// let val = AsciiMetadataValue::from_key::<Ascii>("accept".parse().unwrap());
    /// assert_eq!(val, AsciiMetadataValue::try_from(b"accept").unwrap());
    /// ```
    #[inline]
    pub fn from_key<KeyVE: ValueEncoding>(key: MetadataKey<KeyVE>) -> Self {
        key.into()
    }

    /// Returns the length of `self`, in bytes.
    ///
    /// This method is not available for `MetadataValue<Binary>` because that
    /// cannot be implemented in constant time, which most people would probably
    /// expect. To get the length of `MetadataValue<Binary>`, convert it to a
    /// Bytes value and measure its length.
    ///
    /// # Examples
    ///
    /// ```
    /// # use tonic::metadata::*;
    /// let val = AsciiMetadataValue::from_static("hello");
    /// assert_eq!(val.len(), 5);
    /// ```
    #[inline]
    pub fn len(&self) -> usize {
        self.inner.len()
    }

    /// Yields a `&str` slice if the `MetadataValue` only contains visible ASCII
    /// chars.
    ///
    /// This function will perform a scan of the metadata value, checking all the
    /// characters.
    ///
    /// # Examples
    ///
    /// ```
    /// # use tonic::metadata::*;
    /// let val = AsciiMetadataValue::from_static("hello");
    /// assert_eq!(val.to_str().unwrap(), "hello");
    /// ```
    pub fn to_str(&self) -> Result<&str, ToStrError> {
        self.inner.to_str().map_err(|_| ToStrError::new())
    }

    /// Converts a `MetadataValue` to a byte slice. For Binary values, use
    /// `to_bytes`.
    ///
    /// # Examples
    ///
    /// ```
    /// # use tonic::metadata::*;
    /// let val = AsciiMetadataValue::from_static("hello");
    /// assert_eq!(val.as_bytes(), b"hello");
    /// ```
    #[inline]
    pub fn as_bytes(&self) -> &[u8] {
        self.inner.as_bytes()
    }
}

impl MetadataValue<Binary> {
    /// Convert a byte slice to a `MetadataValue<Binary>`.
    ///
    /// # Examples
    ///
    /// ```
    /// # use tonic::metadata::*;
    /// let val = BinaryMetadataValue::from_bytes(b"hello\xfa");
    /// assert_eq!(val, &b"hello\xfa"[..]);
    /// ```
    #[inline]
    pub fn from_bytes(src: &[u8]) -> Self {
        // Only the Ascii version of try_from can fail.
        Self::try_from(src).unwrap()
    }
}

impl<VE: ValueEncoding> AsRef<[u8]> for MetadataValue<VE> {
    #[inline]
    fn as_ref(&self) -> &[u8] {
        self.inner.as_ref()
    }
}

impl<VE: ValueEncoding> fmt::Debug for MetadataValue<VE> {
    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
        VE::fmt(&self.inner, f)
    }
}

impl<KeyVE: ValueEncoding> From<MetadataKey<KeyVE>> for MetadataValue<Ascii> {
    #[inline]
    fn from(h: MetadataKey<KeyVE>) -> MetadataValue<Ascii> {
        MetadataValue {
            inner: h.inner.into(),
            phantom: PhantomData,
        }
    }
}

macro_rules! from_integers {
    ($($name:ident: $t:ident => $max_len:expr),*) => {$(
        impl From<$t> for MetadataValue<Ascii> {
            fn from(num: $t) -> MetadataValue<Ascii> {
                MetadataValue {
                    inner: HeaderValue::from(num),
                    phantom: PhantomData,
                }
            }
        }

        #[test]
        fn $name() {
            let n: $t = 55;
            let val = AsciiMetadataValue::from(n);
            assert_eq!(val, &n.to_string());

            let n = ::std::$t::MAX;
            let val = AsciiMetadataValue::from(n);
            assert_eq!(val, &n.to_string());
        }
    )*};
}

from_integers! {
    // integer type => maximum decimal length

    // u8 purposely left off... AsciiMetadataValue::from(b'3') could be confusing
    from_u16: u16 => 5,
    from_i16: i16 => 6,
    from_u32: u32 => 10,
    from_i32: i32 => 11,
    from_u64: u64 => 20,
    from_i64: i64 => 20
}

#[cfg(target_pointer_width = "16")]
from_integers! {
    from_usize: usize => 5,
    from_isize: isize => 6
}

#[cfg(target_pointer_width = "32")]
from_integers! {
    from_usize: usize => 10,
    from_isize: isize => 11
}

#[cfg(target_pointer_width = "64")]
from_integers! {
    from_usize: usize => 20,
    from_isize: isize => 20
}

#[cfg(test)]
mod from_metadata_value_tests {
    use super::*;
    use crate::metadata::map::MetadataMap;

    #[test]
    fn it_can_insert_metadata_key_as_metadata_value() {
        let mut map = MetadataMap::new();
        map.insert(
            "accept",
            MetadataKey::<Ascii>::from_bytes(b"hello-world")
                .unwrap()
                .into(),
        );

        assert_eq!(
            map.get("accept").unwrap(),
            AsciiMetadataValue::try_from(b"hello-world").unwrap()
        );
    }
}

impl FromStr for MetadataValue<Ascii> {
    type Err = InvalidMetadataValue;

    #[inline]
    fn from_str(s: &str) -> Result<MetadataValue<Ascii>, Self::Err> {
        HeaderValue::from_str(s)
            .map(|value| MetadataValue {
                inner: value,
                phantom: PhantomData,
            })
            .map_err(|_| InvalidMetadataValue::new())
    }
}

impl<VE: ValueEncoding> From<MetadataValue<VE>> for Bytes {
    #[inline]
    fn from(value: MetadataValue<VE>) -> Bytes {
        Bytes::copy_from_slice(value.inner.as_bytes())
    }
}

impl<'a, VE: ValueEncoding> From<&'a MetadataValue<VE>> for MetadataValue<VE> {
    #[inline]
    fn from(t: &'a MetadataValue<VE>) -> Self {
        t.clone()
    }
}

// ===== ToStrError =====

impl ToStrError {
    pub(crate) fn new() -> Self {
        ToStrError { _priv: () }
    }
}

impl fmt::Display for ToStrError {
    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
        f.write_str("failed to convert metadata to a str")
    }
}

impl Error for ToStrError {}

impl Hash for MetadataValue<Ascii> {
    fn hash<H: Hasher>(&self, state: &mut H) {
        self.inner.hash(state)
    }
}

impl Hash for MetadataValue<Binary> {
    fn hash<H: Hasher>(&self, state: &mut H) {
        match self.to_bytes() {
            Ok(b) => b.hash(state),
            Err(e) => e.hash(state),
        }
    }
}

// ===== PartialEq / PartialOrd =====

impl<VE: ValueEncoding> PartialEq for MetadataValue<VE> {
    #[inline]
    fn eq(&self, other: &MetadataValue<VE>) -> bool {
        // Note: Different binary strings that after base64 decoding
        // will count as the same value for Binary values. Also,
        // different invalid base64 values count as equal for Binary
        // values.
        VE::values_equal(&self.inner, &other.inner)
    }
}

impl<VE: ValueEncoding> Eq for MetadataValue<VE> {}

impl<VE: ValueEncoding> PartialOrd for MetadataValue<VE> {
    #[inline]
    fn partial_cmp(&self, other: &MetadataValue<VE>) -> Option<cmp::Ordering> {
        Some(self.cmp(other))
    }
}

impl<VE: ValueEncoding> Ord for MetadataValue<VE> {
    #[inline]
    fn cmp(&self, other: &Self) -> cmp::Ordering {
        self.inner.cmp(&other.inner)
    }
}

impl<VE: ValueEncoding> PartialEq<str> for MetadataValue<VE> {
    #[inline]
    fn eq(&self, other: &str) -> bool {
        VE::equals(&self.inner, other.as_bytes())
    }
}

impl<VE: ValueEncoding> PartialEq<[u8]> for MetadataValue<VE> {
    #[inline]
    fn eq(&self, other: &[u8]) -> bool {
        VE::equals(&self.inner, other)
    }
}

impl<VE: ValueEncoding> PartialOrd<str> for MetadataValue<VE> {
    #[inline]
    fn partial_cmp(&self, other: &str) -> Option<cmp::Ordering> {
        self.inner.partial_cmp(other.as_bytes())
    }
}

impl<VE: ValueEncoding> PartialOrd<[u8]> for MetadataValue<VE> {
    #[inline]
    fn partial_cmp(&self, other: &[u8]) -> Option<cmp::Ordering> {
        self.inner.partial_cmp(other)
    }
}

impl<VE: ValueEncoding> PartialEq<MetadataValue<VE>> for str {
    #[inline]
    fn eq(&self, other: &MetadataValue<VE>) -> bool {
        *other == *self
    }
}

impl<VE: ValueEncoding> PartialEq<MetadataValue<VE>> for [u8] {
    #[inline]
    fn eq(&self, other: &MetadataValue<VE>) -> bool {
        *other == *self
    }
}

impl<VE: ValueEncoding> PartialOrd<MetadataValue<VE>> for str {
    #[inline]
    fn partial_cmp(&self, other: &MetadataValue<VE>) -> Option<cmp::Ordering> {
        self.as_bytes().partial_cmp(other.inner.as_bytes())
    }
}

impl<VE: ValueEncoding> PartialOrd<MetadataValue<VE>> for [u8] {
    #[inline]
    fn partial_cmp(&self, other: &MetadataValue<VE>) -> Option<cmp::Ordering> {
        self.partial_cmp(other.inner.as_bytes())
    }
}

impl<VE: ValueEncoding> PartialEq<String> for MetadataValue<VE> {
    #[inline]
    fn eq(&self, other: &String) -> bool {
        *self == other[..]
    }
}

impl<VE: ValueEncoding> PartialOrd<String> for MetadataValue<VE> {
    #[inline]
    fn partial_cmp(&self, other: &String) -> Option<cmp::Ordering> {
        self.inner.partial_cmp(other.as_bytes())
    }
}

impl<VE: ValueEncoding> PartialEq<MetadataValue<VE>> for String {
    #[inline]
    fn eq(&self, other: &MetadataValue<VE>) -> bool {
        *other == *self
    }
}

impl<VE: ValueEncoding> PartialOrd<MetadataValue<VE>> for String {
    #[inline]
    fn partial_cmp(&self, other: &MetadataValue<VE>) -> Option<cmp::Ordering> {
        self.as_bytes().partial_cmp(other.inner.as_bytes())
    }
}

impl<'a, VE: ValueEncoding> PartialEq<MetadataValue<VE>> for &'a MetadataValue<VE> {
    #[inline]
    fn eq(&self, other: &MetadataValue<VE>) -> bool {
        **self == *other
    }
}

impl<'a, VE: ValueEncoding> PartialOrd<MetadataValue<VE>> for &'a MetadataValue<VE> {
    #[inline]
    fn partial_cmp(&self, other: &MetadataValue<VE>) -> Option<cmp::Ordering> {
        (**self).partial_cmp(other)
    }
}

impl<'a, VE: ValueEncoding, T: ?Sized> PartialEq<&'a T> for MetadataValue<VE>
where
    MetadataValue<VE>: PartialEq<T>,
{
    #[inline]
    fn eq(&self, other: &&'a T) -> bool {
        *self == **other
    }
}

impl<'a, VE: ValueEncoding, T: ?Sized> PartialOrd<&'a T> for MetadataValue<VE>
where
    MetadataValue<VE>: PartialOrd<T>,
{
    #[inline]
    fn partial_cmp(&self, other: &&'a T) -> Option<cmp::Ordering> {
        self.partial_cmp(*other)
    }
}

impl<'a, VE: ValueEncoding> PartialEq<MetadataValue<VE>> for &'a str {
    #[inline]
    fn eq(&self, other: &MetadataValue<VE>) -> bool {
        *other == *self
    }
}

impl<'a, VE: ValueEncoding> PartialOrd<MetadataValue<VE>> for &'a str {
    #[inline]
    fn partial_cmp(&self, other: &MetadataValue<VE>) -> Option<cmp::Ordering> {
        self.as_bytes().partial_cmp(other.inner.as_bytes())
    }
}

#[test]
fn test_debug() {
    let cases = &[
        ("hello", "\"hello\""),
        ("hello \"world\"", "\"hello \\\"world\\\"\""),
        ("\u{7FFF}hello", "\"\\xe7\\xbf\\xbfhello\""),
    ];

    for &(value, expected) in cases {
        let val = AsciiMetadataValue::try_from(value.as_bytes()).unwrap();
        let actual = format!("{:?}", val);
        assert_eq!(expected, actual);
    }

    let mut sensitive = AsciiMetadataValue::from_static("password");
    sensitive.set_sensitive(true);
    assert_eq!("Sensitive", format!("{:?}", sensitive));
}

#[test]
fn test_is_empty() {
    fn from_str<VE: ValueEncoding>(s: &str) -> MetadataValue<VE> {
        MetadataValue::<VE>::unchecked_from_header_value(s.parse().unwrap())
    }

    assert!(from_str::<Ascii>("").is_empty());
    assert!(from_str::<Binary>("").is_empty());
    assert!(!from_str::<Ascii>("a").is_empty());
    assert!(!from_str::<Binary>("a").is_empty());
    assert!(!from_str::<Ascii>("=").is_empty());
    assert!(from_str::<Binary>("=").is_empty());
    assert!(!from_str::<Ascii>("===").is_empty());
    assert!(from_str::<Binary>("===").is_empty());
    assert!(!from_str::<Ascii>("=====").is_empty());
    assert!(from_str::<Binary>("=====").is_empty());
}

#[test]
fn test_from_shared_base64_encodes() {
    let value = BinaryMetadataValue::try_from(Bytes::from_static(b"Hello")).unwrap();
    assert_eq!(value.as_encoded_bytes(), b"SGVsbG8");
}

#[test]
fn test_value_eq_value() {
    type BMV = BinaryMetadataValue;
    type AMV = AsciiMetadataValue;

    assert_eq!(AMV::from_static("abc"), AMV::from_static("abc"));
    assert_ne!(AMV::from_static("abc"), AMV::from_static("ABC"));

    assert_eq!(BMV::from_bytes(b"abc"), BMV::from_bytes(b"abc"));
    assert_ne!(BMV::from_bytes(b"abc"), BMV::from_bytes(b"ABC"));

    // Padding is ignored.
    assert_eq!(
        BMV::from_static("SGVsbG8hIQ=="),
        BMV::from_static("SGVsbG8hIQ")
    );
    // Invalid values are all just invalid from this point of view.
    unsafe {
        assert_eq!(
            BMV::from_shared_unchecked(Bytes::from_static(b"..{}")),
            BMV::from_shared_unchecked(Bytes::from_static(b"{}.."))
        );
    }
}

#[test]
fn test_value_eq_str() {
    type BMV = BinaryMetadataValue;
    type AMV = AsciiMetadataValue;

    assert_eq!(AMV::from_static("abc"), "abc");
    assert_ne!(AMV::from_static("abc"), "ABC");
    assert_eq!("abc", AMV::from_static("abc"));
    assert_ne!("ABC", AMV::from_static("abc"));

    assert_eq!(BMV::from_bytes(b"abc"), "abc");
    assert_ne!(BMV::from_bytes(b"abc"), "ABC");
    assert_eq!("abc", BMV::from_bytes(b"abc"));
    assert_ne!("ABC", BMV::from_bytes(b"abc"));

    // Padding is ignored.
    assert_eq!(BMV::from_static("SGVsbG8hIQ=="), "Hello!!");
    assert_eq!("Hello!!", BMV::from_static("SGVsbG8hIQ=="));
}

#[test]
fn test_value_eq_bytes() {
    type BMV = BinaryMetadataValue;
    type AMV = AsciiMetadataValue;

    assert_eq!(AMV::from_static("abc"), "abc".as_bytes());
    assert_ne!(AMV::from_static("abc"), "ABC".as_bytes());
    assert_eq!(*"abc".as_bytes(), AMV::from_static("abc"));
    assert_ne!(*"ABC".as_bytes(), AMV::from_static("abc"));

    assert_eq!(*"abc".as_bytes(), BMV::from_bytes(b"abc"));
    assert_ne!(*"ABC".as_bytes(), BMV::from_bytes(b"abc"));

    // Padding is ignored.
    assert_eq!(BMV::from_static("SGVsbG8hIQ=="), "Hello!!".as_bytes());
    assert_eq!(*"Hello!!".as_bytes(), BMV::from_static("SGVsbG8hIQ=="));
}

#[test]
fn test_ascii_value_hash() {
    use std::collections::hash_map::DefaultHasher;
    type AMV = AsciiMetadataValue;

    fn hash(value: AMV) -> u64 {
        let mut hasher = DefaultHasher::new();
        value.hash(&mut hasher);
        hasher.finish()
    }

    let value1 = AMV::from_static("abc");
    let value2 = AMV::from_static("abc");
    assert_eq!(value1, value2);
    assert_eq!(hash(value1), hash(value2));

    let value1 = AMV::from_static("abc");
    let value2 = AMV::from_static("xyz");

    assert_ne!(value1, value2);
    assert_ne!(hash(value1), hash(value2));
}

#[test]
fn test_valid_binary_value_hash() {
    use std::collections::hash_map::DefaultHasher;
    type BMV = BinaryMetadataValue;

    fn hash(value: BMV) -> u64 {
        let mut hasher = DefaultHasher::new();
        value.hash(&mut hasher);
        hasher.finish()
    }

    let value1 = BMV::from_bytes(b"abc");
    let value2 = BMV::from_bytes(b"abc");
    assert_eq!(value1, value2);
    assert_eq!(hash(value1), hash(value2));

    let value1 = BMV::from_bytes(b"abc");
    let value2 = BMV::from_bytes(b"xyz");
    assert_ne!(value1, value2);
    assert_ne!(hash(value1), hash(value2));
}

#[test]
fn test_invalid_binary_value_hash() {
    use std::collections::hash_map::DefaultHasher;
    type BMV = BinaryMetadataValue;

    fn hash(value: BMV) -> u64 {
        let mut hasher = DefaultHasher::new();
        value.hash(&mut hasher);
        hasher.finish()
    }

    unsafe {
        let value1 = BMV::from_shared_unchecked(Bytes::from_static(b"..{}"));
        let value2 = BMV::from_shared_unchecked(Bytes::from_static(b"{}.."));
        assert_eq!(value1, value2);
        assert_eq!(hash(value1), hash(value2));
    }

    unsafe {
        let valid = BMV::from_bytes(b"abc");
        let invalid = BMV::from_shared_unchecked(Bytes::from_static(b"{}.."));
        assert_ne!(valid, invalid);
        assert_ne!(hash(valid), hash(invalid));
    }
}
