数字签名算法:
签名
数字签名---带有密钥(公钥,私钥)的消息摘要算法
验证数据完整性,认证数据来源,抗否认
OSI参考模型
私钥签名,公钥验证
RSA,DSA,ECDSA
1.jdk实现RSA消息摘要算法
package com.samlai.security.digitalSignature;
import java.security.KeyFactory;
import java.security.KeyPair;
import java.security.KeyPairGenerator;
import java.security.NoSuchAlgorithmException;
import java.security.PrivateKey;
import java.security.PublicKey;
import java.security.Signature;
import java.security.interfaces.RSAPrivateKey;
import java.security.interfaces.RSAPublicKey;
import java.security.spec.PKCS8EncodedKeySpec;
import java.security.spec.X509EncodedKeySpec;
import org.apache.commons.codec.binary.Base64;
import org.apache.commons.codec.binary.Hex;
public class RSASignature {
private static String STR = "one type of security:RSA Signature";
public static void main(String[] args) {
jdkRSA();
}
private static void jdkRSA() {
try {
//初始化密钥对
KeyPairGenerator keyPairGenerator=KeyPairGenerator.getInstance("RSA");
keyPairGenerator.initialize(512);
KeyPair keyPair=keyPairGenerator.generateKeyPair();
RSAPublicKey rsaPublicKey=(RSAPublicKey) keyPair.getPublic();
RSAPrivateKey rsaPrivateKey=(RSAPrivateKey) keyPair.getPrivate();
System.out.println("public Key: "+Base64.encodeBase64String(rsaPublicKey.getEncoded()));
System.out.println("private Key: "+Base64.encodeBase64String(rsaPrivateKey.getEncoded()));
//执行签名
PKCS8EncodedKeySpec pkcs8EncodedKeySpec=new PKCS8EncodedKeySpec(rsaPrivateKey.getEncoded());
KeyFactory keyFactory=KeyFactory.getInstance("RSA");
PrivateKey privateKey=keyFactory.generatePrivate(pkcs8EncodedKeySpec);
Signature signature=Signature.getInstance("MD5withRSA");
signature.initSign(privateKey);
signature.update(STR.getBytes());
byte[] result=signature.sign();
System.out.println("jdk RSA sign: "+Hex.encodeHexString(result));
//验证签名
X509EncodedKeySpec x509EncodedKeySpec=new X509EncodedKeySpec(rsaPublicKey.getEncoded());
keyFactory=KeyFactory.getInstance("RSA");
PublicKey publicKey=keyFactory.generatePublic(x509EncodedKeySpec);
signature=Signature.getInstance("MD5withRSA");
signature.initVerify(publicKey);
signature.update(STR.getBytes());
boolean bool=signature.verify(result);
System.out.println("jdk RSA verify: "+bool);
} catch (Exception e) {
e.printStackTrace();
}
}
}
运行的结果:
public Key: MFwwDQYJKoZIhvcNAQEBBQADSwAwSAJBAJJg+/gqw0P+YmtssuJFsJCXGhRzAvp9pGL1VFroU7iNAJOQwfCjntV4/IhDo4yTw4gCWqB8rpc2TMYBlmeTo2ECAwEAAQ==
private Key: MIIBVAIBADANBgkqhkiG9w0BAQEFAASCAT4wggE6AgEAAkEAkmD7+CrDQ/5ia2yy4kWwkJcaFHMC+n2kYvVUWuhTuI0Ak5DB8KOe1Xj8iEOjjJPDiAJaoHyulzZMxgGWZ5OjYQIDAQABAkAKc/KKXkNjb58HnNOJZQCe0quCGlR0HtTGXE6Rz1VrMErHc8MWarHdplH/D6v8eKcYNMr9EtOTiGPD6W3btSYBAiEA0Rg+9Vp39dlfZjXNAKWg683d+5FIQrFBqGdbN1FC5OkCIQCzNyH2CkH2bB37jXL4AkOa2k/1DnL2tZoYibBW7eQfuQIhAMFp2iL+smR51GMpdR4aF4bIAYSI2PzIFmH+aUP8KRKxAiBkF+fM3h/HPM1mILNUlxchFstPh/lnlzfwen5VntopaQIgMZiwqZTLNHK6Is3F+AM7Cmte/uzChQrabemzbR7kY/4=
jdk RSA sign: 8fcdde37093cb268e6c13962fa3091e244004b71e0f1ca6b41f929c530ad71c656061a0b642934591e8c81860e8f97b8ddf724599bf5116c3375bef298410522
jdk RSA verify: true
RSA数字签名流程:
2.使用jdk实现DSA加密算法:
package com.samlai.security.digitalSignature;
import java.security.KeyFactory;
import java.security.KeyPair;
import java.security.KeyPairGenerator;
import java.security.NoSuchAlgorithmException;
import java.security.PrivateKey;
import java.security.PublicKey;
import java.security.Signature;
import java.security.interfaces.DSAPrivateKey;
import java.security.interfaces.DSAPublicKey;
import java.security.spec.PKCS8EncodedKeySpec;
import java.security.spec.X509EncodedKeySpec;
import org.apache.commons.codec.binary.Base64;
import org.apache.commons.codec.binary.Hex;
public class DSASignature {
/**
* DSS(Digital signature Standard)数字签名标准
* DSA(Digital signature ALgorithm)数字签名算法
* DSA仅包含数字签名
*/
private static String STR = "one type of security:DSA Signature";
public static void main(String[] args) {
jdkDSA();
}
private static void jdkDSA() {
try {
//1.初始化密钥
KeyPairGenerator keyPairGenerator=KeyPairGenerator.getInstance("DSA");
keyPairGenerator.initialize(512);
KeyPair keyPair=keyPairGenerator.generateKeyPair();
DSAPublicKey dsaPublicKey=(DSAPublicKey) keyPair.getPublic();
DSAPrivateKey dsaPrivateKey=(DSAPrivateKey) keyPair.getPrivate();
System.out.println("public Key: "+Base64.encodeBase64String(dsaPublicKey.getEncoded()));
System.out.println("private Key: "+Base64.encodeBase64String(dsaPrivateKey.getEncoded()));
//2.执行签名
PKCS8EncodedKeySpec pkcs8EncodedKeySpec=new PKCS8EncodedKeySpec(dsaPrivateKey.getEncoded());
KeyFactory keyFactory=KeyFactory.getInstance("DSA");
PrivateKey privateKey=keyFactory.generatePrivate(pkcs8EncodedKeySpec);
Signature signature=Signature.getInstance("SHA1withDSA");
signature.initSign(privateKey);
signature.update(STR.getBytes());
byte[] result=signature.sign();
System.out.println("jdk DSA sign"+Hex.encodeHexString(result));
//3.验证签名
X509EncodedKeySpec x509EncodedKeySpec=new X509EncodedKeySpec(dsaPublicKey.getEncoded());
keyFactory=KeyFactory.getInstance("DSA");
PublicKey publicKey=keyFactory.generatePublic(x509EncodedKeySpec);
signature=Signature.getInstance("SHA1withDSA");
signature.initVerify(publicKey);
signature.update(STR.getBytes());
boolean bool=signature.verify(result);
System.out.println("jdk DSA verify: "+bool);
} catch (Exception e) {
e.printStackTrace();
}
}
}
运行结果:
public Key: MIHwMIGoBgcqhkjOOAQBMIGcAkEA/KaCzo4Syrom78z3EQ5SbbB4sF7ey80etKII864WF64B81uRpH5t9jQTxeEu0ImbzRMqzVDZkVG9xD7nN1kuFwIVAJYu3cw2nLqOuyYO5rahJtk0bjjFAkBnhHGyepz0TukaScUUfbGpqvJE8FpDTWSGkx0tFCcbnjUDC3H9c9oXkGmzLik1Yw4cIGI1TQ2iCmxBblC+eUykA0MAAkBaR23h5B4H9EL68Jg3spHeGd/jdHP/6os41if2b2LqqXkhVGj7++HtGphlmI5xMyMXO+5D586DQ0swmH3YTTgr
private Key: MIHGAgEAMIGoBgcqhkjOOAQBMIGcAkEA/KaCzo4Syrom78z3EQ5SbbB4sF7ey80etKII864WF64B81uRpH5t9jQTxeEu0ImbzRMqzVDZkVG9xD7nN1kuFwIVAJYu3cw2nLqOuyYO5rahJtk0bjjFAkBnhHGyepz0TukaScUUfbGpqvJE8FpDTWSGkx0tFCcbnjUDC3H9c9oXkGmzLik1Yw4cIGI1TQ2iCmxBblC+eUykBBYCFEEA2YtEJc5ZGOs+OVULCtKIIQhT
jdk DSA sign302c02142f5fb08d0dbf2744be154896e38e53c0abaa9efe02145c8a9bf910440de440f54e082eece4dcc1c65a13
jdk DSA verify: true
流程图:
3.ECDSA实现方式:
package com.samlai.security.digitalSignature;
import java.security.KeyFactory;
import java.security.KeyPair;
import java.security.KeyPairGenerator;
import java.security.PrivateKey;
import java.security.PublicKey;
import java.security.Signature;
import java.security.interfaces.ECPrivateKey;
import java.security.interfaces.ECPublicKey;
import java.security.spec.PKCS8EncodedKeySpec;
import java.security.spec.X509EncodedKeySpec;
import org.apache.commons.codec.binary.Base64;
import org.apache.commons.codec.binary.Hex;
public class ECDSASignature {
/**
* 微软
* Eliptic Curve Digital Signature 椭圆曲线数字签名算法
* 速度快,强度高,签名短
*/
private static String STR = "one type of security:ECDSA Signature";
public static void main(String[] args) {
ECDSA();
}
private static void ECDSA() {
try {
//初始化密钥
KeyPairGenerator keyPairGenerator=KeyPairGenerator.getInstance("EC");
keyPairGenerator.initialize(256);
KeyPair keyPair=keyPairGenerator.generateKeyPair();
ECPublicKey ecPublicKey=(ECPublicKey) keyPair.getPublic();
ECPrivateKey ecPrivateKey=(ECPrivateKey) keyPair.getPrivate();
System.out.println("public Key: "+Base64.encodeBase64String(ecPublicKey.getEncoded()));
System.out.println("private Key: "+Base64.encodeBase64String(ecPrivateKey.getEncoded()));
//执行签名
PKCS8EncodedKeySpec pkcs8EncodedKeySpec=new PKCS8EncodedKeySpec(ecPrivateKey.getEncoded());
KeyFactory keyFactory=KeyFactory.getInstance("EC");
PrivateKey privateKey=keyFactory.generatePrivate(pkcs8EncodedKeySpec);
Signature signature=Signature.getInstance("SHA1withECDSA");
signature.initSign(privateKey);
signature.update(STR.getBytes());
byte[] result=signature.sign();
System.out.println("JDK ECDSA SIGN:"+Hex.encodeHexString(result));
//验证签名
X509EncodedKeySpec x509EncodedKeySpec=new X509EncodedKeySpec(ecPublicKey.getEncoded());
keyFactory=KeyFactory.getInstance("EC");
PublicKey publicKey=keyFactory.generatePublic(x509EncodedKeySpec);
signature=Signature.getInstance("SHA1withECDSA");
signature.initVerify(publicKey);
signature.update(STR.getBytes());
boolean bool=signature.verify(result);
System.out.println("jdk ECDSA verify: "+bool);
} catch (Exception e) {
e.printStackTrace();
}
}
}
public Key: MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAEWdo9gso3Iwuq1vDn2ZlKikokARBJGMmRktG7Z/EDmq3NuCLkZw+VcHh5lBREjeHrvh8F80HiT9SVSy+UFhWFmQ==
private Key: MEECAQAwEwYHKoZIzj0CAQYIKoZIzj0DAQcEJzAlAgEBBCBJPfCsuLcSME1cP5h1oNrXNw6XwERJTCRDfRJF649YAA==
JDK ECDSA SIGN:3045022100dcc2c6c58137a1281803da500465d4c097badc91db351004ba5416127e64e366022011c142cbdb377a409337ec817139a667375270677d553a2bd2c4cbb9cf016bd0
jdk ECDSA verify: true
ECDSA的流程图: