Skip to content

Instantly share code, notes, and snippets.

@milessabin
Forked from rrmckinley/gist:6355794
Last active December 21, 2015 19:59
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save milessabin/6357743 to your computer and use it in GitHub Desktop.
Save milessabin/6357743 to your computer and use it in GitHub Desktop.
import org.json4s._
import org.json4s.native.JsonMethods._
import shapeless._
import poly._
import ops.hlist._
import syntax.singleton._
import record._
object JSON {
def compact[A](a: A)(implicit st: toJSON.Case[A] { type Result <: JValue }): String =
org.json4s.native.JsonMethods.compact(render(st(a)))
def pretty[A](a: A)(implicit st: toJSON.Case[A] { type Result <: JValue }): String =
org.json4s.native.JsonMethods.pretty(render(st(a)))
}
object toJSON extends Poly1 { // Pullback1[JValue] {
implicit def nullToJSON = at[Null](_ => JNull)
implicit def doubleToJSON = at[Double](JDouble(_))
implicit def bigIntToJSON = at[BigInt](JInt(_))
implicit def bigDecimalToJSON = at[BigDecimal](JDecimal(_))
implicit def numToJSON[V <% Long] = at[V](i => JInt(BigInt(i)))
implicit def stringToJSON = at[String](s => if (s == null) JNull else JString(s))
implicit def boolToJSON = at[Boolean](JBool(_))
implicit def jsonToJSON[V <: JValue] = at[V](identity)
implicit def dateToJSON[V <: java.util.Date](implicit f: Formats) =
at[V](s => if (s == null) JNull else JString(f.dateFormat.format(s)))
implicit def traversableToJSON[V, C[V] <: Traversable[V]](implicit st: Case.Aux[V, JValue]) =
at[C[V]](l => JArray(l.toList.map(v => toJSON(v))))
implicit def recordToJSON[R <: HList](implicit foldMap: MapFolder[R, List[JField], fieldToJSON.type]) = {
at[R](r => JObject(r.foldMap(Nil: List[JField])(fieldToJSON)(_ ::: _)))
}
}
object fieldToJSON extends Poly1 {
implicit def f[F, V](implicit tjf: toJSON.Case[V], wk: shapeless.Witness.Aux[F]) = at[FieldType[F, V]] {
f => (keyAsString(f), tjf(f : V)) :: Nil
}
// - could not find implicit value for parameter cse:
// shapeless.poly.Case[com.tagged.vor.toJSON.type,shapeless.::[shapeless.record.FieldType[F,V],shapeless.HNil]]
// - not enough arguments for method apply: (implicit cse:
// shapeless.poly.Case[com.tagged.vor.toJSON.type,shapeless.::
// [shapeless.record.FieldType[F,V],shapeless.HNil]])cse.Result in trait PolyApply. Unspecified value parameter cse.
def keyAsString[F, V](f: FieldType[F, V])(implicit wk: shapeless.Witness.Aux[F]) =
wk.value.toString
// implicit def value[K, V: toJSON.Case] = at[(K, V)] {
// case (k, v) => (keyAsString(k), toJSON(v)) :: Nil
// }
// implicit def option[K, V: toJSON.Case] = at[(K, Option[V])] {
// case (k, Some(v)) => (keyAsString(k), toJSON(v)) :: Nil
// case (k, None) => Nil
// }
// def keyAsString(k: Any): String = {
// def isNumeric(s: String) = s.toCharArray.forall(Character.isDigit)
//
// if (k.getClass == classOf[String]) k.toString
// else {
// val parts = k.getClass.getName.split("\\$")
// parts.reverse.dropWhile(isNumeric).head
// }
// }
}
object Test {
def main(args: Array[String]) {
println(fieldToJSON(("a" ->> 1)))
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment