Skip to content

Instantly share code, notes, and snippets.

@arturaz
Created February 21, 2013 19:41
Show Gist options
  • Star 2 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save arturaz/5007515 to your computer and use it in GitHub Desktop.
Save arturaz/5007515 to your computer and use it in GitHub Desktop.
Serialising case class with Either to JSON in play framework 2.1 scala
package models
import play.api.libs.json._
import play.api.libs.json.Json._
import play.api.libs.functional.syntax._
import org.apache.commons.codec.binary.Base64
/**
* Created with IntelliJ IDEA.
* User: arturas
* Date: 2/21/13
* Time: 9:13 PM
* To change this template use File | Settings | File Templates.
*/
object Js {
/**
* @param data Either Left(length of the binary data for stub) or
* Right(binary data)
*/
case class Attachment(
contentType: String, data: Either[Int, Array[Byte]]
) {
val stub = data.isLeft
}
implicit val attachmentFormat = new Format[Attachment] {
def reads(json: JsValue): JsResult[Attachment] = {
val reads = (
(__ \ "content_type").read[String] ~
(__ \ "stub_data_length").read[Int]
) { (contentType: String, stubDataLength: Int) =>
Attachment(contentType, Left(stubDataLength))
} | (
(__ \ "content_type").read[String] ~
(__ \ "data").read[String]
) { (contentType: String, base64Data: String) =>
val data = Base64.decodeBase64(base64Data.getBytes)
Attachment(contentType, Right(data))
}
reads.reads(json)
}
def writes(o: Attachment): JsValue = obj(
"content_type" -> o.contentType,
o.data.fold(
length => "stub_data_length" -> length,
bytes => "data" -> new String(Base64.encodeBase64(bytes))
)
)
}
}
@andreicioban
Copy link

👍

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment