1.Java計算加密代碼如下:
public class MyClass {
public static void main(String[] args){
String str = "APP&1122322134534&AbcdeffFDDGHJDS";
String finalStr = HmacSha1.genHMAC(str, "123456");
System.out.println("finalStr:"+finalStr);// 0PGsANnMw+1yep5TlAXBLO2Ko3c=
}
}
package study.telchina.com.javatestlib;
import org.apache.commons.codec.binary.Base64;
import java.security.InvalidKeyException;
import java.security.NoSuchAlgorithmException;
import javax.crypto.Mac;
import javax.crypto.spec.SecretKeySpec;
public class HmacSha1 {
private static final String HMAC_SHA1_ALGORITHM = "HmacSHA1";
/**
* 使用 HMAC-SHA1 簽名方法對data進行簽名
*
* @param data 被簽名的字符串
* @param key 密鑰
* @return 加密後的字符串
*/
public static String genHMAC(String data, String key) {
byte[] result = null;
try {
//根據給定的字節數組構造一個密鑰,第二參數指定一個密鑰算法的名稱
SecretKeySpec signinKey = new SecretKeySpec(key.getBytes(), HMAC_SHA1_ALGORITHM);
//生成一個指定 Mac 算法 的 Mac 對象
Mac mac = Mac.getInstance(HMAC_SHA1_ALGORITHM);
//用給定密鑰初始化 Mac 對象
mac.init(signinKey);
//完成 Mac 操作
byte[] rawHmac = mac.doFinal(data.getBytes());
result = Base64.encodeBase64(rawHmac);
} catch (NoSuchAlgorithmException e) {
System.err.println(e.getMessage());
} catch (InvalidKeyException e) {
System.err.println(e.getMessage());
}
if (null != result) {
return new String(result);
} else {
return null;
}
}
}
項目引入jar包:commons-codec-1.14.jar,最終得到的計算結果是: 0PGsANnMw+1yep5TlAXBLO2Ko3c=
2.ionic中計算方式如下:
首先引入插件,執行命令如下:
然後在頁面引入
import hmacSHA1 from 'crypto-js/hmac-sha1';
import Base64 from 'crypto-js/enc-base64';
在參考他的這種方式在頁面中寫下,看下源文件中有hmacSHA1,由於java端是採用的這個算法,所以移動端必須採用這個算法,將hmacSHA2565改爲hmacSHA1
移動端頁面計算加密代碼整理如下:
var str = "APP&1122322134534&AbcdeffFDDGHJDS";
console.log("加密前:"+str);
var a = Base64.stringify(hmacSHA1(str, "123456"));
console.log("加密後:"+a);
str就是我們我加密的內容,123456 就是我們雙方約定的密鑰
移動端計算結果如下:
發現與java端計算的結果並不一致,我們在看下java代碼
注意紅框中的代碼,發現是做了一步Base64運算,調用了encodeBase64方法,而移動端調用了Base64.stringify 方法
我們再去看下Base64中的源碼如下:
發現並沒有卵用,參數都不符合,看來這個是用不了了,後來同事說統一編碼用utf-8,想了想可能是這個原因,於是更改代碼如下:
var str = "APP&1122322134534&AbcdeffFDDGHJDS";
console.log("加密前:"+str);
var a = hmacSHA1(str, "123456").toString(CryptoJS.enc.utf8);
console.log("加密後:"+a);
結果如下:
還是沒有卵用,參考Java代碼,想了想還是得和Base64掛上,於是我又稍微改了下:
var str = "APP&1122322134534&AbcdeffFDDGHJDS";
console.log("加密前:"+str);
var a = hmacSHA1(str, "123456").toString(CryptoJS.enc.Base64);
console.log("加密後:"+a);
於是奇蹟出現了:
與Java計算結果完全一致,最後在優化了下移動端的引入結果如下:
import * as CryptoJS from 'crypto-js/crypto-js';
var str = "APP&1122322134534&AbcdeffFDDGHJDS";
console.log("加密前:"+str);
var a = CryptoJS.HmacSHA1(str, "123456").toString(CryptoJS.enc.Base64);
console.log("加密後:"+a);
針對字母特殊字符數字的組合加密已經測試正常,完全滿足了項目的需求,稍微試了下針對中文的加密移動端與Java端並不完全一致,由於沒這個需求就沒在繼續探究下去,當然保底方案是寫到我們自己開發的cordova插件中去調用,目前裏面已經封裝了三個方法,也不差在多一個哈哈