Conversion from String to Date in Swift Returns Nil

Conversion from string to date in swift returns nil

You set the wrong format specifier for hour and timezone. Use this:

dateFormatter.dateFormat = "EEE, dd MMM yyyy HH:mm:ss Z"
dateFormatter.locale = Locale(identifier: "en_US")
  • hh means 12-hour format so there's no hour 15. Use HH instead
  • +zzzz is invalid timezone specifier. Use Z instead
  • Unless Friday is shortened to Fri in Bulgarian, use an English locale

Returning nil when converting string to date in swift

let dateFormatter = DateFormatter()
dateFormatter.locale = Locale(identifier: "en_US_POSIX")
dateFormatter.dateFormat = "yyyy-MM-dd"
dateFormatter.timeZone = TimeZone(abbreviation: "GMT+0:00")
let assignDate = dateFormatter.date(from: "2019-03-28")
print("assignDate \(assignDate)")

All works fine for me here!

assignDate Optional(2019-03-28 00:00:00 +0000)

Swift DateFormatter returns nil while converting String to Date

Your DateFormatter expects the original string to be in the January, 18, 2018 format. You should convert it to a Date first and only convert it to another format after that.

Also, you should not use YYYY when referring to an ordinary calendar year. See this question for details.

let str = "2018-01-18 13:04:42 +0000" 
let dateFormatter = DateFormatter()
dateFormatter.dateFormat = "yyyy-MM-dd HH:mm:ss Z"
dateFormatter.locale = Locale(identifier: "en_US_POSIX")

guard let date = dateFormatter.date(from: str) else {
return
}

let newDateFormatter = DateFormatter()
newDateFormatter.dateFormat = "MMMM, dd, yyyy"
let newStr = newDateFormatter.string(from: date)
print(newStr) /*January, 18, 2018*/

String to date conversion sometimes returns nil with DateFormatter

Answer for your question (string to date is nil): While converting from string to date, you have to use the same format as String. I assume the originalDate from your comments. You have to change your code like this

let originalDate = "Friday, December 10, 2021 at 4:17:04 PM"
let df: DateFormatter = DateFormatter()
df.locale = Locale(identifier: "en_US_POSIX")
df.dateFormat = "EEEE, MMMM d, yyyy 'at' h:mm:ss a"

let newDate = df.date(from: originalDate)
print(newDate)

If you again want string from date then you can again specify which format you want.

df.dateFormat = "MMM d, yyyy" // Sep 12, 2018 format'
let newStringDate = df.string(from: newDate!)
print(newStringDate)

Note: If you try to log the newDate value in the console using print, sometimes it shows nil. In that case, you can try 'po newDate' in the console.

Converting string to date returns nil

Looks like your string is in ISO8601 format. Use the ISO8601DateFormatter to get date instance. You can use ISO8601DateFormatter.Options to parse varieties of ISO8601 formats. For your string,

For Swift 4.2.1

let formatter = ISO8601DateFormatter()
let date = formatter.date(from: dateStr)
print(date!)

Should output

"2019-02-19 17:10:08 +0000\n"

DateFormatter is returning nil date for a simple date string

Xcode Debugger has a bug as you can see in this post that it will show optional dates as nil even when parsing the date succeeds. If you print the optional date you will see the resulting date.

Swift String to date conversion found nil while unwrapping an Optional value

Your format string does not include the timezone ID "America/Los_Angeles", so it fails to parse your string.

According to here, the format pattern for parsing IDs like that is apparently VV.

Therefore, you should change to:

dateFormatter.dateFormat = "yyyy-MM-dd HH:mm:ss VV"

and the output would be:

NEW DATE! Optional(2022-08-14 20:45:39 +0000)

which is the correct instant. 1pm in LA in the summer is 8pm UTC.

Converting date string to desired date format and the output is nil

You have a minor issue with the date format you are specifying. Your date format should actually be:

yyyy-MM-dd'T'HH:mm:ssZ

Therefore, change your code to:

dateFormatter.dateFormat = "yyyy-MM-dd'T'HH:mm:ssZ"

Output:

date: Optional(2019-12-16 05:33:43 +0000)

Edit following further information from OP in comments

In order to convert from a string in one format to a date, and then to another date format, you need two DateFormatters. The following will convert the original string date and then output it the date to another format:

let dateString: String = "2019-12-16T05:33:43Z"
print(dateString)

let dateFormatter = DateFormatter()
dateFormatter.locale = Locale(identifier: "en_US_POSIX")
dateFormatter.dateFormat = "yyyy-MM-dd'T'HH:mm:ssZ"
if let date = dateFormatter.date(from: dateString)
{
print("date: \(String(describing: date))")

let outputFormatter = DateFormatter()
outputFormatter.locale = Locale(identifier: "en_US_POSIX")
outputFormatter.dateFormat = "yyyy.MMMM.dd hh:mm aaa"
let outputDate = outputFormatter.string(from: date)
print("date: \(String(describing: outputDate))")
}

Output:

2019-12-16T05:33:43Z
date: 2019-12-16 05:33:43 +0000
date: 2019.December.16 05:33 AM

DateFormatter date from string returns nil when iPhone Date & Time 24-Hour Time is off

You're using a very standardized timestamp format, which allows you to take advantage of the ISO8601DateFormatter.

let dateString = "2020-03-05T09:00:00+00:00"

let df = ISO8601DateFormatter()
df.formatOptions = [.withInternetDateTime]

if let date = df.date(from: dateString) {
print(date) // 2020-03-05 09:00:00 +0000
}

If a machine (like your server) is generating the timestamp then it will (should) always be in zulu time (GMT) so you don't need to do anything beyond this. You could specify a time zone but there isn't a point since the string will always zero it out for you.

df.timeZone = TimeZone(secondsFromGMT: 0)

This string represents an absolute moment in time. If you need a relative moment in time, such as the local time from the source, you'll need to identify that time zone and apply it here, which is also very straighforward.



Related Topics



Leave a reply



Submit