之前发布过这个问题或类似的问题,但是没有一个解决方案可以用于最新的库。经过广泛搜索,我发现没有证据表明最流行的库spray-json
或play-json
(或其插件)的最新版本可以处理这种情况。有没有什么能够将超过22个元素的json解析为scala case类?由于scala 2.11案例类不再限于22个元素。请,只有完全可行的解决方案。明显的json示例如下。
{
"a": 1,
"b": 2,
"c": 3,
"d": 4,
"e": 5,
"f": 6,
"g": 7,
"h": 8,
"i": 9,
"j": 10,
"k": 11,
"l": 12,
"m": 13,
"n": 14,
"o": 15,
"p": 16,
"q": 17,
"r": 18,
"s": 19,
"t": 20,
"u": 21,
"v": 22,
"w": 23
}
UPDATE:当你无法控制json结构时就是这种情况,例如它是从第三方api中检索的。 twitter的推文json的一个例子:http://pastebin.com/h8fHAsd8
答案 0 :(得分:13)
circe可以使用Shapeless支持的自动编解码器派生。请注意,与json4s的case类解码不同,这里没有发生运行时反射:
case class Foo(
a: Int, b: Int, c: Int, d: Int, e: Int, f: Int, g: Int, h: Int, i: Int,
j: Int, k: Int, l: Int, m: Int, n: Int, o: Int, p: Int, q: Int, r: Int,
s: Int, t: Int, u: Int, v: Int, w: Int
)
import io.circe.generic.auto._, io.circe.jawn.decode
val json = """{
"a": 1, "b": 2, "c": 3, "d": 4, "e": 5, "f": 6, "g": 7, "h": 8, "i": 9,
"j": 10, "k": 11, "l": 12, "m": 13, "n": 14, "o": 15, "p": 16, "q": 17,
"r": 18, "s": 19, "t": 20, "u": 21, "v": 22, "w": 23
}"""
val result: cats.data.Xor[io.circe.Error, Foo] = decode[Foo](json)
这是一个最小的build.sbt
文件:
scalaVersion := "2.11.7"
addCompilerPlugin(
"org.scalamacros" % "paradise" % "2.1.0-M5" cross CrossVersion.full
)
libraryDependencies ++= Seq(
"io.circe" %% "circe-core" % "0.1.1",
"io.circe" %% "circe-generic" % "0.1.1",
"io.circe" %% "circe-jawn" % "0.1.1"
)
即将推出的0.2.0版本(目前作为快照提供)包括对泛型推导的许多改进,但对于这样的简单示例,0.1.1行为是相同的。
答案 1 :(得分:2)
对于play-json,play-json-extensions提供了一个扩展,支持> 22个字段和一些其他用例,如序列化密封特征结构,单例对象等。
import org.cvogt.play.json.Jsonx
implicit val jsonFormat = Jsonx.formatCaseClass[Foo] // Instead of Json.format
https://github.com/cvogt/play-json-extensions
circe / argonaut当然也值得一试。与play-json / play-json-extensions相比,不确定它们在功能和稳定性方面的比较。
答案 2 :(得分:2)
受@cvogt及其他个人要求的启发,我开发了一个库,通过宏透明地管理> 22个领域和其他功能。
图书馆是here和documentation
JsonFormat注释通过宏创建了一个“pimped”json格式,可以管理很多东西。
主要特点是:
答案 3 :(得分:1)
尝试使用json4s:
scala> import org.json4s._
import org.json4s._
scala> import org.json4s.native.JsonMethods._
import org.json4s.native.JsonMethods._
scala> case class Foo(
| a: String,
| b: String,
| c: String,
| d: String,
| e: String,
| f: String,
| g: String,
| h: String,
| i: String,
| j: String,
| k: String,
| l: String,
| m: String,
| n: String,
| o: String,
| p: String,
| q: String,
| r: String,
| s: String,
| t: String,
| u: String,
| v: String,
| w: String
| )
defined class Foo
scala>
scala> implicit val formats = DefaultFormats
formats: org.json4s.DefaultFormats.type = org.json4s.DefaultFormats$@6eb0a5cb
scala> val f = parse("{\n \"a\": 1,\n \"b\": 2,\n \"c\": 3,\n \"d\": 4,\n \"e\": 5,\n \"f\": 6,\n \"g\": 7,\n \"h\": 8,\n \"i\": 9,\n \"j\": 10,\n \"k\": 11,\n \"l\": 12,\n \"m\": 13,\n \"n\": 14,\n \"o\": 15,\n \"p\": 16,\n \"q\": 17,\n \"r\": 18,\n \"s\": 19,\n \"t\": 20,\n \"u\": 21,\n \"v\": 22,\n \"w\": 23\n}")
.extract[Foo]
f: Foo = Foo(1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23)