Java非对称加密算法--RSA加密算法

Java非对称加密算法--RSA加密算法

         RSA加密算法是一种非对称加密算法。在公开密钥加密和电子商业中RSA被广泛使用。RSA是1977年由罗纳德·李维斯特(Ron Rivest)、阿迪·萨莫尔(Adi Shamir)和伦纳德·阿德曼(Leonard Adleman)一起提出的。当时他们三人都在麻省理工学院工作。RSA就是他们三人姓氏开头字母拼在一起组成的。

1973年,在英国政府通讯总部工作的数学家克利福德·柯克斯(Clifford Cocks)在一个内部文件中提出了一个相同的算法,但他的发现被列入机密,一直到1997年才被发表。

对极大整数做因数分解的难度决定了RSA算法的可靠性。换言之,对一极大整数做因数分解愈困难,RSA算法愈可靠。假如有人找到一种快速因数分解的算法的话,那么用RSA加密的信息的可靠性就肯定会极度下降。但找到这样的算法的可能性是非常小的。今天只有短的RSA钥匙才可能被强力方式解破。到2013年为止,世界上还没有任何可靠的攻击RSA算法的方式。只要其钥匙的长度足够长,用RSA加密的信息实际上是不能被解破的。

下面我是采用Bouncy Castle实现的RSA加密算法。Bouncy
Castle
是一种用于 Java 平台的开放源码的轻量级密码术包。它支持大量的密码术算法,并提供 JCE 1.2.1 的实现。因为 Bouncy Castle 被设计成轻量级的,所以从 J2SE 1.4 到 J2ME(包括 MIDP)平台,它都可以运行。它是在 MIDP 上运行的唯一完整的密码术包。

<span style="font-size:14px;">package com.qiuzhping.rsa;

import org.bouncycastle.jce.provider.BouncyCastleProvider;

import java.io.ByteArrayOutputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.security.KeyPair;
import java.security.KeyPairGenerator;
import java.security.NoSuchAlgorithmException;
import java.security.PrivateKey;
import java.security.PublicKey;
import java.security.SecureRandom;

import javax.crypto.Cipher;

/**
 * 非对称加密是公钥加密,私钥来解密.使用的是Bouncy Castle 是一种用于 Java 平台的开放源码的轻量级密码术包.
 * 1、此Demo使用的是bcprov-ext-jdk15on-152.jar
 * 2、把jar文件复制到 $JAVA_HOME$\jre\lib\ext目录下面
 * 3、修改配置文件\jre\lib\security\java.security
 * security.provider.1=sun.security.provider.Sun
 * security.provider.2=sun.security.rsa.SunRsaSign
 * security.provider.3=com.sun.net.ssl.internal.ssl.Provider
 * security.provider.4=com.sun.crypto.provider.SunJCE
 * security.provider.5=sun.security.jgss.SunProvider
 * security.provider.6=com.sun.security.sasl.Provider
 * security.provider.7=org.jcp.xml.dsig.internal.dom.XMLDSigRI
 * security.provider.8=sun.security.smartcardio.SunPCSC 上述8个是JDK已经实现了的加密方式. 将
 * security.provider.9=org.bouncycastle.jce.provider.BouncyCastleProvider 添加到后面.
 * 非对称加密称为公钥加密,算法更加复杂,速度慢,加密和解密钥匙不相同,任何人都可以知道公钥,只有一个人持有私钥可以解密。
 *
 * @author Peter.Qiu
 *
 */
public class RsaUtil {

	/**
	 * 根据publicKey 对data进行加密.
	 *
	 * @param publicKey
	 * @param data
	 * @throws Exception
	 * @author Peter.Qiu
	 */
	public static byte[] encryptMode(PublicKey publicKey, byte[] data)
			throws Exception {
		try {
			Cipher cipher = Cipher.getInstance("RSA",
					new BouncyCastleProvider());
			cipher.init(Cipher.ENCRYPT_MODE, publicKey);// ENCRYPT_MODE 加密
			int blockSize = cipher.getBlockSize();
			int outputSize = cipher.getOutputSize(data.length);
			int leavedSize = data.length % blockSize;
			int blocksSize = leavedSize != 0 ? data.length / blockSize + 1
					: data.length / blockSize;
			byte[] raw = new byte[outputSize * blocksSize];
			int i = 0;
			while (data.length - i * blockSize > 0) {
				if (data.length - i * blockSize > blockSize) {
					cipher.doFinal(data, i * blockSize, blockSize, raw, i
							* outputSize);
				} else {
					cipher.doFinal(data, i * blockSize, data.length - i
							* blockSize, raw, i * outputSize);
				}
				i++;
			}
			return raw;
		} catch (Exception e) {
			throw e;
		}
	}

	/**
	 * 根据privateKey 对data进行解密.
	 *
	 * @param privateKey
	 * @param data
	 * @throws Exception
	 * @author Peter.Qiu
	 */
	public static byte[] decryptMode(PrivateKey privateKey, byte[] data)
			throws Exception {
		Cipher cipher = Cipher.getInstance("RSA", new BouncyCastleProvider());
		cipher.init(Cipher.DECRYPT_MODE, privateKey);// DECRYPT_MODE 解密
		int blockSize = cipher.getBlockSize();
		ByteArrayOutputStream bout = new ByteArrayOutputStream(64);
		int j = 0;

		while (data.length - j * blockSize > 0) {
			bout.write(cipher.doFinal(data, j * blockSize, blockSize));
			j++;
		}
		return bout.toByteArray();
	}

	/**
	 * 获取密钥.
	 *
	 * @param rsaKeyStore
	 * @return
	 * @throws Exception
	 * @author Peter.Qiu
	 */
	public static KeyPair getKeyPair(String rsaKeyStore) throws Exception {
		FileInputStream fis = new FileInputStream(rsaKeyStore);
		ObjectInputStream oos = new ObjectInputStream(fis);
		KeyPair kp = (KeyPair) oos.readObject();
		oos.close();
		fis.close();
		return kp;
	}

	/**
	 * 将密钥写入文件.
	 *
	 * @param kp
	 * @param path
	 * @throws Exception
	 * @author Peter.Qiu
	 */
	public static void saveKeyPair(KeyPair kp, String path) throws Exception {
		File file = new File(path);
		if (!file.exists() || file.isDirectory()) {
			file.createNewFile();
		}
		FileOutputStream fos = new FileOutputStream(path);
		ObjectOutputStream oos = new ObjectOutputStream(fos);
		// 生成密钥
		oos.writeObject(kp);
		oos.close();
		fos.close();
	}

	/**
	 * 用于生成公匙或私匙.
	 *
	 * @return
	 * @throws NoSuchAlgorithmException
	 * @author Peter.Qiu
	 */
	public static KeyPair generateKeyPair() throws NoSuchAlgorithmException {

		SecureRandom sr = new SecureRandom();
		KeyPairGenerator kg = KeyPairGenerator.getInstance("RSA",
				new BouncyCastleProvider());
		// 注意密钥大小最好为1024,否则解密会有乱码情况.
		kg.initialize(1024, sr);
		KeyPair genKeyPair = kg.genKeyPair();
		return genKeyPair;

	}

	/**
	 * 将公密或私密写入文件.
	 *
	 * @param obj
	 * @param path
	 * @throws Exception
	 * @author Peter.Qiu
	 */
	public static void saveFile(Object obj, String path) throws Exception {
		File file = new File(path);
		if (!file.exists() || file.isDirectory()) {
			file.createNewFile();
		}
		FileOutputStream fos = new FileOutputStream(path);
		ObjectOutputStream oos = new ObjectOutputStream(fos);
		// 生成密钥
		oos.writeObject(obj);
		oos.close();
		fos.close();
	}

	/**
	 * 获取公密.
	 *
	 * @param publicKeyPath
	 * @return
	 * @throws Exception
	 * @author Peter.Qiu
	 */
	public static PublicKey getPublicKey(String publicKeyPath) throws Exception {
		FileInputStream fis = new FileInputStream(publicKeyPath);
		ObjectInputStream oos = new ObjectInputStream(fis);
		PublicKey kp = (PublicKey) oos.readObject();
		oos.close();
		fis.close();
		return kp;
	}

	/**
	 * 获取私密.
	 *
	 * @param privateKeyPath
	 * @return
	 * @throws Exception
	 * @author Peter.Qiu
	 */
	public static PrivateKey getPrivateKey(String privateKeyPath)
			throws Exception {
		FileInputStream fis = new FileInputStream(privateKeyPath);
		ObjectInputStream oos = new ObjectInputStream(fis);
		PrivateKey kp = (PrivateKey) oos.readObject();
		oos.close();
		fis.close();
		return kp;
	}

	public static void main(String[] args) throws Exception {
		File dir = new File("./key/");
		if (!dir.exists()) {
			dir.mkdir();
		}
		// 获取公匙及私匙
		KeyPair generateKeyPair = getKeyPair("./key/key");

		// 生成公钥及私钥
		// generateKeyPair = generateKeyPair();

		// 存储KeyPair到本地用于后期解密 注意修改前台RSAKeyPair
		// saveKeyPair(generateKeyPair,"./key/key");

		System.out.println("generateKeyPair : " + generateKeyPair);
		// 公匙 用于前台加密
		PublicKey publicKey = null;// generateKeyPair.getPublic();
		publicKey = getPublicKey("./key/publicKey.key");
		System.out.println("publicKey:" + publicKey);
		// saveFile(publicKey,"./key/publicKey.key");
		// 私匙 存储在后台用于解密
		PrivateKey privateKey = null;// generateKeyPair.getPrivate(); //
		privateKey = getPrivateKey("./key/privateKey.key");//
		System.out.println("privateKey:" + privateKey);
		// saveFile(privateKey,"./key/privateKey.key");

		// 测试加密解密
		String test = "saaaa";
		test = "Peter.Qiu丘丘丘邱";
		System.out.println("加密前字符:" + test);
		byte[] en_test = encryptMode(publicKey, test.getBytes("UTF-8"));
		System.out.println("加密后字符:" + new String(en_test));

		byte[] de_test = decryptMode(privateKey, en_test);
		System.out.println("解密后字符:" + new String(de_test, "UTF-8"));

	}

}</span>

转摘请注明:http://blog.csdn.net/qiuzhping/article/details/44344373

效果图:

对应完整的项目:http://download.csdn.net/detail/qiu_11/8509319

时间: 2024-10-07 09:42:00

Java非对称加密算法--RSA加密算法的相关文章

Java培训 关于RSA加密算法有哪些应用呢?

Java培训 关于RSA加密算法有哪些应用呢? RSA加密算法是目前最有影响力的公钥加密算法,它能够抵抗到目前为止已知的绝大多数密码攻击. Java培训关于RSA加密算法有哪些应用呢?以下举一个数据库身份验证的案例. 在使用数据集进行身份认证时,密码存在数据库中,认证时用户输入的密码与数据库中密码相同则认证通过,若数据库被破解了则对系统造成威胁,怎样保证系统安全呢?这里就可以应用RSA加密算法,对权限加密. 思路: 就是在url中传用户名密码时,先把用户名进行翻转,然后再进行加密,如输入的密码为

java 非对称加密RSA

package com.aarony.test; import java.io.IOException; import java.security.KeyFactory; import java.security.KeyPair; import java.security.KeyPairGenerator; import java.security.NoSuchAlgorithmException; import java.security.PrivateKey; import java.sec

轻松学习RSA加密算法原理

以前也接触过RSA加密算法,感觉这个东西太神秘了,是数学家的事,和我无关.但是,看了很多关于RSA加密算法原理的资料之后,我发现其实原理并不是我们想象中那么复杂,弄懂之后发现原来就只是这样而已.. 学过算法的朋友都知道,计算机中的算法其实就是数学运算.所以,再讲解RSA加密算法之前,有必要了解一下一些必备的数学知识.我们就从数学知识开始讲解. 必备数学知识 RSA加密算法中,只用到素数.互质数.指数运算.模运算等几个简单的数学知识.所以,我们也需要了解这几个概念即可. 素数 素数又称质数,指在一

Java 加密解密 对称加密算法 非对称加密算法 MD5 BASE64 AES RSA

[前言] 本文简单的介绍了加密技术相关概念,最后总结了java中现有的加密技术以及用法和样例 [最简单的加密] 1.简单的概念 明文:加密前的信息 密文:机密后的信息 算法:加密或解密的算法 密钥:算法使用的钥匙(读作miyao.正确应该是miyue,可是大家都读miyao) 2.简单的样例 将123456每位数字都加1后得到234567, 当中123456就是明文.234567就是密文.加密密钥就是1,加密算法是每位加 3.对称加密和非对称加密 以上为例. 123456-->234567的加密

Java加密技术(四)非对称加密算法RSA

RSA  这种算法1978年就出现了,它是第一个既能用于数据加密也能用于数字签名的算法.它易于理解和操作,也很流行.算法的名字以发明者的名字命名:Ron Rivest, AdiShamir 和Leonard Adleman. 这种加密算法的特点主要是密钥的变化,上文我们看到DES只有一个密钥.相当于只有一把钥匙,如果这把钥匙丢了,数据也就不安全了.RSA同时有两把钥匙,公钥与私钥.同时支持数字签名.数字签名的意义在于,对传输过来的数据进行校验.确保数据在传输工程中不被修改. 流程分析: 甲方构建

JAVA 非对称加密算法RSA

非对称加密算法 RSA过程 : 以甲乙双方为例 1.初始化密钥 构建密钥对,生成公钥.私钥保存到keymap中 KeyPairGenerator ---> KeyPair --> RSAPublicKey.RSAPrivateKey 2.甲方使用私钥加密, 加密后在用私钥对加密数据进行数据签名,然后发送给乙方 RSACoder.encryptByPrivateKey(data, privateKey); RSACoder.sign(encodedData, privateKey); 3.乙方则

Java加密算法 RSA

Java加密算法 RSA 2015-06-06 08:44 511人阅读 评论(0) 收藏 举报  分类: JAVA(57)  公钥加密也称为非对称加密.速度慢.加密和解密的钥匙不相同,某一个人持有私钥,任何人都可以知道公钥 [java] view plaincopy package com.stone.security; import java.security.KeyPair; import java.security.KeyPairGenerator; import java.securi

java RSA加密算法

[转]RSA加密算法 RSA公钥加密算法是1977年由Ron Rivest.Adi Shamirh和LenAdleman在(美国麻省理工学院)开发的.RSA取名来自开发他们三者的名字.RSA是目前最有影响力的公钥加密算法,它能够抵抗到目前为止已知的所有密码攻击,已被ISO推荐为公钥数据加密标准.RSA算法基于一个十分简单的数论事实:将两个大素数相乘十分容易,但那时想要对其乘积进行因式分解却极其困难,因此可以将乘积公开作为加密密钥. RSA公开密钥密码体制.所谓的公开密钥密码体制就是使用不同的加密

Java使用RSA加密算法对内容进行加密

什么是RSA加密算法 RSA是一种典型的非对称性加密算法,具体介绍可参考阮一峰的日志 RSA算法原理 下面是使用RSA算法对传输内容进行加密的一个简要Java案例,主要用到了三个类,大体实现如下: 对内容进行RSA加密和解密校验的类 import java.security.KeyFactory; import java.security.PrivateKey; import java.security.PublicKey; import java.security.spec.PKCS8Enco