关于JAVA发送Https请求(HttpsURLConnection和HttpURLConnection)

https协议对于开发者而言其实只是多了一步证书验证的过程。这个证书正常情况下被jdk/jre/security/cacerts所管理。里面证书包含两种情况:

1、机构所颁发的被认证的证书,这种证书的网站在浏览器访问时https头显示为绿色如百度

2、个人所设定的证书,这种证书的网站在浏览器里https头显示为红色×,且需要点击信任该网站才能继续访问。而点击信任这一步的操作就是我们在java代码访问https网站时区别于http请求需要做的事情。

所以JAVA发送Https请求有两种情况,三种解决办法:

第一种情况:Https网站的证书为机构所颁发的被认证的证书,这种情况下和http请求一模一样,无需做任何改变,用HttpsURLConnection或者HttpURLConnection都可以

public static void main(String[] args) throws Exception{
        URL serverUrl = new URL("https://xxxx");
        HttpURLConnection conn = (HttpURLConnection) serverUrl.openConnection();
        conn.setRequestMethod("GET");
        conn.setRequestProperty("Content-type", "application/json");
        //必须设置false,否则会自动redirect到重定向后的地址
        conn.setInstanceFollowRedirects(false);
        conn.connect();
        String result = getReturn(conn);
    }
 
    /*请求url获取返回的内容*/
    public static String getReturn(HttpURLConnection connection) throws IOException{
        StringBuffer buffer = new StringBuffer();
        //将返回的输入流转换成字符串
        try(InputStream inputStream = connection.getInputStream();
            InputStreamReader inputStreamReader = new InputStreamReader(inputStream, ConstantInfo.CHARSET);
            BufferedReader bufferedReader = new BufferedReader(inputStreamReader);){
            String str = null;
            while ((str = bufferedReader.readLine()) != null) {
                buffer.append(str);
            }
            String result = buffer.toString();
            return result;
        }
}

 

第二种情况:个人所设定的证书,这种证书默认不被信任,需要我们自己选择信任,信任的办法有两种:

A、将证书导入java的运行环境中

 

  • 从该网站下载或者从网站开发者出获取证书cacert.crt
  • 运行命令将证书导入java运行环境:keytool -import -keystore %JAVA_HOME%\jre\lib\security\cacerts -file cacert.crt -alias xxx
  • 完成。java代码中发送https的请求和http一样,同第一种情况。

B、忽略证书验证过程,忽略之后任何Https协议网站皆能正常访问,同第一种情况

import java.security.cert.CertificateException;
import java.security.cert.X509Certificate;
import javax.net.ssl.X509TrustManager;
public class MyX509TrustManager implements X509TrustManager {
 
    @Override
    public void checkClientTrusted(X509Certificate certificates[],String authType) throws CertificateException {
    }
 
    @Override
    public void checkServerTrusted(X509Certificate[] ax509certificate,String s) throws CertificateException {
    }
 
    @Override
    public X509Certificate[] getAcceptedIssuers() {
        // TODO Auto-generated method stub
        return null;
    }
}
public static void main(String[] args) throws Exception{
        SSLContext sslcontext = SSLContext.getInstance("SSL","SunJSSE");
        sslcontext.init(null, new TrustManager[]{new MyX509TrustManager()}, new java.security.SecureRandom());
        URL url = new URL("https://xxxx");
        HostnameVerifier ignoreHostnameVerifier = new HostnameVerifier() {
            public boolean verify(String s, SSLSession sslsession) {
                System.out.println("WARNING: Hostname is not matched for cert.");
                return true;
            }
        };
        HttpsURLConnection.setDefaultHostnameVerifier(ignoreHostnameVerifier);
        HttpsURLConnection.setDefaultSSLSocketFactory(sslcontext.getSocketFactory());
        //之后任何Https协议网站皆能正常访问,同第一种情况
}

C、java代码中加载证书,必须使用HttpsURLConnection方式

public static void main(String[] args) throws Exception{  
        SSLContext sslcontext = SSLContext.getInstance("SSL","SunJSSE");  
        sslcontext.init(null, new TrustManager[]{new MyX509TrustManager()}, new java.security.SecureRandom());  
        URL serverUrl = new URL("https://xxxx");  
        HttpsURLConnection conn = (HttpsURLConnection) serverUrl.openConnection();  
        conn.setSSLSocketFactory(sslcontext.getSocketFactory());  
        conn.setRequestMethod("GET");  
        conn.setRequestProperty("Content-type", "application/json");  
        //必须设置false,否则会自动redirect到重定向后的地址  
        conn.setInstanceFollowRedirects(false);  
        conn.connect();  
        String result = getReturn(conn);  
    }  
  
    /*请求url获取返回的内容*/  
    public static String getReturn(HttpsURLConnection connection) throws IOException{  
        StringBuffer buffer = new StringBuffer();  
        //将返回的输入流转换成字符串  
        try(InputStream inputStream = connection.getInputStream();  
            InputStreamReader inputStreamReader = new InputStreamReader(inputStream, ConstantInfo.CHARSET);  
            BufferedReader bufferedReader = new BufferedReader(inputStreamReader);){  
            String str = null;  
            while ((str = bufferedReader.readLine()) != null) {  
                buffer.append(str);  
            }  
            String result = buffer.toString();  
            return result;  
        }  
}

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值