为了账号安全,请及时绑定邮箱和手机立即绑定

Jetty 升级到 9.4.19.v20190610 后,传入的客户端请求中未出现 X509 证书

Jetty 升级到 9.4.19.v20190610 后,传入的客户端请求中未出现 X509 证书

明月笑刀无情 2023-06-04 10:25:38
Jetty 升级到后,我没有在传入的客户端请求中获得 X509 证书9.4.19.v20190610certifcates = (X509Certificate[])request.getAttribute("javax.servlet.request.X509Certificate");这里的证书是空的。虽然他们是 Jetty 版本9.4.11.v20180605我的客户端程序:private static String loginWithCertificate(String aEndPointURL) {    String line = "";    try {        final String CERT_ALIAS = "employee1";        String CERT_PASSWORD = "changeit";        KeyStore identityKeyStore = KeyStore.getInstance("jks");        FileInputStream identityKeyStoreFile = new FileInputStream(new File(ResourceUtils.getFile("./stores/client1.jks").getAbsolutePath()));        identityKeyStore.load(identityKeyStoreFile, CERT_PASSWORD.toCharArray());        KeyStore trustKeyStore = KeyStore.getInstance("jks");        FileInputStream trustKeyStoreFile = new FileInputStream(new File(ResourceUtils.getFile("./stores/truststore1.jks").getAbsolutePath()));        trustKeyStore.load(trustKeyStoreFile, CERT_PASSWORD.toCharArray());        SSLContext sslContext = SSLContexts.custom()                // load identity keystore                .loadKeyMaterial(identityKeyStore, CERT_PASSWORD.toCharArray(), new PrivateKeyStrategy() {                    @Override                    public String chooseAlias(Map<String, PrivateKeyDetails> aliases, Socket socket) {                        return CERT_ALIAS;                    }                })                // load trust keystore                .loadTrustMaterial(trustKeyStore, null).build();        SSLConnectionSocketFactory sslConnectionSocketFactory = new SSLConnectionSocketFactory(sslContext,                new String[] { "TLSv1.2", "TLSv1.1", "TLSv1"  }, null, SSLConnectionSocketFactory.STRICT_HOSTNAME_VERIFIER);        CloseableHttpClient client = HttpClients.custom().setSSLSocketFactory(sslConnectionSocketFactory).build();        }}
查看完整描述

1 回答

?
紫衣仙女

TA贡献1839条经验 获得超15个赞

仔细查看您的服务器端 SslContextFactory 使用情况,并着眼于您实际使用的内容(剥离以仅显示 SslContextFactory 使用情况)


SslContextFactory sslContextFactory = new SslContextFactory();

sslContextFactory.setKeyStoreResource(Resource.newResource(urlKeyStore));

sslContextFactory.setKeyStorePassword(credential);

sslContextFactory.setExcludeCipherSuites(

        "SSL_RSA_WITH_DES_CBC_SHA",

        "SSL_DHE_RSA_WITH_DES_CBC_SHA",

        "SSL_DHE_DSS_WITH_DES_CBC_SHA",

        "SSL_RSA_EXPORT_WITH_RC4_40_MD5",

        "SSL_RSA_EXPORT_WITH_DES40_CBC_SHA",

        "SSL_DHE_RSA_EXPORT_WITH_DES40_CBC_SHA",

        "SSL_DHE_DSS_EXPORT_WITH_DES40_CBC_SHA");

sslContextFactory.setExcludeProtocols("");

有几件事很突出。


首先,既然你是服务端,那你就应该使用服务端版本...


SslContextFactory sslContextFactory = new SslContextFactory.Server();

接下来,您的使用.setExcludedCipherSuites()不完整并引入了漏洞。


删除(或注释掉)整行。

使用 SslContextFactory 为您提供的默认值。

通过该行,可以为 TLS/SSL 使用无证书和无加密配置。


另外,你的使用setExcludedProtocols("")不好。它正在设置要排除的单个空白协议。这很糟糕,因为您将自己暴露于各种 SSL 漏洞(更不用说 TLS 漏洞了)


也删除(或注释掉)整行。

使用 SslContextFactory 为您提供的默认值。

通过该行,可以为 TLS/SSL 使用无协议(这意味着无加密)配置。


上述 2 个配置会产生大量警告日志,您应该努力拥有一个没有警告的配置。


对于上述两个问题,您可能会从连接中使用的密码套件的名称中了解到一些信息。


String cipherSuiteName = 

    (String) HttpServletRequest.getAttribute("javax.servlet.request.cipher_suite");

您甚至可以获得javax.net.ssl.SSLSession连接中使用的。


SslSession sslSession = 

    (SslSession) HttpServletRequest.getAttribute(

        "org.eclipse.jetty.servlet.request.ssl_session");

System.out.println("protocol is " + sslSession.getProtocol());

System.out.println("cipher suite is " + sslSession.getCipherSuite());

System.out.println("peer certs is " + sslSession.getPeerCertificates());

最后,您的代码没有任何迹象表明您甚至想要来自该配置的客户端证书。


你是否忘记了其中一个...


sslContextFactory.setNeedClientAuth(true);

sslContextFactory.setWantClientAuth(true);

还是您真的不需要客户证书?


查看完整回答
反对 回复 2023-06-04
  • 1 回答
  • 0 关注
  • 156 浏览

添加回答

举报

0/150
提交
取消
意见反馈 帮助中心 APP下载
官方微信