RSA+SHA256+BASE64对数据进行加密解密及校验
2023年7月27日发(作者:)
RSA+SHA256+BASE64对数据进⾏加密解密及校验#需求需要实现加密的认证机制##认证原理a) 密钥分配:RSA算法通过⼯具或⽅法调⽤⽣成公钥和私钥(1024bit),请求端使⽤公钥,服务端使⽤私钥。b) 加密⽅式:请求端通过密钥分配获取公钥,根据RSA加密算法将进⾏哈希后的明⽂请求进⾏公钥加密⽣成token;服务端通过密钥分配获取私钥,根据RSA解密算法将请求端的token进⾏私钥解密。c) 认证⽅式:在服务端,如果明⽂请求的哈希值和私钥解密后信息的哈希值是⼀致的,则认为认证成功,完成授权。d) 数据传输:RSA加密⽣成的是乱码,为了传输,将数据进⾏Base64封装,服务端收到之后进⾏解封装。##认证流程a) 请求端的认证流程,如下图所⽰:b) 服务端的认证流程,如下图所⽰:c) 整体流程#编码⽅法的实现Commons codec,是项⽬中⽤来处理常⽤的编码⽅法的⼯具类包,例如DES、SHA1、MD5、Base64,URL,Soundx等等。不仅是编码,也可⽤于解码。其中MD5/SHA是不可逆算法,BASE64是可逆算法。⽬前最新版本是1.11。RSA不在commons codec⾥。##RSA的实现import ;import ty.*;import vateKey;import licKey;import 8EncodedKeySpec;import .X509EncodedKeySpec;import p;import ;public class RSAUtils { /** * 获取公钥的key */ private static final String PUBLIC_KEY = "RSAPublicKey"; /** * 获取私钥的key */ private static final String PRIVATE_KEY = "RSAPrivateKey"; /** * 随机⽣成密钥对 */ public static Map genKeyPair() { // KeyPairGenerator类⽤于⽣成公钥和私钥对,基于RSA算法⽣成对象 KeyPairGenerator keyPairGen = null; try { keyPairGen = tance("RSA"); } catch (Exception e) { tackTrace(); } // 初始化密钥对⽣成器,密钥⼤⼩为96-1024位 lize(1024,new SecureRandom()); // ⽣成⼀个密钥对,保存在keyPair中 KeyPair keyPair = teKeyPair(); // 得到私钥 RSAPrivateKey privateKey = (RSAPrivateKey) vate(); // 得到公钥 RSAPublicKey publicKey = (RSAPublicKey) lic(); try { // 使⽤Base64对公钥加密得到字符串 String publicKeyString = (oded()); // 使⽤Base64对私钥加密得到字符串 String privateKeyString = (oded()); Map keyMap = new HashMap(2); (PUBLIC_KEY, publicKeyString); (PRIVATE_KEY, privateKeyString); return keyMap; } catch (Exception e) { tackTrace(); return null; } } /** * 从字符串中加载公钥 * @param publicKeyStr 公钥数据字符串 * @return RSAPublicKey 加载出来的公钥 * @exception Exception 加载公钥时产⽣的异常 */ public static RSAPublicKey loadPublicKeyByStr(String publicKeyStr) throws Exception { try { byte[] buffer = (publicKeyStr); KeyFactory keyFactory = tance("RSA"); X509EncodedKeySpec keySpec = new X509EncodedKeySpec(buffer); return (RSAPublicKey) tePublic(keySpec); } catch (Exception e) { throw new Exception(e); } } /** /** * 从字符串中加载私钥 * @param privateKeyStr 私钥数据字符串 * @return RSAPublicKey 加载出来的私钥 * @exception Exception 加载私钥时产⽣的异常 */ public static RSAPrivateKey loadPrivateKeyByStr(String privateKeyStr) throws Exception { try { byte[] buffer = (privateKeyStr); PKCS8EncodedKeySpec keySpec = new PKCS8EncodedKeySpec(buffer); KeyFactory keyFactory = tance("RSA"); return (RSAPrivateKey) tePrivate(keySpec); } catch (Exception e) { throw new Exception(e); } } /** * 公钥加密过程 * @param publicKey 公钥 * @param plainTextData 明⽂数据 * @return byte[] 加密结果 * @throws Exception 加密过程中的异常信息 */ public static byte[] encrypt(RSAPublicKey publicKey, byte[] plainTextData) throws Exception { if (publicKey == null) { throw new Exception("加密公钥为空, 请设置"); } Cipher cipher = null; try { // 使⽤默认RSA cipher = tance("RSA"); (T_MODE, publicKey); byte[] output = l(plainTextData); return output; } catch (Exception e) { throw new Exception(e); } } /** * 私钥加密过程 * @param privateKey 私钥 * @param plainTextData 明⽂数据 * @return byte[] 加密结果 * @throws Exception 加密过程中的异常信息 */ public static byte[] encrypt(RSAPrivateKey privateKey, byte[] plainTextData) throws Exception { if (privateKey == null) { throw new Exception("加密私钥为空, 请设置"); } Cipher cipher = null; try { // 使⽤默认RSA cipher = tance("RSA"); (T_MODE, privateKey); byte[] output = l(plainTextData); return output; } catch (Exception e) { throw new Exception(e); } } /** * 私钥解密过程 * 私钥解密过程 * @param privateKey 私钥 * @param cipherData 密⽂数据 * @return 明⽂ * @throws Exception 解密过程中的异常信息 */ public static byte[] decrypt(RSAPrivateKey privateKey, byte[] cipherData) throws Exception { if (privateKey == null) { throw new Exception("解密私钥为空, 请设置"); } Cipher cipher = null; try { // 使⽤默认RSA cipher = tance("RSA"); // cipher= tance("RSA", new BouncyCastleProvider()); (T_MODE, privateKey); byte[] output = l(cipherData); return output; } catch (Exception e) { throw new Exception(e); } } /** * 公钥解密过程 * @param publicKey 公钥 * @param cipherData 密⽂数据 * @return 明⽂ * @throws Exception 解密过程中的异常信息 */ public static byte[] decrypt(RSAPublicKey publicKey, byte[] cipherData) throws Exception { if (publicKey == null) { throw new Exception("解密公钥为空, 请设置"); } Cipher cipher = null; try { // 使⽤默认RSA cipher = tance("RSA"); // cipher= tance("RSA", new BouncyCastleProvider()); (T_MODE, publicKey); byte[] output = l(cipherData); return output; } catch (Exception e) { throw new Exception(e); } } /** * 获取私钥 * @param keyMap 密钥对 * @return * @throws Exception */ public static String getPrivateKey(Map keyMap) throws Exception { String privateKey = (PRIVATE_KEY); return privateKey; } /** * 获取公钥 * @param keyMap 密钥对 * @return * @throws Exception * @throws Exception */ public static String getPublicKey(Map keyMap) throws Exception { String publicKey = (PUBLIC_KEY); return publicKey; }}##SHA256与Base64实现包有这两个算法的实现,分别如下:###SHA256import Utils;public class SHA256Utils { /** * sha256加密 * */ public static String sha256Hex(String data){ return 256Hex(data); }}###Base64import 64;public class Base64Utils{ /** * 使⽤Base64加密字符串 * @return 加密之后的字符串 * @exception Exception */ public static String encode(byte[] data){ Base64 base64 = new Base64(); String encodedData = AsString(data); return encodedData; } /** * 使⽤Base64解密 * @return 解密之后的字符串 * @exception Exception */ public static byte[] decode(String data){ Base64 base64 = new Base64(); byte[] decodedData = Base64(data); return decodedData; }}#Springmvc的实现当前端对服务端进⾏调⽤时,需要在springmvc中编写⼀个拦截器,实现⼀个class继承HandlerInterceptorAdapter,并重写preHandle函数,实现如下:在dispatcher中添加拦截器: ##拦截器代码实现import tyInterceptor;import il;import ;import Factory;import rInterceptorAdapter;import 64;import rvletRequest;import rvletResponse;import vateKey;import .*;public class tokenInterceptor extends HandlerInterceptorAdapter { private static final Logger logger = ger(); public tokenInterceptor() { } private String getPrivateValues(byte[] decodeByte) throws Exception{ String privateKeyString = ("eKey"); RSAPrivateKey privateKey = ivateKeyByStr(privateKeyString); ("[tokenInterceptor getPrivateValues] : privateKey = %s.", privateKey); //私钥解密 byte[] decodedData = t(privateKey, decodeByte); String token = new String(decodedData); return token; } /* * 使⽤拦截器在客户端访问之前对请求的数据进⾏校验 */ public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception { String token = ""; String serviceToken = ""; String requestValues = ""; String requestUrl = uestURL().toString();//得到请求的URL地址 requestValues += requestUrl; Map params = ameterMap();//得到所有请求的参数 Iterator it = ().iterator(); /*获取URL+body的字符串集合*/ while(t()){ String paramName = (String) (); String paramValue = ameter(paramName); requestValues += paramName; requestValues += paramValue; } /*获取token,并对token做base64解码*/ Enumeration reqHeadInfos = derNames();//获取所有的请求头 while (eElements()) { token = der("Authorization");//根据请求头的名字获取token的值 break; } /*如果没有添加token,默认不进⾏校验*/ if (null == token) { return dle(request, response, handler); } byte[] decodeByte = Base64(token); /*获取私钥解密之后的token值*/ token = getPrivateValues(decodeByte); serviceToken = 256Hex(requestValues); if (!(token)) {//判断两次的token值是否相同 return false; } return dle(request, response, handler); }}
发布者:admin,转转请注明出处:http://www.yc00.com/news/1690460799a352575.html
评论列表(0条)