Skip to content

Instantly share code, notes, and snippets.

@neocsr
Forked from gre/pusher.scala
Created April 8, 2013 05:27
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 neocsr/5334415 to your computer and use it in GitHub Desktop.
Save neocsr/5334415 to your computer and use it in GitHub Desktop.
// Implementing the publishing Pusher REST API
// @see http://pusher.com/docs/rest_api
// with Play (scala) Framework
// @see http://scala.playframework.org/
class Pusher {
val appId = Play.configuration.getProperty("pusher.appId")
val key = Play.configuration.getProperty("pusher.key")
val secret = Play.configuration.getProperty("pusher.secret")
import java.security.MessageDigest
import java.math.BigInteger
import javax.crypto.Mac
import javax.crypto.spec.SecretKeySpec
def trigger(channel:String, event:String, message:String):HttpResponse = {
val domain = "api.pusherapp.com"
val url = "/apps/"+appId+"/channels/"+channel+"/events";
val body = message
val params = List(
("auth_key", key),
("auth_timestamp", (new Date().getTime()/1000) toInt ),
("auth_version", "1.0"),
("name", event),
("body_md5", md5(body))
).sort( (a,b) => a._1 < b._1 ).map( o => o._1+"="+WS.encode(o._2.toString) ).mkString("&");
val signature = sha256( List("POST", url, params).mkString("\n"), secret );
WS.url("http://"+domain+url+"?"+params+"&auth_signature="+WS.encode(signature)).body(body).post()
}
def byteArrayToString(data: Array[Byte]) = {
val hash = new BigInteger(1, data).toString(16);
"0"*(32-hash.length) + hash
}
def md5(s: String):String = byteArrayToString(MessageDigest.getInstance("MD5").digest(s.getBytes("US-ASCII")));
def sha256(s: String, secret: String):String = {
val mac = Mac.getInstance("HmacSHA256");
mac.init(new SecretKeySpec( secret.getBytes(), "HmacSHA256"));
val digest = mac.doFinal(s.getBytes());
String.format("%0" + (digest.length << 1) + "x", new BigInteger(1, digest));
}
}
/*
Usage example :
object WebSockets extends Pusher {
val channel = Play.configuration.getProperty("websockets.channel")
def trigger(event:String, message:String):HttpResponse = trigger(channel, event, message)
}
object Test {
def test = WebSockets.trigger("hello", "{ \"message\": \"test\" }")
}
*/
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment