Created
July 19, 2016 14:13
-
-
Save robertz/cfd7973e3700e44fe0554d98be1fb15e to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
component { | |
/* | |
Parts of this are based on Tim Dawe's | |
http://amazonsig.riaforge.org | |
and | |
Joe Danziger's Amazon S3 REST Wrapper | |
http://amazons3.riaforge.org/ | |
Written by Patrick Liess | |
Twitter: @smrchy | |
http://www.tcs.de | |
Non-SQS specific code removed and moved to CFScript | |
*/ | |
public SQSService function init() { | |
// Handle any init specific code here | |
this.awsAccessKeyID = "[awsAccessKeyID]"; | |
this.secretAccessKey = "[secretAccessKey]"; | |
this.SQSVersion = "2009-02-01"; | |
this.SQSServiceURL = "http://queue.amazonaws.com/"; | |
return this; | |
} | |
public string function sendMessage(required string queue, required string message) { | |
var reqURL = this.SQSserviceUrl & arguments.queue & | |
"?Action=SendMessage" & | |
"&MessageBody=" & URLEncodedFormat(arguments.message,"utf-8") & | |
"&Version=" & this.SQSVersion; | |
reqURL = signRequest(requrl,"GET"); | |
cfhttp(method = "GET", url = reqURL, charset = "utf-8"); | |
return cfhttp.fileContent; | |
} | |
public string function receiveMessage(required string queue) { | |
var reqURL = this.SQSServiceURL & arguments.queue & | |
"?Action=ReceiveMessage" & | |
"&AttributeName=None" & | |
"&MaxNumberOfMessages=10" & | |
"&Version=" & this.SQSVersion; | |
reqURL = signRequest(reqURL, "GET"); | |
cfhttp(method = "GET", url = reqURL, charset = "utf-8"); | |
return cfhttp.fileContent; | |
} | |
public struct function deleteMessage(required string queue, required string receiptHandle) { | |
var reqURL = this.SQSserviceUrl & arguments.queue & | |
"?Action=DeleteMessage" & | |
"&ReceiptHandle=" & URLEncodedFormat(Arguments.receipthandle,"utf-8") & | |
"&Version=" & this.SQSVersion; | |
reqURL = signRequest(requrl, "GET"); | |
cfhttp(method = "GET", url = reqURL, charset = "utf-8"); | |
return cfhttp; | |
} | |
// Utility Functions | |
public string function signRequest(required string request, string method default = "GET") { | |
var lc = {}; | |
// Extract the URL part of the request and strip the protocol | |
lc.requesturl = listfirst(arguments.request, "?"); | |
lc.requesturl = replacenocase(lc.requesturl, "http://", ""); | |
// Split into host and path | |
lc.host = listfirst(lc.requesturl, "/"); | |
lc.path = right(lc.requesturl, len(lc.requesturl) - len(lc.host)); | |
// Process the query string parameters into a structure | |
lc.querystring = listlast(arguments.request, "?"); | |
lc.strParams = {}; | |
var queryArray = listToArray(lc.queryString, "&"); | |
for (var i in queryArray) { | |
lc.strParams[listfirst(i, "=")] = urldecode(listlast(i, "=")); | |
} | |
// Add the timestamp | |
if (not StructKeyExists(lc.strParams, "Timestamp")) { | |
lc.utcdate = dateconvert("local2Utc", now()); | |
lc.strParams["Timestamp"] = dateformat(lc.utcdate, 'yyyy-mm-dd') & "T" & timeformat(lc.utcdate, 'HH:mm:ss') & "Z"; | |
} | |
// Add the standard parameters | |
lc.strParams["AWSAccessKeyId"] = this.awsAccessKeyId; | |
lc.strParams["SignatureVersion"] = 2; | |
lc.strParams["SignatureMethod"] = "HmacSHA1"; | |
// Sort the parameters | |
lc.keys = listsort(structkeylist(lc.strParams), "text"); | |
// Generate a new query string including timestamp, with parameters in the correct order, encoding as we go | |
lc.qs = ""; | |
for(i in lc.keys) { | |
lc.qs = lc.qs & rfc3986EncodedFormat(i) & "=" & rfc3986EncodedFormat(lc.strParams[i]) & "&"; | |
} | |
// Strip off the last & | |
lc.qs = left(lc.qs, len(lc.qs)-1); | |
// Build the string to sign | |
lc.stringToSign = arguments.method & chr(10); | |
lc.stringToSign = lc.stringToSign & lc.host & chr(10); | |
lc.stringToSign = lc.stringToSign & lc.path & chr(10); | |
lc.stringToSign = lc.stringToSign & lc.qs; | |
lc.signature = HMAC_SHA1(lc.stringToSign); | |
// Return the new request URL | |
return "http://" & lc.host & lc.path & "?" & lc.qs & "&Signature=" & urlencodedformat(tobase64(lc.signature)); | |
} | |
private binary function HMAC_SHA1(required string signMessage) { | |
var jMsg = JavaCast("string",arguments.signMessage).getBytes("iso-8859-1"); | |
var jKey = JavaCast("string",this.secretAccessKey).getBytes("iso-8859-1"); | |
var key = createObject("java","javax.crypto.spec.SecretKeySpec"); | |
var mac = createObject("java","javax.crypto.Mac"); | |
key = key.init(jKey,"HmacSHA1"); | |
mac = mac.getInstance(key.getAlgorithm()); | |
mac.init(key); | |
mac.update(jMsg); | |
return mac.doFinal(); | |
} | |
public string function createSignature(required string stringIn) { | |
var fixedData = replace(arguments.stringIn,"\n","#chr(10)#","all"); | |
var digest = HMAC_SHA1(fixedData); | |
var signature = toBase64(digest); | |
return signature; | |
} | |
public string function rfc3986EncodedFormat(required string text) { | |
var lc = {}; | |
lc.objNet = createObject("java","java.net.URLEncoder"); | |
lc.encodedText = lc.objNet.encode(arguments.text, 'utf-8').replace("+", "%20").replace("*", "%2A").replace("%7E", "~"); | |
return lc.encodedText; | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment