当在Codable中进行日期比较时,如何解决单元测试中的错误 [英] How to resolve error in unit testing when we have Date comparison in Codable
问题描述
我尝试使用 Codable
在json解码中使用自定义日期策略,如 https://stackoverflow.com/a/28016692/3477974 。这是简化的实现代码:
I tried to use custom date strategy in json decoding using Codable
as describe in https://stackoverflow.com/a/28016692/3477974 . Here is the simplified implementation code:
public extension Formatter {
static let iso8601: DateFormatter = {
let formatter = DateFormatter()
formatter.calendar = Calendar(identifier: .iso8601)
formatter.locale = Locale(identifier: "en_US_POSIX")
formatter.timeZone = TimeZone(secondsFromGMT: 0)
formatter.dateFormat = "yyyy-MM-dd'T'HH:mm:ss.SSSXXXXX"
return formatter
}()
}
public extension Date {
var iso8601: String {
return Formatter.iso8601.string(from: self)
}
}
public extension JSONDecoder.DateDecodingStrategy {
static let iso8601withFractionalSeconds = custom {
let container = try $0.singleValueContainer()
let string = try container.decode(String.self)
guard let date = Formatter.iso8601.date(from: string) else {
throw DecodingError.dataCorruptedError(in: container,
debugDescription: "Invalid date: " + string)
}
return date
}
}
public extension JSONEncoder.DateEncodingStrategy {
static let iso8601withFractionalSeconds = custom {
var container = $1.singleValueContainer()
try container.encode(Formatter.iso8601.string(from: $0))
}
}
但是,关于单元测试它失败,尽管错误消息显示描述
的日期方法使用的值相等:
However, when it comes to unit testing it fails although the error message shows equal value used by description
method of date:
func test_jsonCodable_iso8601() {
let dates = [Date()] // ["Feb 9, 2020 at 12:55:24 PM"]
let encoder = JSONEncoder()
encoder.dateEncodingStrategy = .iso8601withFractionalSeconds
let data = try! encoder.encode(dates)
let decoder = JSONDecoder()
decoder.dateDecodingStrategy = .iso8601withFractionalSeconds
let decodedDates = try! decoder.decode([Date].self, from: data) // ["Feb 9, 2020 at 12:55:24 PM"]
XCTAssertEqual(dates, decodedDates)
// fails with error message: [2020-02-09 12:55:24 +0000]") is not equal to ("[2020-02-09 12:55:24 +0000]"
}
您是否知道问题是什么以及如何解决?
Do you have any idea what is the issue and how we can resolve it?
顺便说一下,实际的可解码对象是以下类型,其中 publishedAt
的类型为date:
By the way, the actual decodable object is the following one where publishedAt
is of type date:
public struct NewsItem: Equatable {
public let id: UUID
public let author: String
public let title: String
public let description: String
public let urlToImage: URL?
public let publishedAt: Date
public let content: String
public init(id: UUID,
author: String,
title: String,
description: String,
urlToImage: URL?,
publishedAt: Date,
content: String) {
self.id = id
self.author = author
self.title = title
self.description = description
self.urlToImage = urlToImage
self.publishedAt = publishedAt
self.content = content
}
}
extension NewsItem: Decodable {}
推荐答案
您要测试的是日期/ string转换,因此无需为此进行JSON编码和解码。以字符串形式的固定日期开始,将其转换为日期,然后返回并检查最终结果与固定日期
What you are testing is the date/string conversion so there is no need to involve JSON encoding and decoding into this. Start with a fixed date in string form, convert it to date and back and check the end result vs the fixed date
let input = "2020-02-02T19:10:23.123Z"
let formatter = DateFormatter.iso8601
let date = formatter.date(from: input)
let output = date?.iso8601
print(date != nil && input == output!)
请注意,这是在操场上编写的,而不是作为单元测试编写的
Note that this was written in a playground and not as a unit test
这篇关于当在Codable中进行日期比较时,如何解决单元测试中的错误的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!