前言

HI,欢迎来到裴智飞的《每周一博》。今天是九月第三周,我给大家介绍一下安卓如何使用https。

HTTP协议被用于在Web浏览器和网站服务器之间传递信息,HTTP协议以明文方式发送内容,不提供任何方式的数据加密,如果攻击者截取了Web浏览器和网站服务器之间的传输报文,就可以直接读懂其中的信息,因此,HTTP协议不适合传输一些敏感信息,比如:信用卡号、密码等支付信息。

为了解决HTTP协议的这一缺陷,需要使用另一种协议:安全套接字层超文本传输协议HTTPS,为了数据传输的安全,HTTPS在HTTP的基础上加入了SSL协议,SSL依靠证书来验证服务器的身份,并为浏览器和服务器之间的通信加密。

HTTPS和HTTP的区别主要如下:

https协议需要到ca申请证书,一般免费证书较少,因而需要一定费用。

http是超文本传输协议,信息是明文传输,https则是具有安全性的ssl加密传输协议。

http的连接很简单,是无状态的;HTTPS协议是由SSL+HTTP协议构建的可进行加密传输、身份认证的网络协议,比http协议安全。

安卓里使用https的步骤如下,创建一个HttpsURLConnection并设置属性,然后去效验本地证书,接着发起请求,接受结果。

1.创建一个HttpsURLConnection并设置属性

URL url = new URL("https://baidu.com");

HttpsURLConnection urlConnection = url.openConnection();

InputStream in = urlConnection.getInputStream();

urlConnection.setInstanceFollowRedirects(false);

urlConnection.setDoOutput(true);

urlConnection.setDoInput(true);

urlConnection.setConnectTimeout(Common.TIME_OUT);

urlConnection.setReadTimeout(Common.FILE_TIME_OUT);

urlConnection.setRequestMethod("POST");

urlConnection.setRequestProperty("Content-Type", "application/x-www-form-urlencoded; charset=utf-8");

urlConnection.setRequestProperty("Accept-Encoding", "gzip");

2.效验本地证书有两种方式,一种是不安全的,什么证书都相信,另一种则是只相信指定的证书,对其进行效验。

效验要通过SSLSocketFactory创建的 SSLSocket来进行,默认的 SSLSocketFactory校验服务器的证书时,会信任设备内置的100多个根证书。

private synchronized SSLSocketFactory getDefaultSSLSocketFactory() {

try {

SSLContext sslContext = SSLContext.getInstance("TLS");

sslContext.init(null, null, null);

return defaultSslSocketFactory = sslContext.getSocketFactory();

} catch (GeneralSecurityException e) {

throw new AssertionError();

}

}

校验服务器的证书,其实就是通过TrustManager来操作的,更一般的说是X509TrustManager;

private static synchronized SSLSocketFactory getDefaultSSLSocketFactory() {

try {

SSLContext sslContext = SSLContext.getInstance("TLS");

sslContext.init(null, new TrustManager[]{

new X509TrustManager() {

public void checkClientTrusted(X509Certificate[] x509Certificates, String s) throws CertificateException {

}

public void checkServerTrusted(X509Certificate[] x509Certificates, String s) throws CertificateException {

}

public X509Certificate[] getAcceptedIssuers() {

return new X509Certificate[0];

}

}

}, null);

return sslContext.getSocketFactory();

} catch (GeneralSecurityException e) {

throw new AssertionError();

}

}

这种效验过程什么证书都会信任,没有安全性可言,接下来我们看正确的配置。

public static SSLContext getSSLContext() {

// 从assets中加载证书,取到证书的输入流

InputStream is = getApplicationContext().getAssets().open("srca.cer");

// 证书工厂

CertificateFactory cf = CertificateFactory.getInstance("X.509");

Certificate ca = cf.generateCertificate(is);

// 加载证书到密钥库中

String keyStoreType = KeyStore.getDefaultType();

KeyStore keyStore = KeyStore.getInstance(keyStoreType);

keyStore.load(null);

keyStore.setCertificateEntry("cert", ca);

// 加载密钥库到信任管理器

String algorithm = TrustManagerFactory.getDefaultAlgorithm();

TrustManagerFactory trustManagerFactory = TrustManagerFactory.getInstance(algorithm);

trustManagerFactory.init(keyStore);

TrustManager[] trustManagers = trustManagerFactory.getTrustManagers();

// 用 TrustManager 初始化一个 SSLContext

SSLContext sslContext = SSLContext.getInstance("TLS");

sslContext.init(null, trustManagers, null);

urlCon.setSSLSocketFactory(sslContext.getSocketFactory());

有个问题:Android P 限制了明文流量的网络请求,非加密的流量请求都会被系统禁止掉,如果当前应用的请求是http请求,而非 https,这样就会导系统禁止当前应用进行该请求,如果WebView 的url用http协议,同样会出现加载失败,https则不受影响。

所以需要做一个简单的配置,在manifest的application标签下增加一行配置,同时增加一个xml文件。

android:networkSecurityConfig="@xml/network_security_config"

然后传递参数并获取结果

Iterator> it = params.entrySet().iterator();

while (it.hasNext()) {

Entry element = (Entry) it.next();

sb2.append(element.getKey());

sb2.append("=");

sb2.append(element.getValue());

sb2.append("&");

}

if (sb2.length() > 0) {

sb2.deleteCharAt(sb2.length() - 1);

}

os = urlCon.getOutputStream();

os.write(sb2.toString().getBytes());

os.flush();

int statusCode = urlCon.getResponseCode();

if (statusCode == HttpsURLConnection.HTTP_OK) {

is = urlCon.getInputStream();

String contentEncoding = urlCon.getContentEncoding();

if ((contentEncoding != null) && contentEncoding.contains("gzip")) {

is = new GZIPInputStream(new BufferedInputStream(is));

}

// 创建字节输出流对象

baos = new ByteArrayOutputStream();

// 定义读取的长度

int len = 0;

// 定义缓冲区

byte[] buffer = new byte[1024];

// 按照缓冲区的大小,循环读取

while ((len = is.read(buffer)) != -1) {

// 根据读取的长度写入到os对象中

baos.write(buffer, 0, len);

}

// 返回字符串

String result = new String(baos.toByteArray(), "utf-8");

}

结尾:

这样一个使用本地证书效验的https请求就算完成了,但是如果不对内容做加密,而只是依赖https通道是不安全的,因为请求https的证书如果还用https,那么就是一个无尽循环,而用http有如何保证安全呢?另外https比较消耗流量,所以可以采用http配合高强度加密的方式来进行网络传输,关于安卓里面使用加解密的知识我会在下一篇文章里编写,我们下周再见。

android采用Https的解决方案,Android使用https相关推荐

  1. android采用什么图标单位,Android支持的长度单位

    dp(dip): device independent pixels(设备独立像素). 不同设备有不同的显示效果,这个和设备硬件有关,一般我们为了支持WVGA.HVGA和QVGA 推荐使用这个,不依赖 ...

  2. Android采用HTML布局,入门Android布局之html

    新建一个能顺利运行的Android工程后,会发现程序入口AndroidManifest.xml和布局文件activity_layout.xml都是xml文件.xml是Extensible Markup ...

  3. android https详解,如何使用HTTPS和HTTP来解析Android中的JSON数据?

    我跟随this到Parse Json在Android中 我用HttpData处理程序成功完成了它. 在这里,我成功将数据发布到服务器并获得响应.. 现在我想在HTTPS的一部分中使用它. 可以任何人建 ...

  4. Android https证书过期,Android 的 HTTPS 证书过期异常

    8种机械键盘轴体对比 本人程序员,要买一个写代码的键盘,请问红轴和茶轴怎么选? 对于 HTTPS 服务器证书过期的问题,由于 Android 安全库的不断更新,尽管在证书验证的时候抛出的异常大同小异, ...

  5. Android——自建CA证书,实现https请求

    Android 使用https 协议请求客户端 server端操作 自己创建 CA 证书 拿自建CA 证书创建 server 端证书 创建 https 服务 Android客户端操作 创建项目并引入相 ...

  6. 下载 https://github.com/android 上的全部源代码

    从 https://android.googlesource.com/ 上弄源代码下来真是不容易,不但得用 vpn,repo 还得半天.github 的速度就快多了,关键是不用 vpn,随时可以下载. ...

  7. Android采用pm实现静默安装(降级安装)的解决方案

    最近在做一个apk分析器,里面可以解析系统中所有安装app的信息,并提供组内开发的apk文件下载.静默安装(包括降级安装),其中在降级安装中难度较大,在Android4.4与Android 8的解决方 ...

  8. Eclipse新建Android项目报错解决方案详细汇总

    本文记录刚接触Android开发搭建环境后新建工程各种可能的报错,并亲身经历漫长的解决过程(╥╯^╰╥),寻找各种偏方,避免大家采坑,希望能帮助到大家. 报错信息 出错一:The import and ...

  9. android图片压缩终极解决方案

    如题,多种压缩方式常用的有尺寸压缩.质量压缩以及通过JNI调用libjpeg库来进行压缩,三种方式结合使用实现指定图片内存大小,清晰度达到最优,下面就先分别介绍下这几种压缩方式. 原文出处:http: ...

最新文章

  1. R语言sink函数保存文件实战
  2. Amazon Corretto技术细节探秘
  3. FCN全连接卷积网络(5)--Fully Convolutional Networks for Semantic Segmentation阅读(相关工作部分)
  4. iPhone 6S GPU到底多强
  5. 2019澳门理工计算机作品决赛,我校学子在2019年泛珠三角+大学生计算机作品赛总决赛中斩获佳绩...
  6. python发音模块-python声音模块
  7. 安卓Toast显示提示消息(自定义view,根据子线程消息显示提示)
  8. LinkedList的线程安全解决办法
  9. 上下相机贴合对位计算公式_ccd视觉自动对位贴合机主要应用在哪里?
  10. HDU-1150 Machine Schedule 二分图匹配
  11. jQuery:级联查询-省份城市信息
  12. Scrapy抓取起点中文网排行榜
  13. .prevent 与 .stop,以及解决其他地方长按,文本被选中的问题
  14. 51单片机和Arduino有什么区别?
  15. 保研面试/考研复试:英语口语面试必备话题及常用句型句式整理(三)
  16. 如何快速有效提升网站的百度排名
  17. 2022-2027年中国海参行业市场调研及未来发展趋势预测报告
  18. Win10系统安装MySQL5.5.62 解压版
  19. 多线程进阶:volatile的作用以及实现原理
  20. 深入分析RestController与Controller

热门文章

  1. 【能效分析】安科瑞变电所运维云平台解决方案应用分析
  2. 数据库修改字段类型但是有旧数据处理步骤
  3. AI制作牙膏笔刷文字
  4. 第十课:人口金字塔、漏斗图、箱线图
  5. uni-app 边框线 app 上更粗的解决办法
  6. 微信域名检测、防封,微信跳转技术揭秘(一)
  7. 失物招领小程序创业计划书
  8. 渣男手册,安卓恋爱话术库API
  9. 关于我从程序员变成“韭零后“这件事【node实现邮件发送】
  10. 【备忘】python绘制地图实例