蒸气通过日期参数

时间:2019-03-14 22:23:19

标签: swift date vapor

在Vapor 3应用程序中,我有一个Event模型,该模型具有属性startDate: DateendDate: Date
现在,我想知道如何在POST请求中传递这些日期值。在邮递员中,我在x-www-form-urlencoded中尝试了以下操作:

startDate -> 2019-03-14

这将返回以下错误:

  

无法转换为Double:str(\“ 2019-03-14 \”)

显然,Date变成了Double
因此,我需要传递什么值?


注意

我知道,我可以在Postman中插入{{$timestamp}},但是1)在Postman之外使用API​​时,这不能回答我的问题; 2)这不允许我输入其他日期比现在

2 个答案:

答案 0 :(得分:1)

我不确定x-www-form-urlencoded是因为我测试了它,并且如果我以0的形式发送日期,它会将其解码为2001-01-01 00:00:00 +0000,以为肯定是1970-01-01 00:00:00 +0000

但是使用JSON有效负载,您可以灵活地进行操作,因为您可以根据需要提供JSONDecoder配置。

struct Payload: Content {
    var date: Date
}

如果您希望以UNIX时间戳记发送日期

router.post("check") { req throws -> Future<String> in
    let decoder = JSONDecoder()
    decoder.dateDecodingStrategy = .secondsSince1970 // choose it for unix-timestamp
    return try req.content.decode(json: Payload.self, using: decoder).map { p in
        return String(describing: p.date)
    }
}

如果您想以自己的格式发送日期

router.post("check") { req throws -> Future<String> in
    let formatter = DateFormatter()
    formatter.dateFormat = "yyyy-MM-dd HH:mm:ss"
    formatter.timeZone = TimeZone(secondsFromGMT: 0)
    let decoder = JSONDecoder()
    decoder.dateDecodingStrategy = .formatted(formatter) // custom date formatter
    return try req.content.decode(json: Payload.self, using: decoder).map { p in
        return String(describing: p.date)
    }
}

因此,对于unix时间戳,您应该发送从1970年开始的秒,例如0将被解码为1970-01-01 00:00:00 +0000

对于上述自定义格式,您应该发送2018-01-01 00:00:00之类的日期以将其解码为2018-01-01 00:00:00 +0000

UPD:您可以编写扩展程序以对其进行精美解码

extension ContentContainer where M: Request {
    func decodeJson<D>(_ payload: D.Type) throws -> Future<D> where D: Decodable {
        let formatter = DateFormatter()
        formatter.dateFormat = "yyyy-MM-dd HH:mm:ss"
        formatter.timeZone = TimeZone(secondsFromGMT: 0)
        let decoder = JSONDecoder()
        decoder.dateDecodingStrategy = .formatted(formatter)
        return try decode(json: payload, using: decoder)
    }
}

这样您就可以像这样解码有效载荷

router.post("check") { (req) throws -> Future<String> in
    return try req.content.decodeJson(Payload.self).map { p in
        return String(describing: p.date)
    }
}

答案 1 :(得分:1)

因此,这里的问题在于,默认情况下,Date实例使用自2001年1月1日以来的时间间隔进行解码。Vapor使用的URL form decoder不支持不同的日期策略,例如{ {1}}目前正在执行,因此您必须以其他方式进行解码。这里有一些我可以提出的想法:

  • 只需在请求中发送时间戳即可。要在Postman中测试不同的日期,可以在请求前脚本中设置环境变量,然后在请求正文中访问它。
  • 手动实现JSONDecoderEvent.init(from:)方法。只是为了确保您不破坏Fluent编码,您可能必须添加一些额外的逻辑,但这应该可以工作。这是一个示例:

    .encode(to:)