Json 使用读取[T]时丢弃包装器数据
我想我要做的应该相对简单,但我不确定。我正在进行一个API调用,以获取应用程序列表,并希望将它们读出。但是,该列表嵌套在响应中。响应类似于:Json 使用读取[T]时丢弃包装器数据,json,scala,playframework,Json,Scala,Playframework,我想我要做的应该相对简单,但我不确定。我正在进行一个API调用,以获取应用程序列表,并希望将它们读出。但是,该列表嵌套在响应中。响应类似于: { "response": { "instances": [ { /* object I'm concerned with reading */ }, ... ] } } 我的读者目前定义为: implicit val appReader : Reads[App] = ( (__ \ "ip_addre
{
"response": {
"instances": [
{ /* object I'm concerned with reading */ },
...
]
}
}
我的读者目前定义为:
implicit val appReader : Reads[App] = (
(__ \ "ip_address").read[String] and
(__ \ "hostname").read[String] and
(__ \ "application_version").read[String]
)(App)
以及一类:
case class App(
ip: String,
hostname: String,
version: String
)
但是,我不确定如何获取数据,因为它隐藏在响应中,或者是否有方法可以丢弃该数据。我假设应用程序位于实例数组中,如下所示:
val js = Json.parse("""
{
"response": {
"instances": [
{ "ip_address": "192.168.1.1", "hostname": "host1", "application_version": "1.0"},
{ "ip_address": "192.168.1.2", "hostname": "host2", "application_version": "1.0"}
]
}
}
""")
现在,阅读定义为App的应用程序列表:
val responseRead =
(__ \ "response").read(
(__ \ "instances").read[List[App]])
val apps = responseRead.reads(js).get
这将为您提供应用程序列表,而不包括其他应用程序。如果数据结构与假设的有所不同,这将为您指明正确的方向
编辑:大多数情况下,我更喜欢使用播放的方式。您的示例的代码可以编写如下:
case class App(
ip_address: String,
hostname: String,
application_version: String)
object App {
implicit val appFormat = Json.format[App]
}
case class Response(
instances: List[App])
object Response {
implicit val responseFormat = Json.format[Response]
}
case class Root(
response: Response)
object Root {
implicit val rootFormat = Json.format[Root]
}
val root = js.as[Root]
val apps = root.response.instances
如您所见,case类vals必须与其Json计数器部分具有相同的名称。此外,我使用的是格式而不是读取,这当然取决于您,但大多数时候您都需要读取和写入,而这正是格式提供给您的。这种类型仍然是
reads[App]
,我可以将其用作应用程序的隐式读取器,这样我就可以简单地调用json.validate[List[App]]
?哦,没关系,我明白了。我需要将其与读取[App]
的隐式定义一起使用。谢谢