diff --git a/src/header.rs b/src/header.rs index 1834929b6c..478bb6dac7 100644 --- a/src/header.rs +++ b/src/header.rs @@ -10,14 +10,13 @@ //! Several header fields use MIME values for their contents. Keeping with the //! strongly-typed theme, the [mime](http://seanmonstar.github.io/mime.rs) crate //! is used, such as `ContentType(pub Mime)`. -use std::any::Any; use std::ascii::OwnedAsciiExt; use std::char::is_lowercase; use std::fmt::{mod, Show}; use std::from_str::{FromStr, from_str}; use std::mem::{transmute, transmute_copy}; use std::raw::TraitObject; -use std::str::from_utf8; +use std::str::{from_utf8, SendStr, Slice, Owned}; use std::string::raw; use std::collections::hashmap::{HashMap, Entries}; @@ -28,7 +27,7 @@ use rfc7230::read_header; use {HttpResult}; /// A trait for any object that will represent a header field and value. -pub trait Header: Any + 'static { +pub trait Header: 'static { /// Returns the name of the header field this belongs to. /// /// The market `Option` is to hint to the type system which implementation @@ -71,7 +70,7 @@ fn header_name() -> &'static str { /// A map of header fields on requests and responses. pub struct Headers { - data: HashMap<&'static str, Item> + data: HashMap } impl Headers { @@ -94,8 +93,7 @@ impl Headers { let name = unsafe { raw::from_utf8(name) }.into_ascii_lower(); - let name: &'static str = unsafe { transmute(name.as_slice()) }; - match headers.data.find_or_insert(name, Raw(vec![])) { + match headers.data.find_or_insert(Owned(name), Raw(vec![])) { &Raw(ref mut pieces) => pieces.push(value), // at this point, Raw is the only thing that has been inserted _ => unreachable!() @@ -111,7 +109,7 @@ impl Headers { /// /// The field is determined by the type of the value being set. pub fn set(&mut self, value: H) { - self.data.insert(header_name::(), Typed(box value)); + self.data.insert(Slice(header_name::()), Typed(box value)); } /// Get a clone of the header field's value, if it exists. @@ -129,7 +127,7 @@ impl Headers { /// Get a reference to the header field's value, if it exists. pub fn get_ref(&mut self) -> Option<&H> { - self.data.find_mut(&header_name::()).and_then(|item| { + self.data.find_mut(&Slice(header_name::())).and_then(|item| { debug!("get_ref, name={}, val={}", header_name::(), item); let header = match *item { Raw(ref raw) => match Header::parse_header(raw.as_slice()) { @@ -167,12 +165,13 @@ impl Headers { /// let has_type = headers.has::(); /// ``` pub fn has(&self) -> bool { - self.data.contains_key(&header_name::()) + self.data.contains_key(&Slice(header_name::())) } - /// Removes a header from the map, if one existed. Returns true if a header has been removed. + /// Removes a header from the map, if one existed. + /// Returns true if a header has been removed. pub fn remove(&mut self) -> bool { - self.data.remove(&Header::header_name(None::)) + self.data.pop_equiv(&Header::header_name(None::)).is_some() } /// Returns an iterator over the header fields. @@ -195,13 +194,13 @@ impl fmt::Show for Headers { /// An `Iterator` over the fields in a `Headers` map. pub struct HeadersItems<'a> { - inner: Entries<'a, &'static str, Item> + inner: Entries<'a, SendStr, Item> } -impl<'a> Iterator<(&'a &'static str, HeaderView<'a>)> for HeadersItems<'a> { - fn next(&mut self) -> Option<(&'a &'static str, HeaderView<'a>)> { +impl<'a> Iterator<(&'a str, HeaderView<'a>)> for HeadersItems<'a> { + fn next(&mut self) -> Option<(&'a str, HeaderView<'a>)> { match self.inner.next() { - Some((k, v)) => Some((k, HeaderView(v))), + Some((k, v)) => Some((k.as_slice(), HeaderView(v))), None => None } }