Skip to content

Commit

Permalink
Replace time with httpdate
Browse files Browse the repository at this point in the history
quodlibetor authored and seanmonstar committed Sep 17, 2021

Verified

This commit was signed with the committer’s verified signature.
andris9 Andris Reinman
1 parent 2d9a5c4 commit 4bf199f
Showing 3 changed files with 29 additions and 51 deletions.
2 changes: 1 addition & 1 deletion Cargo.toml
Original file line number Diff line number Diff line change
@@ -24,7 +24,7 @@ bitflags = "1.0"
bytes = "1"
mime = "0.3.14"
sha-1 = "0.9"
time = "0.1.34"
httpdate = "1"

[features]
nightly = []
2 changes: 1 addition & 1 deletion src/lib.rs
Original file line number Diff line number Diff line change
@@ -78,11 +78,11 @@ extern crate bitflags;
extern crate bytes;
extern crate headers_core;
extern crate http;
extern crate httpdate;
extern crate mime;
extern crate sha1;
#[cfg(all(test, feature = "nightly"))]
extern crate test;
extern crate time;

pub use headers_core::{Error, Header};

76 changes: 27 additions & 49 deletions src/util/http_date.rs
Original file line number Diff line number Diff line change
@@ -1,10 +1,10 @@
use std::fmt;
use std::str::FromStr;
use std::time::{Duration, SystemTime, UNIX_EPOCH};
use std::time::SystemTime;

use bytes::Bytes;
use http::header::HeaderValue;
use time;
use httpdate;

use super::IterExt;

@@ -32,7 +32,7 @@ use super::IterExt;
// HTTP-date, the sender MUST generate those timestamps in the
// IMF-fixdate format.
#[derive(Clone, Copy, PartialEq, Eq, PartialOrd, Ord, Hash)]
pub(crate) struct HttpDate(time::Tm);
pub(crate) struct HttpDate(httpdate::HttpDate);

impl HttpDate {
pub(crate) fn from_val(val: &HeaderValue) -> Option<Self> {
@@ -74,96 +74,74 @@ impl<'a> From<&'a HttpDate> for HeaderValue {
impl FromStr for HttpDate {
type Err = Error;
fn from_str(s: &str) -> Result<HttpDate, Error> {
time::strptime(s, "%a, %d %b %Y %T %Z")
.or_else(|_| time::strptime(s, "%A, %d-%b-%y %T %Z"))
.or_else(|_| time::strptime(s, "%c"))
.map(HttpDate)
.map_err(|_| Error(()))
Ok(HttpDate(s.parse().map_err(|_| Error(()))?))
}
}

impl fmt::Debug for HttpDate {
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
fmt::Display::fmt(&self.0.to_utc().rfc822(), f)
fmt::Display::fmt(&self.0, f)
}
}

impl fmt::Display for HttpDate {
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
fmt::Display::fmt(&self.0.to_utc().rfc822(), f)
fmt::Display::fmt(&self.0, f)
}
}

impl From<SystemTime> for HttpDate {
fn from(sys: SystemTime) -> HttpDate {
let tmspec = match sys.duration_since(UNIX_EPOCH) {
Ok(dur) => {
// subsec nanos always dropped
time::Timespec::new(dur.as_secs() as i64, 0)
}
Err(err) => {
let neg = err.duration();
// subsec nanos always dropped
time::Timespec::new(-(neg.as_secs() as i64), 0)
}
};
HttpDate(time::at_utc(tmspec))
HttpDate(sys.into())
}
}

impl From<HttpDate> for SystemTime {
fn from(date: HttpDate) -> SystemTime {
let spec = date.0.to_timespec();
if spec.sec >= 0 {
UNIX_EPOCH + Duration::new(spec.sec as u64, spec.nsec as u32)
} else {
UNIX_EPOCH - Duration::new(spec.sec as u64, spec.nsec as u32)
}
SystemTime::from(date.0)
}
}

#[cfg(test)]
mod tests {
use super::HttpDate;
use time::Tm;

const NOV_07: HttpDate = HttpDate(Tm {
tm_nsec: 0,
tm_sec: 37,
tm_min: 48,
tm_hour: 8,
tm_mday: 7,
tm_mon: 10,
tm_year: 94,
tm_wday: 0,
tm_isdst: 0,
tm_yday: 0,
tm_utcoff: 0,
});

use std::time::{Duration, UNIX_EPOCH};

// The old tests had Sunday, but 1994-11-07 is a Monday.
// See https://github.com/pyfisch/httpdate/pull/6#issuecomment-846881001
fn nov_07() -> HttpDate {
HttpDate((UNIX_EPOCH + Duration::new(784198117, 0)).into())
}

#[test]
fn test_display_is_imf_fixdate() {
assert_eq!("Mon, 07 Nov 1994 08:48:37 GMT", &nov_07().to_string());
}

#[test]
fn test_imf_fixdate() {
assert_eq!(
"Sun, 07 Nov 1994 08:48:37 GMT".parse::<HttpDate>().unwrap(),
NOV_07
"Mon, 07 Nov 1994 08:48:37 GMT".parse::<HttpDate>().unwrap(),
nov_07()
);
}

#[test]
fn test_rfc_850() {
assert_eq!(
"Sunday, 07-Nov-94 08:48:37 GMT"
"Monday, 07-Nov-94 08:48:37 GMT"
.parse::<HttpDate>()
.unwrap(),
NOV_07
nov_07()
);
}

#[test]
fn test_asctime() {
assert_eq!(
"Sun Nov 7 08:48:37 1994".parse::<HttpDate>().unwrap(),
NOV_07
"Mon Nov 7 08:48:37 1994".parse::<HttpDate>().unwrap(),
nov_07()
);
}

0 comments on commit 4bf199f

Please sign in to comment.