Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How do you parse a JSON request with Dispatch?

I'm learning Scala, and attempting to understand how traits are working (specifically with the Dispatch library).

I've got something like this:

import dispatch._
import dispatch.liftjson._

object Foo
{
    def main(cmd: Array[String])
    {
        val http = new Http;
        val req = :/("example.com") / path ># (list ! obj);
        val res = http(req);
    }
}

Unfortunately, it's complaining that ># is not registered with dispatch.Request. The trait is described within dispatch.liftjson, and it was my assumption that I should just need to import that trait (which _ should cover) for it to register.

like image 980
David Cramer Avatar asked Jun 02 '11 21:06

David Cramer


1 Answers

You should be importing from dispatch.liftjson.Js._.

Having a trait isn't helpful, as you're not then using it. The JS._ import will bring all the contents of the JS object into your scope, including the implicit conversion requestToJsonVerbs which it has from trait ImplicitJsonVerbs. This method converts a standard Dispatch Request, which you have from :/("example.com") / path, to a JsonVerbs, which has the method >#.

Here's an abridged sample of how I query an API:

import dispatch._
import dispatch.liftjson.Js._

import net.liftweb.common.{Box, Failure, Full}
import net.liftweb.util.Helpers

case class Device(device_token: String, alias: Option[String])

val req = devicesReq / device_token as (app_token, secret)
Helpers.tryo(http(req ># (json => {
  json.extract[Device]
})))

As you can see, I have the correct imports (plus some for some Lift libraries I like), and my Request then 'has' a ># method. I give ># a function that matches the expected signature ((JValue) ⇒ T) and away we go.

In case you're wondering, I'm specifically using lift-json's ability to extract to case classes, meaning that T will be Device. However, lift-json also throws an exception if it is unable to convert the JValue to a Device, so I've wrapped my whole request with Helper.tryo, a Lift helper method that wraps a try-catch call, returning a Box. Box is like the standard Scala Option but with the addition of Failure, which indicates why a Box is empty. So, in this case I will get either a Full[Device] or a Failure. Handy!

like image 179
pr1001 Avatar answered Sep 30 '22 19:09

pr1001