如何在java SSL客户端应用程序中支持多个TrustStore [英] How support multiple TrustStores in java SSL client application

查看:150
本文介绍了如何在java SSL客户端应用程序中支持多个TrustStore的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

在我们的java应用程序中,我们需要使用https协议与SSL上的服务器列表进行通信。要通信的服务器列表将在运行时更改。最初我们没有任何服务器的证书。在运行时,我们将获得新服务器的证书并将公钥证书添加到信任库中;与服务器的任何新的https连接都应该使用更新后的信任存储。

In our java application we need to communicate with a list of servers on SSL using https protocol. The list of servers to communicate will change at runtime. Initially we do not have any of the server's certificate. At runtime, we will obtain a new server's certificate and add the public key certificate into a truststore; and any new https connection with the server should use the updated trust store.

我们认为我们应该使用两个信任存储,一个cacerts(默认一个随jre一起提供)和其他包含我们在列表中动态添加/删除的服务器的证书。这将确保我们不修改java的默认TrustStore(cacerts)。

We are thinking that we should use two trust stores, one cacerts(default one shipped with jre) and other containing certificates of the servers that we add/remove dynamically in a list. This will make sure that we do not modify the default TrustStore(cacerts) of java.

请建议如何实现。
另外,有没有办法只为java中的特定线程使用特定的信任存储,以便其他(现有的和新的)线程仍然应该使用默认的java trueststore(cacerts),并且一个特定的线程将使用服务器的特定信任库。

Please suggest how this can be achieved. Also, is there any way to use a specific trust store only for a particular thread in java, so that other(existing and new) threads should still use the default java trueststore(cacerts), and one specific thread will use the particular truststore for the server.

谢谢你,
迪帕克

Thank you, Deepak

推荐答案

如果要动态导入证书,可能需要使用自定义 x509TrustManager 。在配置 SSLContext ,它本身用于创建 SSLSocketFactory SSLEngine

If you want to import certificate dynamically, you may need to use a custom x509TrustManager. This is done when configuring the SSLContext, which is itself used to create the SSLSocketFactory or SSLEngine.

jSSLutils 是一个可以让你换行的库现有信任管理器并自定义某些设置。你不需要它,但它可能会有所帮助。

jSSLutils is a library that lets you wrap existing trust managers and customize certain settings. You don't need it, but it may help.

这将是这样的:

PKIXSSLContextFactory sslContextFactory = new PKIXSSLContextFactory();
sslContextFactory.setTrustManagerWrapper(new X509TrustManagerWrapper() {
    @Override
    public X509TrustManager wrapTrustManager(final X509TrustManager origManager) {
        return new X509TrustManager() { 
            @Override
            public X509Certificate[] getAcceptedIssuers() {
                return origManager.getAcceptedIssuers();
            }

            @Override
            public void checkServerTrusted(X509Certificate[] chain,
                                                   String authType)
                    throws CertificateException {
                try {
                    // This will call the default trust manager
                    // which will throw an exception if it doesn't know the certificate
                    origManager.checkServerTrusted(chain, authType);
                } catch (CertificateException e) {
                    // If it throws an exception, check what this exception is
                    // the server certificate is in chain[0], you could
                    // implement a callback to the user to accept/refuse
                }
            }

            @Override
            public void checkClientTrusted(X509Certificate[] chain,
                                                   String authType)
                    throws CertificateException {
                origManager.checkClientTrusted(chain, authType);
            }
        };
    }
});
SSLContext sslContext = sslContextFactory.buildSSLContext();

(PKIX)SSLContextFactory X509TrustManagerWrapper 来自jSSLutils,但其余部分可用于J2SE / J2EE。)

(The (PKIX)SSLContextFactory and X509TrustManagerWrapper come from jSSLutils, but the rest is available with the J2SE/J2EE.)

有几个 CertificateException s 您可能想要捕获(请参阅子类)。
如果您对用户进行回调,由于SSL / TLS握手超时,SSL / TLS连接可能会首次失败(如果回调需要很长时间才能回复。 )

There are a few CertificateExceptions that you may want to catch (see subclasses). If you make a callback to the user, it's possible that the SSL/TLS connection will fail the first time because of a time-out on the SSL/TLS handshake (if the callback takes too long to be replied to.)

然后你可以使用 SSLContext 作为默认值使用 SSLContext.setSSLContext(。 ..)(来自Java 6),但这不一定是个好主意。如果可以,将 SSLContext 传递给建立SSL / TLS连接的库。如何做到这一点各不相同,但Apache HTTP Client 4.x有多个选项来配置其SSL设置,其中一个是传递 KeyStore ,另一个通过传递 SSLContext

You could then use this SSLContext as your default using SSLContext.setSSLContext(...) (from Java 6), but that's not necessarily a good idea. If you can, pass the SSLContext to the library that makes the SSL/TLS connection. How this is done varies, but Apache HTTP Client 4.x, for example, has multiple options to configure its SSL settings, one of them being by passing KeyStores, another one being by passing an SSLContext.

您还可以使用每个线程而不是每个要连接的对象(库依赖),通过检查 X509TrustManager 中的当前线程:这可能会使信任管理器在同步和线程管理/感知方面更复杂一些。

You could also to something per thread instead of per object that's going to connect (library dependent), by checking the current thread within the X509TrustManager: this would probably make things a bit more complex in terms of synchronization and thread management/"awareness" by the trust manager.

这篇关于如何在java SSL客户端应用程序中支持多个TrustStore的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆