Skip to content

Instantly share code, notes, and snippets.

@jasonmartens
Last active October 29, 2015 17:44
Show Gist options
  • Save jasonmartens/5f251340704d43bd663b to your computer and use it in GitHub Desktop.
Save jasonmartens/5f251340704d43bd663b to your computer and use it in GitHub Desktop.
/**
* Created by jasonmartens on 10/13/15.
*/
object Main extends App {
import spray.json._
import scala.reflect.ClassTag
trait TestingTrait
case object TestingTypeA extends TestingTrait
case object TestingTypeB extends TestingTrait
case class Wrapper(data: TestingTrait)
object SimpleClassNameExtractor {
def extractSimpleClassName(input: String) = input.split("\\.").last.split("\\$").last
def apply[T](input: Class[T]): String = extractSimpleClassName(input.getName)
}
/**
* A custom version of the Spray DefaultJsonProtocol with an additional
* formatter for ADT's of only case objects.
*/
trait CaseObjectSerializationSupport extends DefaultJsonProtocol {
def caseObjectJsonFormat[T: ClassTag](objects: T*)(implicit tag: ClassTag[T]) = new RootJsonFormat[T] {
/** A mapping from object names to the objects */
private val mapping = objects.map(obj ⇒ key(obj) -> obj).toMap
override def read(json: JsValue): T = (json match {
case JsString(value) ⇒ mapping.get(value)
case _ ⇒ None
}).getOrElse(deserializationError(s"Unknown json value found when converting to $tag: $json"))
/** The toString value of a case object is its name */
override def write(value: T): JsValue = JsString(key(value))
private def key(input: T): String = SimpleClassNameExtractor(input.getClass)
}
}
object CaseObjectSerializationSupport extends CaseObjectSerializationSupport {
implicit val wrapperFormat = jsonFormat1(Wrapper)
}
import CaseObjectSerializationSupport._
val jsResult = """{"data": "TestingA"}""".toJson.convertTo[Wrapper]
println(s"Result: $jsResult")
}
@jasonmartens
Copy link
Author

[error] Main.scala:46: could not find implicit value for evidence parameter of type Main.CaseObjectSerializationSupport.JF[Main.TestingTrait]
[error] implicit val wrapperFormat = jsonFormat1(Wrapper)
[error] ^
[error] Main.scala:51: Cannot find JsonReader or JsonFormat type class for Main.Wrapper
[error] val jsResult = """{"data": "TestingA"}""".toJson.convertTo[Wrapper]
[error] ^
[error] two errors found
error Compilation failed

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