【问题标题】:Scala: Parse JSON directly into a case classScala:将 JSON 直接解析为案例类
【发布时间】:2014-06-25 05:07:19
【问题描述】:

给定一个 JSON 字符串,以及一个与之对应的案例类,有什么简单的方法可以将 JSON 解析为案例类?有许多可用的库,但似乎 Scala 现在可以开箱即用。

如果 JSON 应该被解析成一个案例类的列表呢?

更新:

Jerkson 似乎被抛弃了,我不想安装完整的 Play 或 Lift 框架或其他任何繁重的东西。

【问题讨论】:

  • 您不必安装完整的框架——您只需将 json 库列为依赖项即可。我知道这适用于 lift-json 和 spray-json,它可能也适用于其他人。

标签: json scala parsing scala-2.10 case-class


【解决方案1】:

有几个框架可以做到这一点。

现在用的很多。许多很棒的功能。会把猫拉进来。

https://circe.github.io/circe/ https://github.com/circe/circe

JSON4s

JSON4s 相当成熟,支持 jacksonnative JSON-Parser。在许多项目中使用它来代替 jerkson。

https://github.com/json4s/json4s

play-json

可以在没有完整播放堆栈的情况下使用。作为 typesafe 的 play 项目的一部分,提供了大力支持。

http://www.playframework.com/documentation/2.0/ScalaJson

Scala 酸洗

序列化框架。有一个选项可以序列化/反序列化为 JSON。

https://github.com/scala/pickling

喷洒 JSON

可以序列化和反序列化。需要知道反序列化参数的数量。

https://github.com/spray/spray-json

【讨论】:

    【解决方案2】:

    我用过https://github.com/json4s/json4s,目前唯一的抱怨是https://github.com/json4s/json4s/issues/137

    import org.json4s._
    import org.json4s.native.JsonMethods._
    
    implicit val formats = DefaultFormats
    
    case class ParsedPage(crawlDate: String, domain:String, url:String, text: String)
    
    val js = """ {
    "crawlDate": "20150226",
    "domain": "0x20.be",
    "url": "http://0x20.be/smw/index.php?title=99_Bottles_of_Beer&oldid=6214",
    "text": "99 Bottles of Beer From Whitespace (Hackerspace Gent) Revision as of 14:43, 8 August 2012 by Hans ( Talk | contribs ) 99 Bottles of Beer Where: Loading map... Just me, with 99 bottles of beer and some friends. Subpages"
    }"""
    
    
    parse(js).extract[ParsedPage]
    

    【讨论】:

    • 此问题已修复。
    • 发现这是最好的“无忧无虑”的方法。虽然必须添加 import org.json4s.jackson.JsonMethods._ 而不是 ....native 才能工作。
    【解决方案3】:

    使用 spray-json,因为它很小。

    import spray.json._
    import DefaultJsonProtocol._
    
    
    val json = """{"one" : "1", "two" : "2", "three" : "3"}""".parseJson
    
    case class Numbers(one: String, two: String, three: String)
    
    object MyJsonProtocol extends DefaultJsonProtocol {
      implicit val numbersFormat = jsonFormat3(Numbers)
    
    }
    
    import MyJsonProtocol._
    
    val converted = json.convertTo[Numbers]
    

    使用这个 build.sbt 将 spray-json 下载到 sbt:

    lazy val root = (project in file(".")). settings( name := "jsonExample", libraryDependencies += "io.spray" %% "spray-json" % "1.3.2" )

    【讨论】:

      【解决方案4】:

      使用 net.liftweb

      import net.liftweb.json._
      case class Detail(username:String, password:String)
      implicit val formats = DefaultFormats
      val input = parse(jsonString).extract[Detail]
      println(input.username)
      

      确保 Scala 版本与 lift-json jar 匹配。例如。对于 Scala 2.10,请使用 lift-json_2.10。

      【讨论】:

        【解决方案5】:

        对于第一次遇到此问题的人,circe 也是一个不错的选择

        val customerJson = s"""{"id" : "1", "name" : "John Doe"}"""
        case class Customer(id: String, name: String)
        val customer = decode[Customer](customerJson)
        

        【讨论】:

          【解决方案6】:

          Spray Json 的重量很轻,完全可以满足您的需求。它是一个工具包而不是一个完整的框架,您可以只导入 Spray-json 项目而不是整个项目。

          https://github.com/spray/spray-json

          这些示例可以帮助您快速设置。大多数情况下,您的与 JSON 之间的转换代码最终都是一行代码,但您可以明确地处理它,以防您有一些奇怪的要求。

          【讨论】:

          【解决方案7】:

          我在 Play Framework 中支持 JSON 转换。

          也看看成熟的杰克逊。请注意,您需要使用 Jackson Scala 模块:https://github.com/FasterXML/jackson-module-scala

          一篇不错的文章提供了介绍 - 然后是一些添加隐式转换的代码:https://coderwall.com/p/o--apg/easy-json-un-marshalling-in-scala-with-jackson

          【讨论】:

            猜你喜欢
            • 2019-01-18
            • 2021-09-10
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 2016-07-27
            相关资源
            最近更新 更多