作者:手浪用户2602890763 | 来源:互联网 | 2023-05-25 19:07
我正在编写一些RESTful API测试用例,并且很少使用scala播放框架。
这是我的JSON的示例。
[ {
"size" : "5082",
"date-created" : "Wed Nov 19 17:10:39 CST 2014",
"id" : "546d236fb84e894eefd8f769",
"content-type" : "image/png",
"filename" : "chrome-on-windows.PNG"
}, {
"size" : "15684",
"date-created" : "Mon Jan 12 17:28:02 CST 2015",
"id" : "54b4588266b3d11b1c1e9db6",
"content-type" : "image/png",
"filename" : "logos_ncsa.png"
}, {
"size" : "1267871",
"date-created" : "Mon Jan 12 17:28:03 CST 2015",
"id" : "54b4588366b3d11b1c1e9dba",
"content-type" : "image/jpg",
"filename" : "morrowplots.jpg"
} ]
如您所见,我有一个JSON项目列表/数组。我想获取“ morrowplots.jpg”文件的ID,并将其存储到变量中,以用于成功的API调用。
因此,我将代码设置为如下所示。以下代码中的结果变量是您在上面看到的JSON字符串。
case class FileName(size: String, datecreated: String, id: String, contenttype: String, filename: String)
implicit val fileReads: Reads[FileName] = (
(__ \\ "size").read[String] and
(__ \\ "datecreated").read[String] and
(__ \\ "id").read[String] and
(__ \\ "content-type").read[String] and
(__ \\ "filename").read[String]
)(FileName.apply _)
val json: JsValue = Json.parse(contentAsString(result))
val nameResult: JsResult[FileName] = json.validate[FileName](fileReads)
info("Right after validate")
nameResult match {
case s: JsSuccess[FileName] => {
val testfile: FileName = s.get
// Do something with testfile
info("Success")
}
case e: JsError => {
info("Error")
info("Errors: " + JsError.toFlatJson(e).toString())
}
}
这给了我以下错误。
[信息] +错误:{“ obj size”:[{“ msg”:“ error.path.result.multiple”,“ args”:[]}],“ obj filename”:[{“ msg”:“ error .path.resul t.multiple“,” args“:[]}],” obj id“:[{” msg“:” error.path.result.multiple“,” args“:[]}],” obj content-type“:[{” msg“:” error.path .result.multiple“,” args“:[]}],” obj * datecreated“:[{” msg“:” error.path.missing“, “ args”:[]}]}
那么,如何解决此列表/数组问题以及如何按文件名搜索以获取ID?
提前致谢。
1> Agemen..:
首先,您可能决定使用内置的json实用程序,而不是执行手动解析。
case class FileName(size: String, datecreated: String, id: String, contenttype: String, filename: String)
object FileName {
implicit val formatFileName = Json.format[FileName]
}
在那里,您拥有解析基本json对象所需的全部内容。编译器将使用宏(IIRC)生成与您手工编写的代码等效的代码。由于您的字段没有奇异的验证,因此无需手动编写Reads和Writes类。
然后您可以通过以下方式阅读:
def readString(str: String) = {
val jsr: JsResult[Seq[FileName]] = Json.parse(str).validate[Seq[FileName]]
jsr.fold(
error => {
???
},
success => {
???
}
)
}
jsr在这里是JsResult。它可以是JsSuccess或JsError。
还要注意完整的类型。由于将数组作为输入,因此应将输出放入一个集合(例如Seq)中。
您可以折叠JsResult。fold期望两个功能。一种是针对错误情况,其类型为Seq [(JsPath,Seq [ValidationError])] => X,其中X是函数的返回类型。它向您显示了阻止json转换为Seq [FileName]的所有问题。
另一个是成功案例。它的类型为Seq [FileName] => X,其X与以前相同。
您现在可以决定在这两个函数中放入什么。
正如贾斯汀(Justin)所指出的,您也可以使用火柴来编写它。即使功能较少,也可能会更容易:
def readString(str: String) = {
val jsr: JsResult[Seq[FileName]] = Json.parse(str).validate[Seq[FileName]]
jsr match {
case JsResult(seq) => ???
case e: JsError => ???
}
}