【问题标题】:make play-json read the empty string as None for a type of Option[T]对于 Option[T] 类型,让 play-json 将空字符串读取为 None
【发布时间】:2016-05-25 15:51:30
【问题描述】:

我正在尝试使用 play-json 从 GitHub API 解析 json,但在 Pull Requests 上遇到了 merge_commit_sha 字段的问题(顺便说一下,我知道该字段已被弃用,但不想讨论这个问题在这个解析问题中!)。不幸的是,merge_commit_sha 字段在某些情况下返回为空字符串:

"merge_commit_sha": ""

这就是declared in my case class字段的样子:

merge_commit_sha: Option[ObjectId],

我有一个implicit Format[ObjectId],它不能容忍空字符串,因为这不是 Git 哈希 id 的有效值。我还使用了一个 play-json 宏生成的 Read[PullRequest],我想继续使用它,而不是单独声明拉取请求中每个字段的读取。

由于我已将该字段声明为选项,我希望将 "merge_commit_sha": "" 读取为值 None,但这不是当前发生的情况 - 存在一个字符串,所以 Format[ObjectId]被调用,并返回一个JsFailure

我尝试过的一件事是声明一个具有所需行为的隐式 Format[Option[ObjectId]],但它似乎没有被宏生成的 Read[PullRequest] 使用。

【问题讨论】:

    标签: scala playframework scala-option play-json


    【解决方案1】:

    您可以自己定义一个自定义Reads and Writes

    使用 Json.format[MyType] 使用 Scala 宏。 You may be able to hook into that。虽然,为这个case class“扩​​展”一个宏似乎是错误的。

    自定义读取和写入可能有点“样板式”且乏味,但它们也有其优点。

    例如,如果您的 json 上有一堆新字段,则在验证或将其转换为 case class 时,您不会得到 JsError。您只需从 JSON 中获取您需要的内容并创建对象。它还允许将您的内部模型与您正在消费的内容分开,这在某些情况下是首选。

    希望对你有帮助,

    里斯


    编辑

    使用其他一些 JSON 库后,我可能已经找到了您正在寻找的东西。 我知道这个问题是在 Play JSON 之后专门提出的。

    如果您能够摆脱 Play JSON,请查看 spray-json-shapeless,特别是 JsNullBehaviourJsNullNotNone REF

    【讨论】:

    • "你必须自己定义一个读取。" - 澄清一下,您是说我需要自己手动定义 Read[PullRequest],因为无法使用宏生成的 Read[PullRequest]?鉴于 PullRequest 上有大量字段,这很不幸。
    • 为什么这被否决了,请评论,我可以更新我的答案
    • 碰巧,我没有否决这个答案,尽管我个人觉得它确实没有用处 - 正如我在我的问题中所说,我很想知道是否存在解决方案允许我在调整其中的 Option[ObjectId] 字段的解析时继续使用自动生成的 Read[PullRequest]。所以一个好的答案要么给出一个聪明的解决方案,使之成为可能,要么用一点理由解释为什么这样的事情绝对不可能可能。
    猜你喜欢
    • 1970-01-01
    • 2014-04-07
    • 2020-03-24
    • 1970-01-01
    • 1970-01-01
    • 2013-06-04
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多