1 /**2 * eagle-daiq 2017-05-283 * RSA算法实现类, 细节见单元测试RSACoderTest类4 *
5 * 使用方式:6 * RSACoder rsaCoder = new RSACoder();7 * //初始化 秘钥8 * rsaCoder.initKeyFromFile("cqfaeuser.cer","cqfaeuser.jks","cqfaeuser","123456");9 * String publicKey = rsaCoder.getPublicKey();//取公钥,base64编码10 * String privateKey = rsaCoder.getPrivateKey();//取私钥, base64编码11 * //公钥加密12 * byte[] encodedData = rsaCoder.encryptByPublicKey(data, publicKey);13 * //私钥解密14 * byte[] decodedData = rsaCoder.decryptByPrivateKey(encodedData,privateKey);15 *
16 */17 public class RSACoder {
18 public static final String KEY_ALGORITHM = KeyAlgorithmEnu.RSA.getName();
19 public static final String SIGNATURE_ALGORITHM = KeyAlgorithmEnu.MD5withRSA.getName();
20
21 private static final String PUBLIC_KEY = "RSAPublicKey";
22 private static final String PRIVATE_KEY = "RSAPrivateKey";
23 private Map keyMap = new HashMap<>();
24
25 public RSACoder() {
26 }
27
28 public RSACoder(String publicKeyFile,String keyStoreFile,String alias,String password) {
29 this.initKeyFromFile(publicKeyFile,keyStoreFile,alias,password);
30 }
31
32 /**33 * 用私钥对信息生成数字签名34 *35 *@paramdata36 * 加密数据37 *@paramprivateKey38 * 私钥 base64编码39 *40 *@return41 *@throwsException42 */
43 public String sign(byte[] data, String privateKey) throws Exception {
44 //解密由base64编码的私钥45 byte[] keyBytes = Base64Utils.decryptBASE64(privateKey);
46
47 //构造PKCS8EncodedKeySpec对象48 PKCS8EncodedKeySpec pkcs8KeySpec = new PKCS8EncodedKeySpec(keyBytes);
49
50 //KEY_ALGORITHM 指定的加密算法51 KeyFactory keyFactory = KeyFactory.getInstance(KEY_ALGORITHM);
52
53 //取私钥匙对象54 PrivateKey priKey = keyFactory.generatePrivate(pkcs8KeySpec);
55
56 //用私钥对信息生成数字签名57 Signature signature = Signature.getInstance(SIGNATURE_ALGORITHM);
58 signature.initSign(priKey);
59 signature.update(data);
60
61 return Base64Utils.encryptBASE64(signature.sign());
62 }
63
64 /**65 * 校验数字签名66 *67 *@paramdata68 * 加密数据69 *@parampublicKey70 * 公钥 base64编码71 *@paramsign72 * 数字签名73 *74 *@return校验成功返回true 失败返回false75 *@throwsException76 *77 */
78 public boolean verify(byte[] data, String publicKey, String sign)
79 throws Exception {
80
81 //解密由base64编码的公钥82 byte[] keyBytes = Base64Utils.decryptBASE64(publicKey);
83
84 //构造X509EncodedKeySpec对象85 X509EncodedKeySpec keySpec = new X509EncodedKeySpec(keyBytes);
86
87 //KEY_ALGORITHM 指定的加密算法88 KeyFactory keyFactory = KeyFactory.getInstance(KEY_ALGORITHM);
89
90 //取公钥匙对象91 PublicKey pubKey = keyFactory.generatePublic(keySpec);
92
93 Signature signature = Signature.getInstance(SIGNATURE_ALGORITHM);
94 signature.initVerify(pubKey);
95 signature.update(data);
96
97 //验证签名是否正常98 return signature.verify(Base64Utils.decryptBASE64(sign));
99 }
100
101 /**102 * 解密
103 * 用私钥解密104 *105 *@paramdata106 *@paramkey base64编码107 *@return108 *@throwsException109 */
110 public byte[] decryptByPrivateKey(byte[] data, String key)
111 throws Exception {
112 //对密钥解密113 byte[] keyBytes = Base64Utils.decryptBASE64(key);
114
115 //取得私钥116 PKCS8EncodedKeySpec pkcs8KeySpec = new PKCS8EncodedKeySpec(keyBytes);
117 KeyFactory keyFactory = KeyFactory.getInstance(KEY_ALGORITHM);
118 Key privateKey = keyFactory.generatePrivate(pkcs8KeySpec);
119
120 //对数据解密121 Cipher cipher = Cipher.getInstance(keyFactory.getAlgorithm());
122 cipher.init(Cipher.DECRYPT_MODE, privateKey);
123
124 return cipher.doFinal(data);
125 }
126
127 /**128 * 解密
129 * 用公钥解密130 *131 *@paramdata132 *@paramkey base64编码133 *@return134 *@throwsException135 */
136 public byte[] decryptByPublicKey(byte[] data, String key)
137 throws Exception {
138 //对密钥解密139 byte[] keyBytes = Base64Utils.decryptBASE64(key);
140
141 //取得公钥142 X509EncodedKeySpec x509KeySpec = new X509EncodedKeySpec(keyBytes);
143 KeyFactory keyFactory = KeyFactory.getInstance(KEY_ALGORITHM);
144 Key publicKey = keyFactory.generatePublic(x509KeySpec);
145
146 //对数据解密147 Cipher cipher = Cipher.getInstance(keyFactory.getAlgorithm());
148 cipher.init(Cipher.DECRYPT_MODE, publicKey);
149
150 return cipher.doFinal(data);
151 }
152
153 /**154 * 加密
155 * 用公钥加密156 *157 *@paramdata158 *@paramkey base64编码159 *@return160 *@throwsException161 */
162 public byte[] encryptByPublicKey(byte[] data, String key)
163 throws Exception {
164 //对公钥解密165 byte[] keyBytes = Base64Utils.decryptBASE64(key);
166
167 //取得公钥168 X509EncodedKeySpec x509KeySpec = new X509EncodedKeySpec(keyBytes);
169 KeyFactory keyFactory = KeyFactory.getInstance(KEY_ALGORITHM);
170 Key publicKey = keyFactory.generatePublic(x509KeySpec);
171
172 //对数据加密173 Cipher cipher = Cipher.getInstance(keyFactory.getAlgorithm());
174 cipher.init(Cipher.ENCRYPT_MODE, publicKey);
175
176 return cipher.doFinal(data);
177 }
178
179 /**180 * 加密
181 * 用私钥加密182 *183 *@paramdata184 *@paramkey base64编码185 *@return186 *@throwsException187 */
188 public byte[] encryptByPrivateKey(byte[] data, String key)
189 throws Exception {
190 //对密钥解密191 byte[] keyBytes = Base64Utils.decryptBASE64(key);
192
193 //取得私钥194 PKCS8EncodedKeySpec pkcs8KeySpec = new PKCS8EncodedKeySpec(keyBytes);
195 KeyFactory keyFactory = KeyFactory.getInstance(KEY_ALGORITHM);
196 Key privateKey = keyFactory.generatePrivate(pkcs8KeySpec);
197
198 //对数据加密199 Cipher cipher = Cipher.getInstance(keyFactory.getAlgorithm());
200 cipher.init(Cipher.ENCRYPT_MODE, privateKey);
201
202 return cipher.doFinal(data);
203 }
204
205 /**206 * 取得私钥,base64编码207 *208 *@return209 *@throwsException210 */
211 public String getPrivateKey()
212 throws Exception {
213 Key key = (Key) keyMap.get(PRIVATE_KEY);
214
215 return Base64Utils.encryptBASE64(key.getEncoded());
216 }
217
218 /**219 * 取得公钥,base64编码220 *221 *@return222 *@throwsException223 */
224 public String getPublicKey()
225 throws Exception {
226 Key key = (Key) keyMap.get(PUBLIC_KEY);
227
228 return Base64Utils.encryptBASE64(key.getEncoded());
229 }
230
231 /**232 * 从文件加载base64的公钥串233 *@see#loadPublicKeyByFile(String)234 *@paramfilePath235 *@return236 */
237 public String loadBase64PublicKeyByFile(String filePath){
238 return Base64Utils.encryptBASE64(loadPublicKeyByFile(filePath).getEncoded());
239 }
240
241 /**242 * 从文件加载公钥243 *@paramfilepath244 *@return245 */
246 public PublicKey loadPublicKeyByFile(String filepath) {
247 try {
248 //通过证书,获取公钥249 CertificateFactory cf = CertificateFactory.getInstance("X.509");
250 Certificate c = cf.generateCertificate(FileUtils.getFileStream(filepath));
251 PublicKey publicKey = c.getPublicKey();
252 return publicKey;
253 } catch (Exception e) {
254 throw new RuntimeException(String.format("公钥数据流file=%s读取错误",filepath),e);
255 }
256 }
257
258 /**259 * 从文件加载base64私钥串260 *@see#loadBase64PrivateKeyByFile(String, String, String)261 *@paramfilepath262 *@paramalias263 *@parampassword264 *@return265 */
266 public String loadBase64PrivateKeyByFile(String filepath, String alias, String password){
267 return Base64Utils.encryptBASE64(loadPrivateKeyByFile(filepath,alias,password).getEncoded());
268 }
269 /**270 * 从文件加载私钥271 *@paramfilepath java 私钥库文件272 *@paramalias 私钥别名273 *@parampassword 私钥密码274 *@return275 */
276 public PrivateKey loadPrivateKeyByFile(String filepath, String alias, String password){
277 try {
278 KeyStore ks= KeyStore.getInstance("JKS");
279 ks.load(FileUtils.getFileStream(filepath), password.toCharArray());
280
281 PrivateKey privateKey = (PrivateKey)ks.getKey(alias, password.toCharArray());
282 return privateKey;
283 } catch (Exception e) {
284 throw new RuntimeException(String.format("私钥数据流[file=%s,alias=%s]读取错误",filepath,alias),e);
285 }
286 }
287
288 /**289 * 初始化密钥 - 程序自动生成公私秘钥290 *291 *@return292 *@throwsException293 */
294 public void initDefaultKey() throws Exception {
295 KeyPairGenerator keyPairGen = KeyPairGenerator
296 .getInstance(KEY_ALGORITHM);
297 keyPairGen.initialize(2048);
298
299 KeyPair keyPair = keyPairGen.generateKeyPair();
300
301 //公钥302 RSAPublicKey publicKey = (RSAPublicKey) keyPair.getPublic();
303
304 //私钥305 RSAPrivateKey privateKey = (RSAPrivateKey) keyPair.getPrivate();
306
307
308 keyMap.put(PUBLIC_KEY, publicKey);
309 keyMap.put(PRIVATE_KEY, privateKey);
310 }
311
312 /**313 * 从文件初始化公私秘钥314 *@parampublicKeyFile 公钥文件315 *@paramkeyStoreFile 秘钥库文件316 *@paramalias 秘钥别名317 *@parampassword 秘钥库密码318 */
319 public void initKeyFromFile(String publicKeyFile,String keyStoreFile,String alias,String password){
320 keyMap.put(PUBLIC_KEY, this.loadPublicKeyByFile(publicKeyFile));
321 keyMap.put(PRIVATE_KEY, this.loadPrivateKeyByFile(keyStoreFile,alias,password));
322 }
323