2010-06-02 16 views
5

Proszę pomóc! Odsunąłem włosy od tego. :)HMAC SHA1 ColdFusion

Mam witrynę, której potrzebuję do HMAC SHA1 w celu uwierzytelnienia. Obecnie działa z innym językiem, ale teraz muszę przenieść go do ColdFusion. Dla mojego życia nie mogę dopasować strun. Każda pomoc będzie mile widziana.

danych: https%3A%2F%2Fwww%2Etestwebsite%2Ecom%3Fid%3D5447
Klucz: 265D5C01D1B4C8FA28DC55C113B4D21005BB2B348859F674977B24E0F37C81B05FAE85FB75EA9CF53ABB9A174C59D98C7A61E2985026D2AA70AE4452A6E3F2F9

Poprawna odpowiedź: WJd%2BKxmFxGWdbw4xQJZXd3%2FHkFQ%3d
Moja odpowiedź: knIVr6wIt6%2Fl7mBJPTTbwQoTIb8%3d

Oba są kodowane Base64 URL, a następnie kodowane.

+0

Najlepiej wysłać aktualny kod, który pokaże funkcję (-y), którego używasz do tego celu. –

Odpowiedz

9

Wykonuję samodzielnie urządzenie HMAC-SHA1. Najlepiej mogę powiedzieć, że znalazłem tę starą funkcję. Pracował świetnie dla tego, co robię do tej pory. Zapomniałem, gdzie go znalazłem, więc nie mogę przyznać autorowi.

Dla rzeczy Base 64 ... uruchom tę funkcję na swoim szyfrowaniu, po prostu wykonaj cfset newString = toBase64 (oldString) na zwróconych elementach.

<cffunction name="hmacEncrypt" returntype="binary" access="public" output="false"> 
    <cfargument name="signKey" type="string" required="true" /> 
    <cfargument name="signMessage" type="string" required="true" /> 
    <cfargument name="algorithm" type="string" default="HmacSHA1" /> 
    <cfargument name="charset" type="string" default="UTF-8" /> 

    <cfset var msgBytes = charsetDecode(arguments.signMessage, arguments.charset) /> 
    <cfset var keyBytes = charsetDecode(arguments.signKey, arguments.charset) /> 
    <cfset var keySpec = createObject("java","javax.crypto.spec.SecretKeySpec") /> 
    <cfset var mac = createObject("java","javax.crypto.Mac") /> 

    <cfset key = keySpec.init(keyBytes, arguments.algorithm) /> 
    <cfset mac = mac.getInstance(arguments.algorithm) /> 
    <cfset mac.init(key) /> 
    <cfset mac.update(msgBytes) /> 

    <cfreturn mac.doFinal() /> 
</cffunction> 
+1

dokładnie to, czego potrzebowałem. Dzięki. FYI: colfdusion 10 ma wbudowaną funkcję hmac(), nie jest to miłe :) – jan

1

Steve - Dziękuję za odpowiedź. Właściwie używałem już funkcji hmacEncrypt. Zrozumiałem jednak mój problem. Przechodziłem kluczem HEX zamiast łańcucha. Akceptował klucz, ponieważ technicznie był to ciąg. Aby przywrócić go do napisu, użyłem innej funkcji wraz z powyższą. Ten poniżej zmienia HEX na ciąg znaków. Nie napisałem poniższej funkcji ani nie pamiętam, skąd się wziął, aby uzyskać kredyt autora, ale działało świetnie.

<cffunction name="Hex2Bin" returntype="any" hint="Converts a Hex string to binary"> 
    <cfargument name="inputString" type="string" required="true" hint="The hexadecimal string to be written."> 
    <cfset var outStream = CreateObject("java", "java.io.ByteArrayOutputStream").init()> 
    <cfset var inputLength = Len(arguments.inputString)> 
    <cfset var outputString = ""> 
    <cfset var i = 0> 
    <cfset var ch = ""> 
    <cfif inputLength mod 2 neq 0> 
    <cfset arguments.inputString = "0" & inputString> 
    </cfif> 
    <cfloop from="1" to="#inputLength#" index="i" step="2"> 
     <cfset ch = Mid(inputString, i, 2)> 
     <cfset outStream.write(javacast("int", InputBaseN(ch, 16)))> 
    </cfloop> 
    <cfset outStream.flush()> 
    <cfset outStream.close()> 
    <cfreturn outStream.toByteArray()> 
</cffunction> 
+1

(* To było oryginalnie opublikowane jako odpowiedź, ale zostało usunięte przez mody *): "[Ronald-c] (http: // stackoverflow.com/users/475420/roland-c) powiedział: Napisałem Hex2Bin lata temu dla kogoś na liście mailingowej CFC! Podobnie jak FYI, jak z CF7, możesz teraz zrobić to: 'BinaryDecode (inputString," hex ") '. Jest znacznie prostszy (i bardziej wydajny), ponieważ dodali wbudowaną funkcję." – Leigh

4

krótsza metoda szyfrowania (na Barney's method), który generuje ciąg:

<cffunction name="CFHMAC" output="false" returntype="string"> 
    <cfargument name="signMsg" type="string" required="true" /> 
    <cfargument name="signKey" type="string" required="true" /> 
    <cfargument name="encoding" type="string" default="utf-8" /> 
    <cfset var key = createObject("java", "javax.crypto.spec.SecretKeySpec").init(signKey.getBytes(arguments.encoding), "HmacSHA1") /> 
    <cfset var mac = createObject("java", "javax.crypto.Mac").getInstance("HmacSHA1") /> 
    <cfset mac.init(key) /> 
    <cfreturn toBase64(mac.doFinal(signMsg.getBytes(arguments.encoding))) /> 
</cffunction> 

Ponadto

  1. ColdFusion 10 obsługuje HMAC-SHA1 do szyfrowania i mieszania natywny.
  2. Istnieje biblioteka o nazwie CF_HMAC distributed by Adobe
  3. Istnieje kilka bibliotek, które zajmują się HMAC w związku podczas podpisywania plików dla Amazon. Wśród nich są cf-amazon-s3, Barney's S3 URL Builder i RIAForge S3
+0

Nice. Po prostu zachowaj ostrożność przy użyciu 'String.getBytes()', ponieważ używa domyślnego kodowania (nie zawsze, co chcesz). Uczyniłbym z zestawu znaków opcjonalny parametr, domyślnie UTF-8. Następnie przekaż go do [charsetDecode] (http://help.adobe.com/en_US/ColdFusion/9.0/CFMLRef/WSc3ff6d0ea77859461172e0811cbec22c24-7f64.html) lub getBytes (charset) – Leigh

+0

FYI, ponieważ ten post wciąż pojawia się często, naprawiony kodowanie getBytes() – Leigh