I need to get a simple JSON serialization solution with minimum ceremony. So I was quite happy finding this forthcoming Play 2.2 library. This works perfectly with plain case classes, e.g.
import play.api.libs.json._ sealed trait Foo case class Bar(i: Int) extends Foo case class Baz(f: Float) extends Foo implicit val barFmt = Json.format[Bar] implicit val bazFmt = Json.format[Baz]
But the following fails:
implicit val fooFmt = Json.format[Foo] // "No unapply function found"
How would I set up the alleged missing extractor for Foo
?
Or would you recommend any other standalone library that handles my case more or less fully automatically? I don't care whether that is with macros at compile time or reflection at runtime, as long as it works out of the box.
AMENDED 2015-09-22
The library play-json-extra includes the play-json-variants strategy, but also the [play-json-extensions] strategy (flat string for case objects mixed with objects for case classes no extra $variant or $type unless needed). It also provides serializers and deserializers for macramé based enums.
Previous answer There is now a library called play-json-variants which allows you to write :
implicit val format: Format[Foo] = Variants.format[Foo]
This will generate the corresponding formats automatically, it will also handle disambiguation of the following case by adding a $variant attribute (the equivalent of 0__ 's class
attribute)
sealed trait Foo case class Bar(x: Int) extends Foo case class Baz(s: String) extends Foo case class Bah(s: String) extends Foo
would generate
val bahJson = Json.obj("s" -> "hello", "$variant" -> "Bah") // This is a `Bah` val bazJson = Json.obj("s" -> "bye", "$variant" -> "Baz") // This is a `Baz` val barJson = Json.obj("x" -> "42", "$variant" -> "Bar") // And this is a `Bar`
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With