1、简介

Apache HttpClient是一个底层、轻量级的客户端HTTP库,用于与HTTP服务器进行通信。

在本教程中,我们将学习如何在使用HttpClient时配置支持的传输层安全(TLS)版本。

我们将首先概述TLS版本协商如何在客户端和服务器之间工作。

之后,我们将看看在使用HttpClient时配置支持的TLS版本的三种不同方式

2、TLS版本协商

TLS是一种互联网协议,可在两方之间提供安全、可信的通信。它封装了像HTTP这样的应用层协议。

TLS协议自1999年首次发布以来已多次修订。

因此,客户端和服务器在建立新连接时,首先就他们将使用的TLS版本达成一致非常重要。

TLS版本在客户端和服务器交换hello消息后达成一致:

  1. 客户端发送支持的 TLS 版本列表。
  2. 服务器选择一个并在响应中包含所选版本。
  3. 客户端和服务器使用所选版本继续连接设置。

由于存在降级攻击的风险,因此正确配置Web客户端支持的TLS版本非常重要。

请注意,为了使用最新版本的TLS(TLS 1.3),我们必须使用Java 11或更高版本

3、固定设置TLS版本

3.1、SSLConnectionSocketFactory

让我们通过HttpClients#custom定制构建方法提供的HttpClientBuilder,来定制我们的HTTPClient配置。

此构建器模式允许我们传入我们自己的SSLConnectionSocketFactory,它将根据一组所需支持的TLS版本进行实例化:

SSLConnectionSocketFactory sslsf = new SSLConnectionSocketFactory(
SSLContexts.createDefault(),
new String[] { "TLSv1.2", "TLSv1.3" },
null,
SSLConnectionSocketFactory.getDefaultHostnameVerifier()); CloseableHttpClient httpClient = HttpClients.custom().setSSLSocketFactory(sslsf).build();

返回的Httpclient对象现在可以执行HTTP请求了。

通过在SSLConnectionSocketFactory构造函数中显式设置支持的协议,客户端将仅支持通过TLS 1.2或TLS 1.3的通信。

请注意,在 Apache HttpClient 4.3 之前的版本中,该类称为SSLSocketFactory

3.2、Java运行时参数

另外,我们可以使用Java的https.protocols系统属性配置支持的TLS版本。

此方法可以防止必须将值硬编码到应用程序代码中。

相反,我们将配置HttpClient以在设置连接时使用该系统属性。

HttpClient API提供了两种方法来实现。第一个是通过HttpClients#createSystem

CloseableHttpClient httpClient = HttpClients.createSystem();

如果需要更多的客户端配置,我们可以使用builder方法代替:

CloseableHttpClient httpClient = HttpClients.custom().useSystemProperties().build();

这两种方法都告诉HttpClient在连接配置期间使用系统属性。

这允许我们在应用程序运行时使用命令行参数设置所需的TLS版本。例如:

$ java -Dhttps.protocols=TLSv1.1,TLSv1.2,TLSv1.3 -jar webClient.jar

4、动态设置TLS版本

还可以根据主机名和端口等连接详细信息设置TLS版本。我们将扩展SSLConnectionSocketFactory并覆盖prepareSocket方法。

客户端会在启动新连接之前调用prepareSocket方法,这将可以让我们在每个连接的基础上决定使用哪些TLS协议。

也可以启用对旧TLS版本的支持,但前提是远程主机具有特定的子域:

SSLConnectionSocketFactory sslsf = new SSLConnectionSocketFactory(SSLContexts.createDefault()){

    @Override
protected void prepareSocket(SSLSocket socket) { String hostname = socket.getInetAddress().getHostName();
if (hostname.endsWith("internal.system.com")){
socket.setEnabledProtocols(new String[] { "TLSv1", "TLSv1.1", "TLSv1.2", "TLSv1.3" });
}
else {
socket.setEnabledProtocols(new String[] {"TLSv1.3"});
}
}
};
CloseableHttpClient httpClient = HttpClients.custom().setSSLSocketFactory(sslsf).build();

在上面的示例中,prepareSocket方法首先获取SSLSocket将连接到的远程主机名,然后使用主机名来确定要启用的TLS协议。

现在,我们的HTTP客户端将对每个请求强制执行TLS 1.3,除了目标主机名的格式为*.internal.system.com

由于能够在创建新SSLSocket之前插入自定义逻辑,我们的应用程序现在可以自定义TLS通信的详细信息。

5、结论

在本文中,我们研究了在使用Apache HttpClient库时配置支持的TLS版本的三种不同方式。

我们已经了解了如何为所有连接或基于每个连接设置TLS版本。

原文:https://www.baeldung.com/apache-httpclient-tls

翻译:码农熊猫

更多技术干货,请访问我的个人网站https://pinmost.com,或关注公众号【码农熊猫】

如何在Apache HttpClient中设置TLS版本的更多相关文章

  1. 如何在Linux服务器中隐藏PHP版本

    通常,大多数默认设置安装的web服务器存在信息泄露,这其中之一就是PHP.PHP 是如今流行的服务端html嵌入式语言(之一?).在如今这个充满挑战的时代,有许多攻击者会尝试发现你服务端的漏洞.因此, ...

  2. 如何在 Apache Flink 中使用 Python API?

    本文根据 Apache Flink 系列直播课程整理而成,由 Apache Flink PMC,阿里巴巴高级技术专家 孙金城 分享.重点为大家介绍 Flink Python API 的现状及未来规划, ...

  3. 为何在font-family属性中设置多个值

    通常前端开发中会对body标签中设置font-family属性多个值,例如: body{padding:0;margin:0;font-size:12px;text-align:left;font-f ...

  4. 转--Android如何在java代码中设置margin

    ========  3 在Java代码里设置button的margin(外边距)? 1.获取按钮的LayoutParams LinearLayout.LayoutParams layoutParams ...

  5. 如何在Webstorm/Phpstorm中设置连接FTP,并快速进行文件比较,上传下载,同步等操作

    Phpstorm除了能直接打开localhost文件之外,还可以连接FTP,除了完成正常的数据传递任务之外,还可以进行本地文件与服务端文件的异同比较,同一文件自动匹配目录上传,下载,这些功能是平常ID ...

  6. apache服务器中设置目录不可访问

    <Directory "d:/amp/apache/htdocs/images">    Allow from all    Options None</Dire ...

  7. Android如何在java代码中设置margin

    习惯了直接在xml里设置margin(距离上下左右都是10dip),如: <ImageView android:layout_margin="10dip" android:s ...

  8. 如何在Quartus II中设置Virtual pin

    为了验证FPGA工程中的某个模块的功能和时序的正确性,常常需要对其单独进行验证,但是这些模块通常都与内部的众多信号相连(如系统总线,中断信号线等),往往一个模块的对外接口引脚会多达几百个,对其单独仿真 ...

  9. 如何在Windows系统中设置Python程序定时运行

    文章出处:http://blog.csdn.net/wwy11/article/details/51100432 首先,我们肯定是要用到Windows下的[计划任务]功能 之后点击右侧的[创建基本任务 ...

随机推荐

  1. Python+Selenium学习笔记11 - python官网的tutorial - 定义函数

    1 def f(a, L=[]): 2 L.append(a) 3 return L 4 5 print f(5) 6 print f(2) 输出 1 def f(a, L=None): 2 if L ...

  2. Selenium八种元素定位方法源码阅读

    接触过Selenium的都知道元素定位有八种方法,但用不同的方法在执行时有什么区别呢? 元素定位8种方法(Python版),当然还有每一个方法对应的find_elements方法 find_eleme ...

  3. ASML光刻机PK 原子弹,难度?

    ASML光刻机PK 原子弹,难度? 一.  物理世界和网络世界的交汇点:光刻机 光刻机的技术有多高级,看看这个知乎提问,可以感受一下: 有人这样形容光刻机:这是一种集合了数学.光学.流体力学.高分子物 ...

  4. CPU的自动调度矩阵乘法

    CPU的自动调度矩阵乘法 这是一个有关如何对CPU使用自动调度程序的文档. 与依靠手动模板定义搜索空间的基于模板的autotvm不同,自动调度程序不需要任何模板.用户只需要编写计算声明,而无需任何调度 ...

  5. NSight Compute 用户手册(中)

    NSight Compute 用户手册(中) NVIDIA Nsight Compute支持密码和私钥身份验证方法.在此对话框中,选择身份验证方法并输入以下信息: 密码 IP/主机名:目标设备的IP地 ...

  6. python赋值,深拷贝和浅拷贝的区别

    1.赋值 list1=[[1,2],'fei',66] list2=list1 list1 [[1, 2], 'fei', 66] list2 [[1, 2], 'fei', 66] list2.ap ...

  7. 【NX二次开发】缝合片体例子UF_MODL_create_sew

    缝合片体,没有成功缝合的片体涂绿色. 效果:  源码: extern DllExport void ufusr(char *param, int *returnCode, int rlen) { UF ...

  8. 【贪心】8.29题解-cut

    cut 题目描述 出于某些方面的需求,我们要把一块N×M的木板切成一个个1×1的小方块. 对于一块木板,我们只能从某条横线或者某条竖线(要在方格线上),而且这木板是不均匀的,从不同的线切割下去要花不同 ...

  9. sys用户无法远程登陆

    1.用sys用户远程登陆 [oracle@edbjr2p2 admin]$ sqlplus system/oracle@PROD3 as sysdbaSQL*Plus: Release 11.2.0. ...

  10. Vue开发项目全流程

    只记录vue项目开发流程,不说明怎样安装node和vue-cli等 确认安装 安装好node之后,可查看是否安装成功,有版本则安装成功.输入node -v 查看vue是否安装成功,有版本则安装成功.输 ...