@@ -93,6 +93,38 @@ open class HTTPCookie : NSObject {
9393 let _version : Int
9494 var _properties : [ HTTPCookiePropertyKey : Any ]
9595
96+ // See: https://tools.ietf.org/html/rfc2616#section-3.3.1
97+
98+ // Sun, 06 Nov 1994 08:49:37 GMT ; RFC 822, updated by RFC 1123
99+ static let _formatter1 : DateFormatter = {
100+ let formatter = DateFormatter ( )
101+ formatter. locale = Locale ( identifier: " en_US_POSIX " )
102+ formatter. dateFormat = " EEE, dd MMM yyyy HH:mm:ss O "
103+ formatter. timeZone = TimeZone ( abbreviation: " GMT " )
104+ return formatter
105+ } ( )
106+
107+ // Sun Nov 6 08:49:37 1994 ; ANSI C's asctime() format
108+ static let _formatter2 : DateFormatter = {
109+ let formatter = DateFormatter ( )
110+ formatter. locale = Locale ( identifier: " en_US_POSIX " )
111+ formatter. dateFormat = " EEE MMM d HH:mm:ss yyyy "
112+ formatter. timeZone = TimeZone ( abbreviation: " GMT " )
113+ return formatter
114+ } ( )
115+
116+ // Sun, 06-Nov-1994 08:49:37 GMT ; Tomcat servers sometimes return cookies in this format
117+ static let _formatter3 : DateFormatter = {
118+ let formatter = DateFormatter ( )
119+ formatter. locale = Locale ( identifier: " en_US_POSIX " )
120+ formatter. dateFormat = " EEE, dd-MMM-yyyy HH:mm:ss O "
121+ formatter. timeZone = TimeZone ( abbreviation: " GMT " )
122+ return formatter
123+ } ( )
124+
125+ static let _allFormatters : [ DateFormatter ]
126+ = [ _formatter1, _formatter2, _formatter3]
127+
96128 static let _attributes : [ HTTPCookiePropertyKey ]
97129 = [ . name, . value, . originURL, . version, . domain,
98130 . path, . secure, . expires, . comment, . commentURL,
@@ -292,12 +324,8 @@ open class HTTPCookie : NSObject {
292324 if let date = expiresProperty as? Date {
293325 expDate = date
294326 } else if let dateString = expiresProperty as? String {
295- let formatter = DateFormatter ( )
296- formatter. locale = Locale ( identifier: " en_US_POSIX " )
297- formatter. dateFormat = " EEE, dd MMM yyyy HH:mm:ss O " // per RFC 6265 '<rfc1123-date, defined in [RFC2616], Section 3.3.1>'
298- let timeZone = TimeZone ( abbreviation: " GMT " )
299- formatter. timeZone = timeZone
300- expDate = formatter. date ( from: dateString)
327+ let results = HTTPCookie . _allFormatters. compactMap { $0. date ( from: dateString) }
328+ expDate = results. first
301329 }
302330 }
303331 _expiresDate = expDate
@@ -418,7 +446,7 @@ open class HTTPCookie : NSObject {
418446 let name = pair. components ( separatedBy: " = " ) [ 0 ]
419447 var value = pair. components ( separatedBy: " \( name) = " ) [ 1 ] //a value can have an "="
420448 if canonicalize ( name) == . expires {
421- value = value. insertComma ( at : 3 ) //re-insert the comma
449+ value = value. unmaskCommas ( ) //re-insert the comma
422450 }
423451 properties [ canonicalize ( name) ] = value
424452 }
@@ -439,7 +467,7 @@ open class HTTPCookie : NSObject {
439467 //we pass this to a map()
440468 private class func removeCommaFromDate( _ value: String ) -> String {
441469 if value. hasPrefix ( " Expires " ) || value. hasPrefix ( " expires " ) {
442- return value. removeCommas ( )
470+ return value. maskCommas ( )
443471 }
444472 return value
445473 }
@@ -623,12 +651,12 @@ fileprivate extension String {
623651 return self . trimmingCharacters ( in: NSCharacterSet . whitespacesAndNewlines)
624652 }
625653
626- func removeCommas ( ) -> String {
627- return self . replacingOccurrences ( of: " , " , with: " " )
654+ func maskCommas ( ) -> String {
655+ return self . replacingOccurrences ( of: " , " , with: " &comma " )
628656 }
629657
630- func insertComma ( at index : Int ) -> String {
631- return String ( self . prefix ( index ) ) + " , " + String ( self . suffix ( self . count - index ) )
658+ func unmaskCommas ( ) -> String {
659+ return self . replacingOccurrences ( of : " &comma " , with : " , " )
632660 }
633661}
634662
0 commit comments