【转】网络安全-Java SSLSocketFactory 创建方式


特别提示:本人博客部分有参考网络其他博客,但均是本人亲手编写过并验证通过。如发现博客有错误,请及时提出以免误导其他人,谢谢!欢迎转载,但记得标明文章出处: http://www.cnblogs.com/mao2080/

1、问题描述

  Java客服端使用证书连接到服务器,加密方式有了两种:方式一:CA、Client CRT、Client Key 文件  |  方式二:KeyStore.jks、TrustStore.jks、Password。

2、操作方法

  1、通过 CA、Client CRT、Client Key,客户端自己创建 KeyStore、TrustStore,再创建 SSLSocketFactory

 1     /**
 2      * 创建 SSLSocketFactory 工厂
 3      *
 4      * @param caCrtFile 服务端 CA 证书
 5      * @param crtFile 客户端 CRT 文件
 6      * @param keyFile 客户端 Key 文件
 7      * @param password SSL 密码,随机
 8      * @return {@link SSLSocketFactory}
 9      * @throws Exception 异常
10      */
11     public static SSLSocketFactory getSocketFactory(final String caCrtFile, final String crtFile, final String keyFile, final String password) throws Exception {
12         InputStream caInputStream = null;
13         InputStream crtInputStream = null;
14         InputStream keyInputStream = null;
15         try {
16             Security.addProvider(new BouncyCastleProvider());
17             CertificateFactory cf = CertificateFactory.getInstance("X.509");
18             // load CA certificate
19             caInputStream = new ClassPathResource(caCrtFile).getInputStream();
20             X509Certificate caCert = null;
21             while (caInputStream.available() > 0) {
22                 caCert = (X509Certificate) cf.generateCertificate(caInputStream);
23             }
24             // load client certificate
25             crtInputStream = new ClassPathResource(crtFile).getInputStream();
26             X509Certificate cert = null;
27             while (crtInputStream.available() > 0) {
28                 cert = (X509Certificate) cf.generateCertificate(crtInputStream);
29             }
30 
31             // load client private key
32             keyInputStream = new ClassPathResource(keyFile).getInputStream();
33             PEMParser pemParser = new PEMParser(new InputStreamReader(keyInputStream));
34             Object object = pemParser.readObject();
35             PEMDecryptorProvider decProv = new JcePEMDecryptorProviderBuilder().build(password.toCharArray());
36             JcaPEMKeyConverter converter = new JcaPEMKeyConverter().setProvider("BC");
37             KeyPair key;
38             if (object instanceof PEMEncryptedKeyPair) {
39                 System.out.println("Encrypted key - we will use provided password");
40                 key = converter.getKeyPair(((PEMEncryptedKeyPair) object).decryptKeyPair(decProv));
41             } else {
42                 System.out.println("Unencrypted key - no password needed");
43                 key = converter.getKeyPair((PEMKeyPair) object);
44             }
45             pemParser.close();
46 
47             // CA certificate is used to authenticate server
48             KeyStore caKs = KeyStore.getInstance(KeyStore.getDefaultType());
49             caKs.load(null, null);
50             caKs.setCertificateEntry("ca-certificate", caCert);
51             TrustManagerFactory tmf = TrustManagerFactory.getInstance("X509");
52             tmf.init(caKs);
53 
54             // client key and certificates are sent to server so it can authenticate
55             // us
56             KeyStore ks = KeyStore.getInstance(KeyStore.getDefaultType());
57             ks.load(null, null);
58             ks.setCertificateEntry("certificate", cert);
59             ks.setKeyEntry("private-key", key.getPrivate(), password.toCharArray(), new java.security.cert.Certificate[]{cert});
60             KeyManagerFactory kmf = KeyManagerFactory.getInstance(KeyManagerFactory.getDefaultAlgorithm());
61             kmf.init(ks, password.toCharArray());
62 
63             // finally, create SSL socket factory
64             SSLContext context = SSLContext.getInstance("TLSv1.2");
65             context.init(kmf.getKeyManagers(), tmf.getTrustManagers(), null);
66 
67             return context.getSocketFactory();
68 
69         }
70         finally {
71             if (null != caInputStream) {
72                 caInputStream.close();
73             }
74             if (null != crtInputStream) {
75                 crtInputStream.close();
76             }
77             if (null != keyInputStream) {
78                 keyInputStream.close();
79             }
80         }
81     }

  2、服务端提供 KeyStore.jks、TrustStore.jks,创建 SSLSocketFactory

 1     /**
 2      * 创建 SSLSocketFactory 工厂
 3      *
 4      * @param keyStoreJks 客户端 KeyStore
 5      * @param trustStoreJks 客户端 信任库 trust store
 6      * @param password 密码
 7      * @return {@link SSLSocketFactory}
 8      * @throws Exception 异常
 9      */
10     public static SSLSocketFactory getSocketFactory(final String keyStoreJks, final String trustStoreJks, final String password) throws Exception {
11         InputStream keyStoreJksInputStream = null;
12         InputStream trustStoreJksInputStream = null;
13         try {
14             ClassPathResource classPathResource = new ClassPathResource(keyStoreJks);
15             keyStoreJksInputStream = classPathResource.getInputStream();
16             KeyStore ks = KeyStore.getInstance(KeyStore.getDefaultType());
17             ks.load(keyStoreJksInputStream, password.toCharArray());
18             KeyManagerFactory kmf = KeyManagerFactory.getInstance(KeyManagerFactory.getDefaultAlgorithm());
19             kmf.init(ks, password.toCharArray());
20 
21             classPathResource = new ClassPathResource(trustStoreJks);
22             trustStoreJksInputStream = classPathResource.getInputStream();
23             KeyStore trustStore = KeyStore.getInstance(KeyStore.getDefaultType());
24             trustStore.load(trustStoreJksInputStream, password.toCharArray());
25             TrustManagerFactory trustManagerFactory = TrustManagerFactory.getInstance("X509");
26             trustManagerFactory.init(trustStore);
27 
28             // finally, create SSL socket factory
29             SSLContext context = SSLContext.getInstance("TLSv1.2");
30             context.init(kmf.getKeyManagers(), trustManagerFactory.getTrustManagers(), null);
31             return context.getSocketFactory();
32         }
33         finally {
34             try {
35                 if (null != keyStoreJksInputStream) {
36                     keyStoreJksInputStream.close();
37                 }
38             } catch (IOException e) {
39                 System.out.println(e.getMessage());
40             }
41 
42             try {
43                 if (null != trustStoreJksInputStream) {
44                     trustStoreJksInputStream.close();
45                 }
46             } catch (IOException e) {
47                 System.out.println(e.getMessage());
48             }
49         }
50     }

3、参考网站

https://blog.csdn.net/weixin_43803007/article/details/105513034(原文地址)


免责声明!

本站转载的文章为个人学习借鉴使用,本站对版权不负任何法律责任。如果侵犯了您的隐私权益,请联系本站邮箱yoyou2525@163.com删除。



 
粤ICP备18138465号  © 2018-2025 CODEPRJ.COM