Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,50 @@ public typealias EncodeResult = (data: Data?, error: Error?)

open class CodableHelper {

/// OpenAPI's "date-time" compatible DateFormater.
/// Supports both OpenAPI's "date-time" formats (with/-out fractional secs) for deserialize dates from JSON format and `Configuration.dateFormat` for serialize dates into JSON format.
/// - SeeAlso:
/// [stackoverflow.com: How to convert a date string with optional fractional seconds using Codable in Swift4](https://stackoverflow.com/questions/46458487/)
class OpenApiIso8601DateFormatter: DateFormatter {
static let formatters: [DateFormatter] = [
iso8601Formatter(withFractionalSeconds: true),
iso8601Formatter(withFractionalSeconds: false)
]

static func iso8601Formatter(withFractionalSeconds fractional: Bool) -> DateFormatter {
let formatter = DateFormatter()
formatter.calendar = Calendar(identifier: .iso8601)
formatter.locale = Locale(identifier: "en_US_POSIX")
formatter.timeZone = TimeZone(secondsFromGMT: 0)
formatter.dateFormat = Configuration.getDateFormat(withFractionalSeconds: fractional)
return formatter
}

override public func getObjectValue(_ obj: AutoreleasingUnsafeMutablePointer<AnyObject?>?,
for string: String,
errorDescription error: AutoreleasingUnsafeMutablePointer<NSString?>?) -> Bool {
// using flatMap instead of compactMap for backward-comp.
guard let date = (type(of: self).formatters.flatMap { $0.date(from: string) }).first else {
error?.pointee = "Invalid ISO8601 date: \(string)" as NSString
return false
}

obj?.pointee = date as NSDate
return true
}

override public func string(for obj: Any?) -> String? {
guard let date = obj as? Date else {
return nil
}

// create new formatter, which is considering dateFormat config
let newFormatter = self.copy() as! DateFormatter
newFormatter.dateFormat = Configuration.dateFormat
return newFormatter.string(from: date)
}
}

public static var dateformatter: DateFormatter?

open class func decode<T>(_ type: T.Type, from data: Data) -> (decodableObj: T?, error: Error?) where T : Decodable {
Expand All @@ -22,11 +66,7 @@ open class CodableHelper {
decoder.dateDecodingStrategy = .formatted(df)
} else {
decoder.dataDecodingStrategy = .base64
let formatter = DateFormatter()
formatter.calendar = Calendar(identifier: .iso8601)
formatter.locale = Locale(identifier: "en_US_POSIX")
formatter.timeZone = TimeZone(secondsFromGMT: 0)
formatter.dateFormat = Configuration.dateFormat
let formatter = OpenApiIso8601DateFormatter()
decoder.dateDecodingStrategy = .formatted(formatter)
}

Expand All @@ -51,11 +91,7 @@ open class CodableHelper {
encoder.dateEncodingStrategy = .formatted(df)
} else {
encoder.dataEncodingStrategy = .base64
let formatter = DateFormatter()
formatter.calendar = Calendar(identifier: .iso8601)
formatter.locale = Locale(identifier: "en_US_POSIX")
formatter.timeZone = TimeZone(secondsFromGMT: 0)
formatter.dateFormat = Configuration.dateFormat
let formatter = OpenApiIso8601DateFormatter()
encoder.dateEncodingStrategy = .formatted(formatter)
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,14 @@ open class Configuration {

// This value is used to configure the date formatter that is used to serialize dates into JSON format.
// You must set it prior to encoding any dates, and it will only be read once.
public static var dateFormat = "yyyy-MM-dd'T'HH:mm:ss.SSSZZZZZ"
public static var dateFormat = Configuration.getDateFormat(withFractionalSeconds: true)


/// Get one of the two OpenAPI compatible "date-time" formats. Either with or without fractional seconds, which are optional by the OpenAPI specification.
///
/// - Parameter withFractionalSeconds: use true to get format with fractional seconds and use false to get format without them.
/// - Returns: OpenAPI compatible "date-time" format
public static func getDateFormat(withFractionalSeconds fractional: Bool) -> String {
return "yyyy-MM-dd'T'HH:mm:ss\(fractional ? ".SSS" : "")ZZZZZ"
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -70,11 +70,7 @@ private let dateFormatter: DateFormatter = {
if let formatter = CodableHelper.dateformatter {
return formatter
} else {
let formatter = DateFormatter()
formatter.calendar = Calendar(identifier: .iso8601)
formatter.locale = Locale(identifier: "en_US_POSIX")
formatter.timeZone = TimeZone(secondsFromGMT: 0)
formatter.dateFormat = Configuration.dateFormat
let formatter = CodableHelper.OpenApiIso8601DateFormatter()
return formatter
}
}()
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,50 @@ public typealias EncodeResult = (data: Data?, error: Error?)

open class CodableHelper {

/// OpenAPI's "date-time" compatible DateFormater.
/// Supports both OpenAPI's "date-time" formats (with/-out fractional secs) for deserialize dates from JSON format and `Configuration.dateFormat` for serialize dates into JSON format.
/// - SeeAlso:
/// [stackoverflow.com: How to convert a date string with optional fractional seconds using Codable in Swift4](https://stackoverflow.com/questions/46458487/)
class OpenApiIso8601DateFormatter: DateFormatter {
static let formatters: [DateFormatter] = [
iso8601Formatter(withFractionalSeconds: true),
iso8601Formatter(withFractionalSeconds: false)
]

static func iso8601Formatter(withFractionalSeconds fractional: Bool) -> DateFormatter {
let formatter = DateFormatter()
formatter.calendar = Calendar(identifier: .iso8601)
formatter.locale = Locale(identifier: "en_US_POSIX")
formatter.timeZone = TimeZone(secondsFromGMT: 0)
formatter.dateFormat = Configuration.getDateFormat(withFractionalSeconds: fractional)
return formatter
}

override public func getObjectValue(_ obj: AutoreleasingUnsafeMutablePointer<AnyObject?>?,
for string: String,
errorDescription error: AutoreleasingUnsafeMutablePointer<NSString?>?) -> Bool {
// using flatMap instead of compactMap for backward-comp.
guard let date = (type(of: self).formatters.flatMap { $0.date(from: string) }).first else {
error?.pointee = "Invalid ISO8601 date: \(string)" as NSString
return false
}

obj?.pointee = date as NSDate
return true
}

override public func string(for obj: Any?) -> String? {
guard let date = obj as? Date else {
return nil
}

// create new formatter, which is considering dateFormat config
let newFormatter = self.copy() as! DateFormatter
newFormatter.dateFormat = Configuration.dateFormat
return newFormatter.string(from: date)
}
}

public static var dateformatter: DateFormatter?

open class func decode<T>(_ type: T.Type, from data: Data) -> (decodableObj: T?, error: Error?) where T : Decodable {
Expand All @@ -22,11 +66,7 @@ open class CodableHelper {
decoder.dateDecodingStrategy = .formatted(df)
} else {
decoder.dataDecodingStrategy = .base64
let formatter = DateFormatter()
formatter.calendar = Calendar(identifier: .iso8601)
formatter.locale = Locale(identifier: "en_US_POSIX")
formatter.timeZone = TimeZone(secondsFromGMT: 0)
formatter.dateFormat = Configuration.dateFormat
let formatter = OpenApiIso8601DateFormatter()
decoder.dateDecodingStrategy = .formatted(formatter)
}

Expand All @@ -51,11 +91,7 @@ open class CodableHelper {
encoder.dateEncodingStrategy = .formatted(df)
} else {
encoder.dataEncodingStrategy = .base64
let formatter = DateFormatter()
formatter.calendar = Calendar(identifier: .iso8601)
formatter.locale = Locale(identifier: "en_US_POSIX")
formatter.timeZone = TimeZone(secondsFromGMT: 0)
formatter.dateFormat = Configuration.dateFormat
let formatter = OpenApiIso8601DateFormatter()
encoder.dateEncodingStrategy = .formatted(formatter)
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,14 @@ open class Configuration {

// This value is used to configure the date formatter that is used to serialize dates into JSON format.
// You must set it prior to encoding any dates, and it will only be read once.
public static var dateFormat = "yyyy-MM-dd'T'HH:mm:ss.SSSZZZZZ"
public static var dateFormat = Configuration.getDateFormat(withFractionalSeconds: true)


/// Get one of the two OpenAPI compatible "date-time" formats. Either with or without fractional seconds, which are optional by the OpenAPI specification.
///
/// - Parameter withFractionalSeconds: use true to get format with fractional seconds and use false to get format without them.
/// - Returns: OpenAPI compatible "date-time" format
public static func getDateFormat(withFractionalSeconds fractional: Bool) -> String {
return "yyyy-MM-dd'T'HH:mm:ss\(fractional ? ".SSS" : "")ZZZZZ"
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -69,11 +69,7 @@ private let dateFormatter: DateFormatter = {
if let formatter = CodableHelper.dateformatter {
return formatter
} else {
let formatter = DateFormatter()
formatter.calendar = Calendar(identifier: .iso8601)
formatter.locale = Locale(identifier: "en_US_POSIX")
formatter.timeZone = TimeZone(secondsFromGMT: 0)
formatter.dateFormat = Configuration.dateFormat
let formatter = CodableHelper.OpenApiIso8601DateFormatter()
return formatter
}
}()
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,50 @@ public typealias EncodeResult = (data: Data?, error: Error?)

open class CodableHelper {

/// OpenAPI's "date-time" compatible DateFormater.
/// Supports both OpenAPI's "date-time" formats (with/-out fractional secs) for deserialize dates from JSON format and `Configuration.dateFormat` for serialize dates into JSON format.
/// - SeeAlso:
/// [stackoverflow.com: How to convert a date string with optional fractional seconds using Codable in Swift4](https://stackoverflow.com/questions/46458487/)
class OpenApiIso8601DateFormatter: DateFormatter {
static let formatters: [DateFormatter] = [
iso8601Formatter(withFractionalSeconds: true),
iso8601Formatter(withFractionalSeconds: false)
]

static func iso8601Formatter(withFractionalSeconds fractional: Bool) -> DateFormatter {
let formatter = DateFormatter()
formatter.calendar = Calendar(identifier: .iso8601)
formatter.locale = Locale(identifier: "en_US_POSIX")
formatter.timeZone = TimeZone(secondsFromGMT: 0)
formatter.dateFormat = Configuration.getDateFormat(withFractionalSeconds: fractional)
return formatter
}

override public func getObjectValue(_ obj: AutoreleasingUnsafeMutablePointer<AnyObject?>?,
for string: String,
errorDescription error: AutoreleasingUnsafeMutablePointer<NSString?>?) -> Bool {
// using flatMap instead of compactMap for backward-comp.
guard let date = (type(of: self).formatters.flatMap { $0.date(from: string) }).first else {
error?.pointee = "Invalid ISO8601 date: \(string)" as NSString
return false
}

obj?.pointee = date as NSDate
return true
}

override public func string(for obj: Any?) -> String? {
guard let date = obj as? Date else {
return nil
}

// create new formatter, which is considering dateFormat config
let newFormatter = self.copy() as! DateFormatter
newFormatter.dateFormat = Configuration.dateFormat
return newFormatter.string(from: date)
}
}

public static var dateformatter: DateFormatter?

open class func decode<T>(_ type: T.Type, from data: Data) -> (decodableObj: T?, error: Error?) where T : Decodable {
Expand All @@ -22,11 +66,7 @@ open class CodableHelper {
decoder.dateDecodingStrategy = .formatted(df)
} else {
decoder.dataDecodingStrategy = .base64
let formatter = DateFormatter()
formatter.calendar = Calendar(identifier: .iso8601)
formatter.locale = Locale(identifier: "en_US_POSIX")
formatter.timeZone = TimeZone(secondsFromGMT: 0)
formatter.dateFormat = Configuration.dateFormat
let formatter = OpenApiIso8601DateFormatter()
decoder.dateDecodingStrategy = .formatted(formatter)
}

Expand All @@ -51,11 +91,7 @@ open class CodableHelper {
encoder.dateEncodingStrategy = .formatted(df)
} else {
encoder.dataEncodingStrategy = .base64
let formatter = DateFormatter()
formatter.calendar = Calendar(identifier: .iso8601)
formatter.locale = Locale(identifier: "en_US_POSIX")
formatter.timeZone = TimeZone(secondsFromGMT: 0)
formatter.dateFormat = Configuration.dateFormat
let formatter = OpenApiIso8601DateFormatter()
encoder.dateEncodingStrategy = .formatted(formatter)
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,14 @@ open class Configuration {

// This value is used to configure the date formatter that is used to serialize dates into JSON format.
// You must set it prior to encoding any dates, and it will only be read once.
public static var dateFormat = "yyyy-MM-dd'T'HH:mm:ss.SSSZZZZZ"
public static var dateFormat = Configuration.getDateFormat(withFractionalSeconds: true)


/// Get one of the two OpenAPI compatible "date-time" formats. Either with or without fractional seconds, which are optional by the OpenAPI specification.
///
/// - Parameter withFractionalSeconds: use true to get format with fractional seconds and use false to get format without them.
/// - Returns: OpenAPI compatible "date-time" format
public static func getDateFormat(withFractionalSeconds fractional: Bool) -> String {
return "yyyy-MM-dd'T'HH:mm:ss\(fractional ? ".SSS" : "")ZZZZZ"
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -69,11 +69,7 @@ private let dateFormatter: DateFormatter = {
if let formatter = CodableHelper.dateformatter {
return formatter
} else {
let formatter = DateFormatter()
formatter.calendar = Calendar(identifier: .iso8601)
formatter.locale = Locale(identifier: "en_US_POSIX")
formatter.timeZone = TimeZone(secondsFromGMT: 0)
formatter.dateFormat = Configuration.dateFormat
let formatter = CodableHelper.OpenApiIso8601DateFormatter()
return formatter
}
}()
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,50 @@ public typealias EncodeResult = (data: Data?, error: Error?)

open class CodableHelper {

/// OpenAPI's "date-time" compatible DateFormater.
/// Supports both OpenAPI's "date-time" formats (with/-out fractional secs) for deserialize dates from JSON format and `Configuration.dateFormat` for serialize dates into JSON format.
/// - SeeAlso:
/// [stackoverflow.com: How to convert a date string with optional fractional seconds using Codable in Swift4](https://stackoverflow.com/questions/46458487/)
class OpenApiIso8601DateFormatter: DateFormatter {
static let formatters: [DateFormatter] = [
iso8601Formatter(withFractionalSeconds: true),
iso8601Formatter(withFractionalSeconds: false)
]

static func iso8601Formatter(withFractionalSeconds fractional: Bool) -> DateFormatter {
let formatter = DateFormatter()
formatter.calendar = Calendar(identifier: .iso8601)
formatter.locale = Locale(identifier: "en_US_POSIX")
formatter.timeZone = TimeZone(secondsFromGMT: 0)
formatter.dateFormat = Configuration.getDateFormat(withFractionalSeconds: fractional)
return formatter
}

override public func getObjectValue(_ obj: AutoreleasingUnsafeMutablePointer<AnyObject?>?,
for string: String,
errorDescription error: AutoreleasingUnsafeMutablePointer<NSString?>?) -> Bool {
// using flatMap instead of compactMap for backward-comp.
guard let date = (type(of: self).formatters.flatMap { $0.date(from: string) }).first else {
error?.pointee = "Invalid ISO8601 date: \(string)" as NSString
return false
}

obj?.pointee = date as NSDate
return true
}

override public func string(for obj: Any?) -> String? {
guard let date = obj as? Date else {
return nil
}

// create new formatter, which is considering dateFormat config
let newFormatter = self.copy() as! DateFormatter
newFormatter.dateFormat = Configuration.dateFormat
return newFormatter.string(from: date)
}
}

public static var dateformatter: DateFormatter?

open class func decode<T>(_ type: T.Type, from data: Data) -> (decodableObj: T?, error: Error?) where T : Decodable {
Expand All @@ -22,11 +66,7 @@ open class CodableHelper {
decoder.dateDecodingStrategy = .formatted(df)
} else {
decoder.dataDecodingStrategy = .base64
let formatter = DateFormatter()
formatter.calendar = Calendar(identifier: .iso8601)
formatter.locale = Locale(identifier: "en_US_POSIX")
formatter.timeZone = TimeZone(secondsFromGMT: 0)
formatter.dateFormat = Configuration.dateFormat
let formatter = OpenApiIso8601DateFormatter()
decoder.dateDecodingStrategy = .formatted(formatter)
}

Expand All @@ -51,11 +91,7 @@ open class CodableHelper {
encoder.dateEncodingStrategy = .formatted(df)
} else {
encoder.dataEncodingStrategy = .base64
let formatter = DateFormatter()
formatter.calendar = Calendar(identifier: .iso8601)
formatter.locale = Locale(identifier: "en_US_POSIX")
formatter.timeZone = TimeZone(secondsFromGMT: 0)
formatter.dateFormat = Configuration.dateFormat
let formatter = OpenApiIso8601DateFormatter()
encoder.dateEncodingStrategy = .formatted(formatter)
}

Expand Down
Loading