使用maven引入httpclient ,版本4.5.4
<dependency> <groupId>org.apache.httpcomponents</groupId> <artifactId>httpclient</artifactId> <version>4.5.2</version> <scope>test</scope> </dependency>
- 导出证书
- a. 通过浏览器访问https网站导出证书
– 在浏览器中输入https://192.168.1.120:38080/,根据提示导出证书(因为是使用docker安装的https服务,这里的38080端口就是对应的https 443端口)。
我用的是filefox,输入地址后,会看到证书不信任提示,按照提示一步步导出,“添加例外——查看——详细信息——导出”,保存类型选择“X509含链证书(PEM)”,即后缀为.crt
打开crt文件,选择“详细信息——复制到文件——一顿下一步”,生成.cer文件。 - b.在mac系统里面可以直接通过钥匙链来导出.cer文件
– 在钥匙链的种类里面选证书,然后选择 https网站的证书名字,选择菜单里面的文件菜单下的导出项目,保存成.cer文件
- a. 通过浏览器访问https网站导出证书
将证书导入到jdk中。
- A. 打开终端,进入$JAVA_HOME\jre\lib\security文件夹中
- B. 使用keytools生成认证文件
sudo keytool -import -noprompt -keystore cacerts -storepass changeit -alias terrier -file /Users/roamer/Desktop/terrier.cer
其中的-alias terrier 是自己设置的别名
-file 后面要跟crt文件的全路径
操作成功后,会提示<证书已添加到密钥库中>- C. 删除认证文件的命令
sudo keytool -delete -alias terrier -keystore cacerts -storepass changeit
java代码使用httpClient访问https的RESTful 服务
package com.ninelephas.terrier; import java.io.IOException; import java.util.ArrayList; import java.util.List; import java.util.UUID; import org.apache.commons.httpclient.HttpException; import org.apache.http.NameValuePair; import org.apache.http.client.entity.UrlEncodedFormEntity; import org.apache.http.client.methods.CloseableHttpResponse; import org.apache.http.client.methods.HttpPost; import org.apache.http.conn.ssl.NoopHostnameVerifier; import org.apache.http.impl.client.CloseableHttpClient; import org.apache.http.impl.client.HttpClients; import org.apache.http.message.BasicNameValuePair; import org.apache.http.util.EntityUtils; import org.apache.logging.log4j.LogManager; import org.apache.logging.log4j.Logger; import org.junit.Test; import org.junit.runner.RunWith; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.test.context.ContextConfiguration; import org.springframework.test.context.junit4.SpringJUnit4ClassRunner; import org.springframework.test.context.web.WebAppConfiguration; import com.fasterxml.jackson.databind.ObjectMapper; import com.fasterxml.jackson.core.JsonGenerator; import com.ninelephas.terrier.controller.PassportController; import com.ninelephas.terrier.entity.Passport; /** * * @ClassName: PassportTester * @Description: http client 测试类 * @author 徐泽宇 * @date 2016年12月7日 下午4:17:36 * */ @RunWith(SpringJUnit4ClassRunner.class) @ContextConfiguration({"classpath:/META-INF/applicationContext.xml", "classpath:/META-INF/spring-mvc.xml"}) @WebAppConfiguration public class PassportTester { /** * Logger for this class */ private static final Logger logger = LogManager.getLogger(PassportTester.class.getName()); // private static final String urlString = "http://127.0.0.1:8080/terrier"; private static final String urlString = "https://192.168.1.120:38080"; /** * * checkPassword * * @Auther 徐泽宇 * @Date 2016年12月12日 下午6:22:36 * @Title: checkPassword * @Description: 使用http协议,测试判断密码是非正确 * @throws HttpException * @throws IOException */ @Test public void checkPassword() throws Exception { final String url = urlString + "/passport/check_password.json"; logger.debug("url is {}", url); //$NON-NLS-1$ CloseableHttpClient httpClient = null; try { HttpPost httpPost = new HttpPost(url); if (url.startsWith("https")) { // https访问 httpClient = HttpClients.custom().setSSLHostnameVerifier(new NoopHostnameVerifier()).build(); } else { // 普通的http调用 httpClient = HttpClients.createDefault(); } List<NameValuePair> nvps = new ArrayList<NameValuePair>(); nvps.add(new BasicNameValuePair("mobile", "1111222")); nvps.add(new BasicNameValuePair("md5Password", "md5加密的密文")); httpPost.setEntity(new UrlEncodedFormEntity(nvps, "utf-8")); CloseableHttpResponse response = httpClient.execute(httpPost); try { logger.debug("调用返回状态码:{}", response.getStatusLine()); logger.debug("http 返回的内容是\n{}", EntityUtils.toString(response.getEntity(), "UTF-8")); } finally { response.close(); } } finally { httpClient.close(); } } }
注意的几个问题
– a.一定要保证导入证书的jre就是当前调用httpClient的java类使用的jre。否则就算证书导入成功,httpClient还是访问不了https.会出现以下错误:javax.net.ssl.SSLHandshakeException: sun.security.validator.ValidatorException: PKIX path building failed: sun.security.provider.certpath.SunCertPathBuilderException: unable to find valid certification path to requested target
可以通过查看在$JAVA_HOME\jre\lib\security\下的cacerts文件中查找-alias 指定的别名的方式来确认是否是成功导入。
–b. 在调用httpClient的java类中,需要对HttpClient生成的时候使用语句httpClient = HttpClients.custom().setSSLHostnameVerifier(new NoopHostnameVerifier()).build();
否则会出现如下错误:
javax.net.ssl.SSLPeerUnverifiedException: Host name '192.168.1.120' does not match the certificate subject provided by the peer (CN=joinku, OU=joinku, O=joinku, L=joinku, ST=joinku, C=joinku)
使用apache的httpcomponents中的httpclient 4.5对https进行访问
最新推荐文章于 2024-06-17 08:34:00 发布