使Volley完美支持自定义证书的Https
其实在最早的版本里,Volley甚至是不支持https协议的,只能跑http,当然你也可以自己修改他的源码让他支持,如今volley的代码经过一些改进以后,
已经可以完美支持https协议了,无论是在2.3版本以上还是在2.3版本以下,大家可以尝试用volley去访问github 是成功的,但是你如果用volley去访问
12306这种类似的 用自定义证书的网站 就很容易失败。那我下面就把volley 代码稍作修改,让volley也可以完美支持自定义证书的https请求。
当然代码只是展示功能使用,你们可以用更优雅的方式 ----实现一个HttpStack,然后直接传你自定义好的stack即可。我这里图简便就写了个最简单
的演示代码。其实难倒是也不难,主要还是要考虑2.3版本以上和以下的两种情况。
第一步,把你的自定义证书 拷贝到res/raw/下。
第二步,稍微修改下volley的源码
- /*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
- package com.android.volley.toolbox;
- import android.content.Context;
- import android.content.pm.PackageInfo;
- import android.content.pm.PackageManager.NameNotFoundException;
- import android.net.http.AndroidHttpClient;
- import android.os.Build;
- import android.util.Log;
- import com.android.volley.Network;
- import com.android.volley.RequestQueue;
- import org.apache.http.client.HttpClient;
- import org.apache.http.conn.scheme.PlainSocketFactory;
- import org.apache.http.conn.scheme.Scheme;
- import org.apache.http.conn.scheme.SchemeRegistry;
- import org.apache.http.impl.client.DefaultHttpClient;
- import org.apache.http.impl.conn.tsccm.ThreadSafeClientConnManager;
- import org.apache.http.params.BasicHttpParams;
- import org.apache.http.params.HttpParams;
- import java.io.File;
- import java.io.IOException;
- import java.io.InputStream;
- import java.security.KeyManagementException;
- import java.security.KeyStore;
- import java.security.KeyStoreException;
- import java.security.NoSuchAlgorithmException;
- import java.security.UnrecoverableKeyException;
- import java.security.cert.Certificate;
- import java.security.cert.CertificateException;
- import java.security.cert.CertificateFactory;
- import javax.net.ssl.SSLContext;
- import javax.net.ssl.SSLSocketFactory;
- import javax.net.ssl.TrustManagerFactory;
- public class Volley {
- /**
- * Default on-disk cache directory.
- */
- private static final String DEFAULT_CACHE_DIR = "volley";
- private Context mContext;
- /**
- * Creates a default instance of the worker pool and calls {@link RequestQueue#start()} on it.
- *
- * @param context A {@link Context} to use for creating the cache dir.
- * @param stack An {@link HttpStack} to use for the network, or null for default.
- * @return A started {@link RequestQueue} instance.
- */
- public static RequestQueue newRequestQueue(Context context, HttpStack stack, boolean selfSignedCertificate, int rawId) {
- File cacheDir = new File(context.getCacheDir(), DEFAULT_CACHE_DIR);
- String userAgent = "volley/0";
- try {
- String packageName = context.getPackageName();
- PackageInfo info = context.getPackageManager().getPackageInfo(packageName, );
- userAgent = packageName + "/" + info.versionCode;
- } catch (NameNotFoundException e) {
- }
- if (stack == null) {
- if (Build.VERSION.SDK_INT >= ) {
- if (selfSignedCertificate) {
- stack = new HurlStack(null, buildSSLSocketFactory(context, rawId));
- } else {
- stack = new HurlStack();
- }
- } else {
- // Prior to Gingerbread, HttpUrlConnection was unreliable.
- // See: http://android-developers.blogspot.com/2011/09/androids-http-clients.html
- if (selfSignedCertificate)
- stack = new HttpClientStack(getHttpClient(context, rawId));
- else {
- stack = new HttpClientStack(AndroidHttpClient.newInstance(userAgent));
- }
- }
- }
- Network network = new BasicNetwork(stack);
- RequestQueue queue = new RequestQueue(new DiskBasedCache(cacheDir), network);
- queue.start();
- return queue;
- }
- /**
- * Creates a default instance of the worker pool and calls {@link RequestQueue#start()} on it.
- *
- * @param context A {@link Context} to use for creating the cache dir.
- * @return A started {@link RequestQueue} instance.
- */
- public static RequestQueue newRequestQueue(Context context) {
- return newRequestQueue(context, null, false, );
- }
- private static SSLSocketFactory buildSSLSocketFactory(Context context, int certRawResId) {
- KeyStore keyStore = null;
- try {
- keyStore = buildKeyStore(context, certRawResId);
- } catch (KeyStoreException e) {
- e.printStackTrace();
- } catch (CertificateException e) {
- e.printStackTrace();
- } catch (NoSuchAlgorithmException e) {
- e.printStackTrace();
- } catch (IOException e) {
- e.printStackTrace();
- }
- String tmfAlgorithm = TrustManagerFactory.getDefaultAlgorithm();
- TrustManagerFactory tmf = null;
- try {
- tmf = TrustManagerFactory.getInstance(tmfAlgorithm);
- tmf.init(keyStore);
- } catch (NoSuchAlgorithmException e) {
- e.printStackTrace();
- } catch (KeyStoreException e) {
- e.printStackTrace();
- }
- SSLContext sslContext = null;
- try {
- sslContext = SSLContext.getInstance("TLS");
- } catch (NoSuchAlgorithmException e) {
- e.printStackTrace();
- }
- try {
- sslContext.init(null, tmf.getTrustManagers(), null);
- } catch (KeyManagementException e) {
- e.printStackTrace();
- }
- return sslContext.getSocketFactory();
- }
- private static HttpClient getHttpClient(Context context, int certRawResId) {
- KeyStore keyStore = null;
- try {
- keyStore = buildKeyStore(context, certRawResId);
- } catch (KeyStoreException e) {
- e.printStackTrace();
- } catch (CertificateException e) {
- e.printStackTrace();
- } catch (NoSuchAlgorithmException e) {
- e.printStackTrace();
- } catch (IOException e) {
- e.printStackTrace();
- }
- if (keyStore != null) {
- }
- org.apache.http.conn.ssl.SSLSocketFactory sslSocketFactory = null;
- try {
- sslSocketFactory = new org.apache.http.conn.ssl.SSLSocketFactory(keyStore);
- } catch (NoSuchAlgorithmException e) {
- e.printStackTrace();
- } catch (KeyManagementException e) {
- e.printStackTrace();
- } catch (KeyStoreException e) {
- e.printStackTrace();
- } catch (UnrecoverableKeyException e) {
- e.printStackTrace();
- }
- HttpParams params = new BasicHttpParams();
- SchemeRegistry schemeRegistry = new SchemeRegistry();
- schemeRegistry.register(new Scheme("http", PlainSocketFactory.getSocketFactory(), ));
- schemeRegistry.register(new Scheme("https", sslSocketFactory, ));
- ThreadSafeClientConnManager cm = new ThreadSafeClientConnManager(params, schemeRegistry);
- return new DefaultHttpClient(cm, params);
- }
- private static KeyStore buildKeyStore(Context context, int certRawResId) throws KeyStoreException, CertificateException, NoSuchAlgorithmException, IOException {
- String keyStoreType = KeyStore.getDefaultType();
- KeyStore keyStore = KeyStore.getInstance(keyStoreType);
- keyStore.load(null, null);
- Certificate cert = readCert(context, certRawResId);
- keyStore.setCertificateEntry("ca", cert);
- return keyStore;
- }
- private static Certificate readCert(Context context, int certResourceID) {
- InputStream inputStream = context.getResources().openRawResource(certResourceID);
- Certificate ca = null;
- CertificateFactory cf = null;
- try {
- cf = CertificateFactory.getInstance("X.509");
- ca = cf.generateCertificate(inputStream);
- } catch (CertificateException e) {
- e.printStackTrace();
- }
- return ca;
- }
- }
第三步就是调用方式稍微做下修改:
其实主要就是你如果想使用自定义的证书https的时候 第三个参数记得传true,并且把证书也传进去,
当然写的优雅的话还是最好自己写个httpstack,然后volley的源码可以不用改,只需要在使用的时候
传自己的stack即可
http://liuwangshu.cn/application/network/4-volley-sourcecode.html
使Volley完美支持自定义证书的Https的更多相关文章
- Android 使Volley完美支持自定义证书的Https
其实在最早的版本里,Volley甚至是不支持https协议的,只能跑http,当然你也可以自己修改他的源码让他支持,如今volley的代码经过一些改进以后, 已经可以完美支持https协议了,无论是在 ...
- 让个人域名下GithubPage完美支持https
让个人域名下GithubPage完美支持https 欢迎访问完美HTTPS支持的GithubPage个人博客 : https://zggdczfr.cn/ 前言 最近笔记本挂了送去维修,耽误了我的学习 ...
- Retrofit 2.0 超能实践(一),okHttp完美支持Https传输
http: //blog.csdn.net/sk719887916/article/details/51597816 Tamic首发 前阵子看到圈子里Retrofit 2.0,RxJava(Andro ...
- Retrofit 2.0 超能实践,完美支持Https传输
http://blog.csdn.NET/sk719887916/article/details/51597816 前阵子看到圈子里Retrofit 2.0,RxJava(Android), OkHt ...
- Volley框架支持HTTPS请求。
第一次写帖子,嘿嘿. 最近了解到google2013IO大会出了个网络框架,正好项目也需要用到,就看了下. 最后发现接口都是HTTPS的,但是Volley默认是不支持HTTPS,网上找了好久,都没有对 ...
- 并发编程概述 委托(delegate) 事件(event) .net core 2.0 event bus 一个简单的基于内存事件总线实现 .net core 基于NPOI 的excel导出类,支持自定义导出哪些字段 基于Ace Admin 的菜单栏实现 第五节:SignalR大杂烩(与MVC融合、全局的几个配置、跨域的应用、C/S程序充当Client和Server)
并发编程概述 前言 说实话,在我软件开发的头两年几乎不考虑并发编程,请求与响应把业务逻辑尽快完成一个星期的任务能两天完成绝不拖三天(剩下时间各种浪),根本不会考虑性能问题(能接受范围内).但随着工 ...
- iOS 的三种自建证书方法https请求相关配置
如果你的app服务端安装的是SLL颁发的CA,可以使用系统方法直接实现信任SSL证书,关于Apple对SSL证书的要求请参考:苹果官方文档CertKeyTrustProgGuide 这种方式不需要在B ...
- 使用Go和Let's Encrypt证书部署HTTPS
为什么要使用HTTPS?使用HTTPS的途径有哪些?如何用Go来部署HTTPS?拿出你的小本本,你要的干货都在这儿! HTTPS的好处我们已在之前的文章中提高好多.它加密浏览器和服务器之间的流量,保障 ...
- iOS使用自签名证书实现HTTPS请求
概述 在16年的WWDC中,Apple已表示将从2017年1月1日起,所有新提交的App必须强制性应用HTTPS协议来进行网络请求. 默认情况下非HTTPS的网络访问是禁止的并且不能再通过简单粗暴的向 ...
随机推荐
- C语言判断大小端的几种方法
在操作系统中,经常会用到判断大小端,很多面试题中也会经常遇到,以前的时候没有总结过,这里总结一下. 以后用到了就直接可以用了. 所谓的大小端,大致的解释意思就是: [大端模式] CPU对操作数的存放方 ...
- 机器学习与Tensorflow(5)——循环神经网络、长短时记忆网络
1.循环神经网络的标准模型 前馈神经网络能够用来建立数据之间的映射关系,但是不能用来分析过去信号的时间依赖关系,而且要求输入样本的长度固定 循环神经网络是一种在前馈神经网络中增加了分亏链接的神经网络, ...
- django 模型关系
模型关系 关系数据库的威力体现在表之间的相互关联,Django提供了三种最常见的数据库关系:多对一 (many-to-one),多对多(many-to-many),一对一(one-to-one) 多对 ...
- nRF52832 矩阵按键调试 同一列上的按键 任意两个按键 按下 检测不到低电平(电平拉不下来)
参考链接:https://blog.csdn.net/zhanghuaishu0/article/details/78505045 调试过程中发现 同一列上的按键 任意两个按键 按下 检测不到低电平( ...
- C# 判断字符串是否符合十六进制,八进制,二进制和十进制整数格式的正则表达式
/// <summary> /// 判断是否十六进制格式字符串 /// </summary> /// <param name="str">< ...
- Jstl标签汇总
JSTL的核心标签库标签共13个,使用这些标签能够完成JSP页面的基本功能,减少编码工作. 从功能上可以分为4类:表达式控制标签.流程控制标签.循环标签.URL操作标签. (1)表达式控制标签:ou ...
- Centos7安装Mysql8(官方整合包)
1. 下载整合包 [root@master ~]# wget https://dev.mysql.com/get/Downloads/MySQL-8.0/mysql-8.0.12-1.el7.x86_ ...
- 【API知识】MongoTemplate非映射方式操作Document
前言 我是MongoDB小白,刚开始学.不过,我猜大多数使用MongoDB的,都是采用映射方式处理的,即需要有定义好的用于映射的实体类.但是这样的话,如果表的结构在未来可能频繁变动,增删字段,甚至添加 ...
- javascript的作用域和优先级
变量的作用域是在定义时决定的,不是在运行时活动对象是在运行时决定的?如果就创建一个对象,使用完毕就完了,就使用json字面量的方式如果对象被反复创建,反复使用,就使用自定义的构造函数方式优先级内部变量 ...
- U3D GameObject 解读
GameObject本身没有功能,是Unity场景里所有组件的基类,但很多时候我们需要在脚本中操作GameObject.先讲一下GameObject类包含哪些内容,其中常用的用红色标出了 Variab ...