java - 如何使用 IBMJSSE2 默认提供程序从 SSLContext 获取所有 TLS 会话?
问题描述
我使用为 TLS 连接提供的默认值,IBMJSSEProvider2
并且我有以下代码来显示有关 TLS 会话的信息:
SSLSessionContext sslSessionContext = SSLContext.getDefault().getClientSessionContext();
Enumeration<byte[]> sessionIds = sslSessionContext.getIds();
while (sessionIds.hasMoreElements()) {
SSLSession sslSession = sslSessionContext.getSession(sessionIds.nextElement());
writer.write("Client: " + sslSession.getPeerHost() + ":" + sslSession.getPeerPort() + "\n");
writer.write("\tProtocol: " + sslSession.getProtocol() + "\n");
writer.write("\tSessionID: " + byteArrayToHex(sslSession.getId()) + "\n");
writer.write("\tCipherSuite: " + sslSession.getCipherSuite() + "\n");
for (X509Certificate certificate : sslSession.getPeerCertificateChain()) {
writer.write("\tX509 Certificate: " + certificate.getSubjectDN() + "\n");
writer.write("\t\tIssuer: " + certificate.getIssuerDN().getName() + "\n");
writer.write("\t\tAlgorithm: " + certificate.getSigAlgName() + "\n");
writer.write("\t\tValidity: " + certificate.getNotAfter() + "\n");
}
}
上面的代码在 WebSphere 8.5 的一个实例上运行。当我运行这个算法时,它不会打印关于我使用RestTemplate
Spring 3.2 的实现与任何 HTTPS URL 建立的连接的任何信息。使用来自 Oracle 的其他提供程序会显示信息。我是否缺少使它起作用的东西?
我正在尝试制作一个简单的解决方案来解决 WebSphere 的实时实例支持哪些 TLS 版本。当然,不建议现场客户使用此方法。
解决方案
问题在于,底层库可能没有使用 WebSphere 上的默认上下文。因此,我必须创建一个自定义客户端来使用特定的 SSLContext,这样我就可以列出我需要的所有信息。以下是实现此目的的代码:
private static String URL = "https://www.google.com";
private static String TRUST_STORE_FILE = "/Users/xpto/trust.p12";
private static String TRUST_STORE_PASS = "truststore";
private static String TRUST_STORE_TYPE = "PKCS12";
private static String TLS_VERSION = "TLSv1.2";
public static void main(String[] args) throws Exception {
KeyStore keyStore = KeyStore.getInstance(TRUST_STORE_TYPE);
keyStore.load(new FileInputStream(TRUST_STORE_FILE), TRUST_STORE_PASS.toCharArray());
SSLContext sslContext = SSLContexts
.custom()
.loadTrustMaterial(keyStore)
.useProtocol(TLS_VERSION)
.build();
HttpComponentsClientHttpRequestFactory clientFactory = new HttpComponentsClientHttpRequestFactory(HttpClients
.custom()
.setSSLSocketFactory(new SSLConnectionSocketFactory(sslContext))
.build());
RestTemplate restTemplate = new RestTemplate(clientFactory);
HttpHeaders requestHeaders = new HttpHeaders();
requestHeaders.setContentType(MediaType.APPLICATION_JSON);
requestHeaders.setAccept(Arrays.asList(MediaType.APPLICATION_JSON));
HttpEntity<String> requestEntity = new HttpEntity<String>(requestHeaders);
print("Requesting: " + URL);
ResponseEntity<String> response = restTemplate.exchange(URL, HttpMethod.GET, requestEntity, String.class);
print("Response: " + response.getBody());
printSSLContextInfo(sslContext);
}
private static void printSSLContextInfo(SSLContext sslContext) throws Exception {
print("-------------\nPrinting TLS Client Information");
SSLSessionContext sslSessionContext = sslContext.getClientSessionContext();
Enumeration<byte[]> sessionIds = sslSessionContext.getIds();
while (sessionIds.hasMoreElements()) {
SSLSession sslSession = sslSessionContext.getSession(sessionIds.nextElement());
print("Client: " + sslSession.getPeerHost() + ":" + sslSession.getPeerPort());
print("\tProtocol: " + sslSession.getProtocol());
print("\tSessionID: " + byteArrayToHex(sslSession.getId()));
print("\tCipherSuite: " + sslSession.getCipherSuite());
for (X509Certificate certificate : sslSession.getPeerCertificateChain()) {
print("\tX509 Certificate: " + certificate.getSubjectDN());
print("\t\tIssuer: " + certificate.getIssuerDN().getName());
print("\t\tAlgorithm: " + certificate.getSigAlgName());
print("\t\tValidity: " + certificate.getNotAfter());
}
}
}
public static String byteArrayToHex(byte[] a) {
StringBuilder sb = new StringBuilder(a.length * 2);
for (byte b : a)
sb.append(String.format("%02x", b));
return sb.toString();
}
public static void print(Object msg) {
System.out.println(msg);
}
推荐阅读
- dns - 如何使用具有不可替代令牌标准的 RNS 域?(如ERC721)
- c# - 如何使用 Visual Studio 查看/导航 asp.net 核心源代码?
- discord.py - 你如何停止让不和谐的机器人问一些东西,然后当我输入一些东西时,命令会停止,所以我不能向它发送垃圾邮件
- javascript - 是否可以在 Vue.js 中使用 python 脚本?
- performance - 如何在 AS3 中创建和删除许多子对象而不阻塞 CPU 或 RAM
- c# - 无法为服务接口提供 Dto 引用
- jenkins - 根据之前选择的参数动态隐藏/显示 Jenkins 参数
- reactjs - “盖茨比构建”命令 jsx 不正确,但盖茨比开发没有
- c - 为什么字符数组在以下上下文中像指针一样工作
- xamarin.forms - Xamarin 在发布版本中形成 Android Jar 绑定问题