在Scala中做HTTP请求
我想发出一个简单的POST请求到一个web服务,它返回一些XML在斯卡拉。
似乎Dispatch是用于此任务的标准库,但我找不到它的文档。 上面链接的主站点详细解释了什么是承诺以及如何执行asynchronous编程,但实际上并不loggingAPI。 有一个周期表 – 看起来有点可怕 – 但它只对那些已经知道该怎么做的人才有用,只需要提醒一下这个神秘的语法。
也似乎斯卡拉斯有一些HTTP的设施 ,但我也找不到任何文件。
我使用以下: https : //github.com/scalaj/scalaj-http 。
这是一个简单的GET请求:
import scalaj.http.Http Http("http://foo.com/search").param("q", "monkeys").asString
以及一个POST的例子:
val result = Http("http://example.com/url").postData("""{"id":"12","json":"data"}""") .header("Content-Type", "application/json") .header("Charset", "UTF-8") .option(HttpOptions.readTimeout(10000)).asString
Scalaj HTTP可通过SBT获得:
libraryDependencies += "org.scalaj" % "scalaj-http_2.11" % "2.3.0"
你可以使用喷雾客户端 。 缺乏文档(我花了一些时间来了解如何使用查询参数进行GET请求 ),但是如果您已经使用了喷雾,这是一个很好的select。 而且文档比调度更好。
我们在AI2上使用它来调度,因为操作符不太符号,我们已经使用了喷雾/演员。
import spray.client.pipelining._ val url = "http://youruri.com/yo" val pipeline: HttpRequest => Future[HttpResponse] = sendReceive // Post with header and parameters val responseFuture1: Future[String] = pipeline(Post(Uri(url) withParams ("param" -> paramValue), yourPostData) map (_.entity.asString) // Post with header val responseFuture2: Future[String] = pipeline(Post(url, yourPostData)) map (_.entity.asString)
我正在使用发送: http : //dispatch.databinder.net/Dispatch.html
他们刚刚发布了一个新版本(0.9.0),并带有一个我非常喜欢的全新API。 这是asynchronous的。
来自项目页面的示例:
import dispatch._ val svc = url("http://api.hostip.info/country.php") val country = Http(svc OK as.String) for (c <- country) println(c)
编辑:这可能会帮助你https://github.com/dispatch/reboot/blob/master/core/src/main/scala/requests.scala
另一个select是Typesafe的play-ws,这是Play Framework WS库作为独立的lib分解出来的:
http://blog.devalias.net/post/89810672067/play-framework-seperated-ws-library
我不一定把这个作为最好的select,但值得一提。
为什么不使用Apache HttpComponents ? 这是应用程序常见问题解答 ,涵盖了各种各样的情况。
如果我可以做一个无耻的插件,我有一个叫做Bee-Client的API,它仅仅是Scala for Java的HttpUrlConnection的一个包装器。
我必须这样做来testing一个终点(在集成testing中)。 所以下面是从Scala中的GET请求获取响应的代码。 我正在利用scala.io.Source从端点和ObjectMapper中读取json到对象的转换。
private def buildStockMasterUrl(url:String, stockStatus:Option[String]) = { stockStatus match { case Some(stockStatus) => s"$url?stockStatus=${stockStatus}" case _ => url } } private def fetchBooksMasterData(stockStatus:Option[String]): util.ArrayList[BooksMasterData] = { val url: String = buildBooksMasterUrl("http://localhost:8090/books/rest/catalogue/booksMasterData",stockStatus) val booksMasterJson : String = scala.io.Source.fromURL(url).mkString val mapper = new ObjectMapper() apper.readValue(booksMasterJson,classOf[util.ArrayList[BooksMasterData]]) } case class BooksMasterData(id:String,description: String,category: String)
这是我的testing方法相同
test("validate booksMasterData resource") { val booksMasterData = fetchBooksMasterData(Option(null)) booksMasterData.size should be (740) }