2013-04-11 5 views
13

Ist es möglich, dass json4s keine Ausnahme auslöst, wenn das erforderliche Feld fehlt?Ist es möglich, dass json4s keine Ausnahme auslöst, wenn das erforderliche Feld fehlt?

Wenn ich „Extrakt“ Objekt aus roher json String wirft es Ausnahme wie diese

org.json4s.package$MappingException: No usable value for pager 
No usable value for rpp 
Did not find value which can be converted into byte 
    at org.json4s.reflect.package$.fail(package.scala:98) 
    at org.json4s.Extraction$ClassInstanceBuilder.org$json4s$Extraction$ClassInstanceBuilder$$buildCtorArg(Extraction.scala:388) 
    at org.json4s.Extraction$ClassInstanceBuilder$$anonfun$11.apply(Extraction.scala:396) 

Ist es möglich, es nur null sein zu lassen?

Antwort

17

Es ist ziemlich einfach, Sie müssen Option und seine Potentiale, Some und None verwenden.

val json = ("name" -> "joe") ~ ("age" -> Some(35)); 
val json = ("name" -> "joe") ~ ("age" -> (None: Option[Int])) 

Beachten Sie jedoch, im obigen Fall ein match für Ihre Option durchgeführt werden. Wenn es None ist, wird es vollständig aus der Zeichenfolge entfernt, so dass es null nicht zurückgibt.

Im selben Muster, um unvollständige JSON zu analysieren, verwenden Sie eine case class mit Option.

case class someModel(
    age: Option[Int], 
    name: Option[String] 
); 
val json = ("name" -> "joe") ~ ("age" -> None); 
parse(json).extract[someModel]; 

Es gibt ein Verfahren, das keine Ausnahme ausgelöst wird, und das ist extractOpt

parse(json).extractOpt[someModel]; 

Eine Art und Weise, mit der scala API zu replizieren würde scala.util.Try zu benutzen:

Try { parse(json).extract[someModel] }.toOption 
4

Ich habe mich mit diesem Problem bei Datenmigrationen beschäftigt und wollte, dass Standardwerte nicht definierte Felder ausfüllen.

Meine Lösung bestand darin, die Standardwerte in den JValue zusammenzuführen, bevor das Ergebnis extrahiert wurde.

val defaultsJson = Extraction.decompose(defaults) 
    val valueJson = JsonUtil.jValue(v) 
    (defaultsJson merge valueJson).extract[T] 

JsonUtil.scala

import org.json4s._ 

    object JsonUtil { 
    import java.nio.charset.StandardCharsets.UTF_8 
    import java.io.{InputStreamReader, ByteArrayInputStream} 

    def jValue(json: String): JValue = { 
     jValue(json.getBytes(UTF_8)) 
    } 

    def jValue(json: Array[Byte]): JValue = { 
     val reader = new InputStreamReader(new ByteArrayInputStream(json), UTF_8) 
     native.JsonParser.parse(reader) 
    } 
    } 
Verwandte Themen