1- use crate :: Exception ;
21use std:: fmt:: { self , Display , Formatter } ;
32use std:: str:: { from_utf8, FromStr } ;
43use std:: time:: { Duration , SystemTime , UNIX_EPOCH } ;
54
5+ use http_types:: { Error , ErrorKind , StatusCode } ;
6+
67const IMF_FIXDATE_LENGTH : usize = 29 ;
78const RFC850_MAX_LENGTH : usize = 23 ;
89const ASCTIME_LENGTH : usize = 24 ;
@@ -37,7 +38,7 @@ pub struct HttpDate {
3738/// Supports the preferred IMF-fixdate and the legacy RFC 805 and
3839/// ascdate formats. Two digit years are mapped to dates between
3940/// 1970 and 2069.
40- pub ( crate ) fn parse_http_date ( s : & str ) -> Result < SystemTime , Exception > {
41+ pub ( crate ) fn parse_http_date ( s : & str ) -> Result < SystemTime , Error > {
4142 s. parse :: < HttpDate > ( ) . map ( |d| d. into ( ) )
4243}
4344
@@ -64,15 +65,19 @@ impl HttpDate {
6465 }
6566}
6667
67- fn parse_imf_fixdate ( s : & [ u8 ] ) -> Result < HttpDate , Exception > {
68+ fn err ( msg : & ' static str ) -> Error {
69+ Error :: from_str ( ErrorKind :: InvalidData , msg, StatusCode :: BadRequest )
70+ }
71+
72+ fn parse_imf_fixdate ( s : & [ u8 ] ) -> Result < HttpDate , Error > {
6873 // Example: `Sun, 06 Nov 1994 08:49:37 GMT`
6974 if s. len ( ) != IMF_FIXDATE_LENGTH
7075 || & s[ 25 ..] != b" GMT"
7176 || s[ 16 ] != b' '
7277 || s[ 19 ] != b':'
7378 || s[ 22 ] != b':'
7479 {
75- return Err ( "Date time not in imf fixdate format" . into ( ) ) ;
80+ return Err ( err ( "Date time not in imf fixdate format" ) ) ;
7681 }
7782 Ok ( HttpDate {
7883 second : from_utf8 ( & s[ 23 ..25 ] ) ?. parse ( ) ?,
@@ -92,7 +97,7 @@ fn parse_imf_fixdate(s: &[u8]) -> Result<HttpDate, Exception> {
9297 b" Oct " => 10 ,
9398 b" Nov " => 11 ,
9499 b" Dec " => 12 ,
95- _ => return Err ( "Invalid Month" . into ( ) ) ,
100+ _ => return Err ( err ( "Invalid Month" ) ) ,
96101 } ,
97102 year : from_utf8 ( & s[ 12 ..16 ] ) ?. parse ( ) ?,
98103 week_day : match & s[ ..5 ] {
@@ -103,15 +108,15 @@ fn parse_imf_fixdate(s: &[u8]) -> Result<HttpDate, Exception> {
103108 b"Fri, " => 5 ,
104109 b"Sat, " => 6 ,
105110 b"Sun, " => 7 ,
106- _ => return Err ( "Invalid Day" . into ( ) ) ,
111+ _ => return Err ( err ( "Invalid Day" ) ) ,
107112 } ,
108113 } )
109114}
110115
111- fn parse_rfc850_date ( s : & [ u8 ] ) -> Result < HttpDate , Exception > {
116+ fn parse_rfc850_date ( s : & [ u8 ] ) -> Result < HttpDate , Error > {
112117 // Example: `Sunday, 06-Nov-94 08:49:37 GMT`
113118 if s. len ( ) < RFC850_MAX_LENGTH {
114- return Err ( "Date time not in rfc850 format" . into ( ) ) ;
119+ return Err ( err ( "Date time not in rfc850 format" ) ) ;
115120 }
116121
117122 fn week_day < ' a > ( s : & ' a [ u8 ] , week_day : u8 , name : & ' static [ u8 ] ) -> Option < ( u8 , & ' a [ u8 ] ) > {
@@ -127,9 +132,9 @@ fn parse_rfc850_date(s: &[u8]) -> Result<HttpDate, Exception> {
127132 . or_else ( || week_day ( s, 5 , b"Friday, " ) )
128133 . or_else ( || week_day ( s, 6 , b"Saturday, " ) )
129134 . or_else ( || week_day ( s, 7 , b"Sunday, " ) )
130- . ok_or :: < & ' static str > ( "Invalid day" ) ?;
135+ . ok_or_else ( || err ( "Invalid day" ) ) ?;
131136 if s. len ( ) != 22 || s[ 12 ] != b':' || s[ 15 ] != b':' || & s[ 18 ..22 ] != b" GMT" {
132- return Err ( "Date time not in rfc850 format" . into ( ) ) ;
137+ return Err ( err ( "Date time not in rfc850 format" ) ) ;
133138 }
134139 let mut year = from_utf8 ( & s[ 7 ..9 ] ) ?. parse :: < u16 > ( ) ?;
135140 if year < 70 {
@@ -155,18 +160,18 @@ fn parse_rfc850_date(s: &[u8]) -> Result<HttpDate, Exception> {
155160 b"-Oct-" => 10 ,
156161 b"-Nov-" => 11 ,
157162 b"-Dec-" => 12 ,
158- _ => return Err ( "Invalid month" . into ( ) ) ,
163+ _ => return Err ( err ( "Invalid month" ) ) ,
159164 } ,
160165 year : year,
161166 week_day : week_day,
162167 } )
163168}
164169
165- fn parse_asctime ( s : & [ u8 ] ) -> Result < HttpDate , Exception > {
170+ fn parse_asctime ( s : & [ u8 ] ) -> Result < HttpDate , Error > {
166171 // Example: `Sun Nov 6 08:49:37 1994`
167172 if s. len ( ) != ASCTIME_LENGTH || s[ 10 ] != b' ' || s[ 13 ] != b':' || s[ 16 ] != b':' || s[ 19 ] != b' '
168173 {
169- return Err ( "Date time not in asctime format" . into ( ) ) ;
174+ return Err ( err ( "Date time not in asctime format" ) ) ;
170175 }
171176 Ok ( HttpDate {
172177 second : from_utf8 ( & s[ 17 ..19 ] ) ?. parse ( ) ?,
@@ -189,7 +194,7 @@ fn parse_asctime(s: &[u8]) -> Result<HttpDate, Exception> {
189194 b"Oct " => 10 ,
190195 b"Nov " => 11 ,
191196 b"Dec " => 12 ,
192- _ => return Err ( "Invalid month" . into ( ) ) ,
197+ _ => return Err ( err ( "Invalid month" ) ) ,
193198 } ,
194199 year : from_utf8 ( & s[ 20 ..24 ] ) ?. parse ( ) ?,
195200 week_day : match & s[ 0 ..4 ] {
@@ -200,7 +205,7 @@ fn parse_asctime(s: &[u8]) -> Result<HttpDate, Exception> {
200205 b"Fri " => 5 ,
201206 b"Sat " => 6 ,
202207 b"Sun " => 7 ,
203- _ => return Err ( "Invalid day" . into ( ) ) ,
208+ _ => return Err ( err ( "Invalid day" ) ) ,
204209 } ,
205210 } )
206211}
@@ -323,18 +328,18 @@ impl From<HttpDate> for SystemTime {
323328}
324329
325330impl FromStr for HttpDate {
326- type Err = Exception ;
331+ type Err = Error ;
327332
328333 fn from_str ( s : & str ) -> Result < Self , Self :: Err > {
329334 if !s. is_ascii ( ) {
330- return Err ( "Not ascii" . into ( ) ) ;
335+ return Err ( err ( "Not ascii" ) ) ;
331336 }
332337 let x = s. trim ( ) . as_bytes ( ) ;
333338 let date = parse_imf_fixdate ( x)
334339 . or_else ( |_| parse_rfc850_date ( x) )
335340 . or_else ( |_| parse_asctime ( x) ) ?;
336341 if !date. is_valid ( ) {
337- return Err ( "Invalid date time" . into ( ) ) ;
342+ return Err ( err ( "Invalid date time" ) ) ;
338343 }
339344 Ok ( date)
340345 }
0 commit comments