Set-up:
A project I am working on has a pub/sub server with an HTTP interface. Subscription works by accepting server-sent-events.
curl -X GET server:port/topics/news
which will be pushed whenever a message is published to the given topic URL
curl -X PUT server:port/topics/news -d "Politician Lies!"
Problem:
I have a scala project which needs to subscribe to this pub/sub server. The Play! framework is able to handle this by using PlayWS with Enumeratee + Iteratee. Unfortunately, the PlayWS library requires that a Play! Application is in scope and I am not using Play. Is there a library (with minimal dependancies) I can use which allows me to accept server-sent-events? I'll need at least one working example in order to get started.
I have a preference for scala libraries but I'm willing to accept a Java solution if I have to.
You have several possibilities:
In Play 2.3, the WS library is now a separate library, so that should help. RC2 is already available
Alternatively, you could depend on Play 2.x and use a StaticApplication
like so:
val application = new StaticApplication(new java.io.File("."))
This will essentially bootstrap a Play application, and from there on you can use the WS
library as usual
I've accepted Manuel Bernhardt's answer because it led me in the right direction but I feel a full example is important for anyone else with this issue.
I updated my build.sbt file to include PlayWS 2.3 and the Iteratees library.
libraryDependencies ++= Seq(
"com.typesafe.play" %% "play-ws" % "2.3.0",
"com.typesafe.play" %% "play-iteratees" % "2.3.0"
)
The WS singleton requires an implicit Play Application to be used (something I don't have or want) so instead I will need to create my own client
val builder = new (com.ning.http.client.AsyncHttpClientConfig.Builder)()
val client = new play.api.libs.ws.ning.NingWSClient(builder.build())
I then create my Iteratee so that I can handle my server-sent-events.
def print = Iteratee.foreach { chunk: Array[Byte] =>
println(new String(chunk))
}
and finally subscribe to the server
client.url("http://localhost:8080/topics/news").get(_ => print)
Now, when an event is sent
curl -X PUT server:port/topics/news -d "Politician Lies!"
My Scala application will print the received event
data: Politician Lies!
I'm not aware of other Scala libraries that implement a Server Sent Events client, but the Jersey project has a Java library for Server Sent Events clients (as well as servers). The API does not appear to be very verbose, and appears like it can be nicely wrapped in some code to fit in more idiomatically with Scala.