SwiftDate icon indicating copy to clipboard operation
SwiftDate copied to clipboard

.toISODate(region: Region.ISO) Not working as expected

Open morgz opened this issue 4 years ago • 1 comments
trafficstars

The docs state this should return the date in the region specified in the ISO string. This is not the case unless I'm missing something. It converts to GMT.

po "2017-08-05T16:04:03+02:00".toISODate(region: Region.ISO)
▿ Optional<DateInRegion>
  ▿ some : {abs_date='2017-08-05T14:04:03Z', rep_date='2017-08-05T14:04:03Z', region={calendar='gregorian', timezone='GMT', locale='en_US_POSIX'}
    ▿ date : 2017-08-05 14:04:03 +0000
      - timeIntervalSinceReferenceDate : 523634643.0
    ▿ region : {calendar='gregorian', timezone='GMT', locale='en_US_POSIX'}
      ▿ calendar : gregorian (fixed)
        - identifier : gregorian
        - kind : "fixed"
        ▿ locale : Optional<Locale>
          ▿ some : en_US_POSIX (fixed)
            - identifier : "en_US_POSIX"
            - kind : "fixed"
        ▿ timeZone : GMT (fixed)
          - identifier : "GMT"
          - kind : "fixed"
          ▿ abbreviation : Optional<String>
            - some : "GMT"
          - secondsFromGMT : 0
          - isDaylightSavingTime : false
        - firstWeekday : 1
        - minimumDaysInFirstWeek : 1
    - customFormatter : nil

morgz avatar Apr 01 '21 20:04 morgz

I'm very new to this library so I could be wrong here, but doesn't Region.ISO define GMT as the timezone? From Region.swift:83...

/// ISO Region is defined by the gregorian calendar, gmt timezone and english posix locale
public static var ISO: Region {

By specifying Region.ISO as the region you are telling it to create a DateInRegion object that reflects the specified string in the GMT timezone.

let vdate = "2017-08-05T16:04:03+02:00".toISODate(region: Region.ISO)

Optional({abs_date='2017-08-05T14:04:03Z', rep_date='2017-08-05T14:04:03Z', region={calendar='gregorian', timezone='GMT', locale='en_US_POSIX'})

If you don't specify a Region, the returned DateInRegion reflects the timezone defined in the string (which is what I think you wanted?)

let vdate = "2017-08-05T16:04:03+02:00".toISODate()

Optional({abs_date='2017-08-05T14:04:03Z', rep_date='2017-08-05T16:04:03+02:00', region={calendar='gregorian', timezone='GMT+0200', locale='en_US_POSIX'})

Just to be confusing (which dates are!) the date object (type Date) in the DateInRegion result does not have the concept of a timezone - it's just a point in time. To print it for a particular timezone, create a formatter and set the zone on the formatter eg.

let df = ISO8601DateFormatter()
df.timeZone = vdate!.region.timeZone
Swift.print(df.string(from: vdate!.date))

/// Produces "2017-08-05T16:04:03+02:00"

dagronf avatar Apr 26 '21 14:04 dagronf