Android网络开发学习总结

本文深入探讨了Android网络框架Volley的工作原理,包括其请求处理流程和优缺点,以及如何解决重复请求问题。同时,介绍了OkHttp的缓存处理和与HttpURLConnection的关系。还提到了WebSocket与HTTP的区别,以及GET和POST请求的不同。此外,文章分析了网络请求的基本流程和关键协议,如TCP与UDP,以及HTTP状态码的含义。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

目录

一、网络框架对比和源码分析

1.Volley: 

重复请求问题

2.okhttp

3.Retrofit

4.其它

二、网络细节

1.Get与post区别

2.HttpURLConnection与HttpClient

三、网络请求流程

四、网络协议

1.HTTP相关

2.HTTP与HTTPS

3.http statusCode(状态码)

4.TCP与UDP

5.数字证书、数字签名等


一、网络框架对比和源码分析

自己去设计网络请求框架,怎么做?

Android常用的网络框架

1.Volley: 

转载自:Android网络框架-Volley

其中蓝色的是主线程,绿色的是缓存线程,黄色的是网络线程

1.当一个Request请求添加到RequestQueue请求队列中,Volley就开始工作了。RequestQueue请求队列中持有一个CacheDispatcher缓存管家和一组NetworkDispatcher网络管家。

2.RequestQueue会先叫来CacheDispatcher缓存管家,让他去看看,当前请求的数据在没在cache中。

     2.1.当前的数据在cache中,那就把数据从cache中取出来,然后经过一番加工,将加工好的数据交付给主线程。

     2.2.当前数据没在cache中,进行第3步。

3.进行到了这一步,那肯定是数据没有在缓存中,那只能去网络中获取了,这时候RequestQueue会叫来NetworkDispatcher,NetworkDispatcher可是有一帮呢,其实这是一个线程池,默认情况下会启动4个线程去网络下载数据。所以RequestQueue把当前闲着的NetworkDispatcher叫来,给他们分配任务。

4.拿到任务的NetworkDispatcher就会去网络上下载数据了,与此同时,他会判断下载到的数据能否写入到cache缓存中,如果可以的话就写入cache,以便于下一次直接从cache中获取到数据。最后,将数据加工,交付给主线程。
 

优缺点:Android Volley的优缺点及源码分析

volley中为了提高请求处理的速度,采用了ByteArrayPool进行内存中的数据存储的,如果下载大量的数据,这个存储空间就会溢出,所以不适合大量的数据。

volley 的线程池是基于数组实现的,即newFixedThreadPool(4)核心线程数不超过4个,也不会自动扩展,一旦大数据上传或者下载长时间占用了线程资源,后续所有的请求都会被阻塞。最后,Volley是不适合上次和下载大文件

重复请求问题

setRetryPolicy 设置超时时间,重连次数。

解决Volley重复请求问题

2.okhttp

 原理参考:OkHttp原理

在这里插入图片描述

okhttp如何处理网络缓存的: 使用CacheControl处理,Request.Builder().cacheControl(cache)

HttpUrlConnection 和 okhttp关系: HttpUrlConnection 在Android4.4之后,是通过okhttp实现的,用HttpHandler作为桥梁过渡。

建造者模式。分发器、拦截器

2.1 分发器

    分发器用线程池和队列来调度任务请求。分同步请求和异步请求。

2.2 拦截器


    五大默认拦截器:是否retry, 桥接应用与服务器,处理缓存,建立与服务器的连接,与服务器通信。

2.2.1 自定应应用拦截器和网络拦截器区别
  • 首先,应用拦截器在RetryAndFollowUpInterceptorCacheInterceptor之前,所以一旦发生错误重试或者网络重定向,网络拦截器可能执行多次,因为相当于进行了二次请求,但是应用拦截器永远只会触发一次。另外如果在CacheInterceptor中命中了缓存就不需要走网络请求了,因此会存在短路网络拦截器的情况。
  • 其次,除了CallServerInterceptor之外,每个拦截器都应该至少调用一次realChain.proceed方法。实际上在应用拦截器这层可以多次调用proceed方法(本地异常重试)或者不调用proceed方法(中断),但是网络拦截器这层连接已经准备好,可且仅可调用一次proceed方法。
  • 最后,从使用场景看,应用拦截器因为只会调用一次,通常用于统计客户端的网络请求发起情况;而网络拦截器一次调用代表了一定会发起一次网络通信,因此通常可用于统计网络链路上传输的数据。

作者:程序员江同学
链接:https://juejin.cn/post/7020027832977850381
来源:稀土掘金
著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。

2.3 OKHttp如何复用TCP连接

TCP握手耗时,新建连接消耗资源。复用TCP能减少请求时间。

# ExchangeFinder
//为承载新的数据流 寻找 连接。寻找顺序是 已分配的连接、连接池、新建连接
private RealConnection findConnection(int connectTimeout, int readTimeout, int writeTimeout,
    int pingIntervalMillis, boolean connectionRetryEnabled) throws IOException {
  synchronized (connectionPool) {
    // 1.尝试使用 已给数据流分配的连接.(例如重定向请求时,可以复用上次请求的连接)
    releasedConnection = transmitter.connection;
    result = transmitter.connection;

    if (result == null) {
      // 2. 没有已分配的可用连接,就尝试从连接池获取。(连接池稍后详细讲解)
      if (connectionPool.transmitterAcquirePooledConnection(address, transmitter, null, false)) {
        result = transmitter.connection;
      }
    }
  }

  synchronized (connectionPool) {
    if (newRouteSelection) {
      //3. 现在有了IP地址,再次尝试从连接池获取。可能会因为连接合并而匹配。(这里传入了routes,上面的传的null)
      routes = routeSelection.getAll();
      if (connectionPool.transmitterAcquirePooledConnection(address, transmitter, routes, false)) {
        foundPooledConnection = true;
        result = transmitter.connection;
      }
    }

  // 4.第二次没成功,就把新建的连接,进行TCP + TLS 握手,与服务端建立连接. 是阻塞操作
  result.connect(connectTimeout, readTimeout, writeTimeout, pingIntervalMillis,
      connectionRetryEnabled, call, eventListener);

  synchronized (connectionPool) {
    // 5. 最后一次尝试从连接池获取,注意最后一个参数为true,即要求 多路复用(http2.0)
    //意思是,如果本次是http2.0,那么为了保证 多路复用性,(因为上面的握手操作不是线程安全)会再次确认连接池中此时是否已有同样连接
    if (connectionPool.transmitterAcquirePooledConnection(address, transmitter, routes, true)) {
      // 如果获取到,就关闭我们创建里的连接,返回获取的连接
      result = transmitter.connection;
    } else {
      //最后一次尝试也没有的话,就把刚刚新建的连接存入连接池
      connectionPool.put(result);
    }
  }
 
  return result;
}

2.4 OKHttp空闲连接如何清除

  1. 在将连接加入连接池时就会启动定时任务
  2. 有空闲连接的话,如果最长的空闲时间大于5分钟 或 空闲数 大于5,就移除关闭这个最长空闲连接;如果 空闲数 不大于5 且 最长的空闲时间不大于5分钟,就返回到5分钟的剩余时间,然后等待这个时间再来清理。
  3. 没有空闲连接就等5分钟后再尝试清理。
  4. 没有连接不清理。

2.5 OkHttp 优点

  1. 使用简单;
  2. 扩展性强:自定义应用拦截器,网络拦截器等;
  3. 功能强大,支持多种协议;
  4. 通过连接池复用底层TCP,减少请求延时;
  5. 支持GZIP,减少数据流量;
  6. ……


2.6 使用方法参考

OKhttp使用方法 

  1. OkHttpClient 申明工具类,
  2. Request 封装请求的地址参数等,
  3. 并传入newCall做参数,
  4. enqueue插入队列,
  5. 在onResponse 回调中处理。

    

可和RxJava, Retrofit 搭配使用。

3. RXJava

建造者模式、观察者模式、链式处理,


4.Retrofit

retrofit设计思想

  1. 底层基于OkHttp,
  2. 用注解方式申明url路径等,语言简洁, 链式处理,
  3. 动态代理 封装了一些通用逻辑

5.其它

WebSocket与socket的区别:WebSocket 和Http都是可靠传输的应用层协议,但WebSocket能双向通信。Socket不是协议,是为了通信抽象出来的一层接口。   WebSocket用于即时通讯,替代轮询。

二、网络细节

1.Get与post区别

参考:Get和post区别

(1)post更安全(不会作为url的一部分,不会被缓存、保存在服务器日志、以及浏览器浏览记录中)
(2)post发送的数据更大(get有url长度限制,非协议的限制,而是浏览器和服务器限制了长度 Get传参长度的误解
(3)post能发送更多的数据类型(get只能发送ASCII字符)
(4)post比get慢
(5)post用于修改和写入数据,get一般用于搜索排序和筛选之类的操作(淘宝,支付宝的搜索查询都是get提交),目的是资源的获取,读取数据.

get效率高
 

2.HttpURLConnection与HttpClient

Android 2.3版本及以后,HttpURLConnection则是最佳的选择。它的API简单,体积较小,因而非常适用于Android项目。压缩和缓存机制可以有效地减少网络访问的流量,在提升速度和省电方面也起到了较大的作用。

Android6.0 后已经不支持HttpClient。

三、网络请求流程

描述一次网络请求的流程:

  1.  通过URL查找IP;
  2. 对IP结果建立TCP链接;
  3. 向服务器发送数据;
  4. 服务器解析并返回数据;
  5. 浏览器解析HTML;

client如何确定自己发送的消息被server收到?: 需要应用层实现,server收到信息后给予反馈。

Https请求慢的解决办法?(提示:DNS,携带数据,直接访问IP)

四、网络协议

1.HTTP相关

HTTP协议:是用于从万维网服务器传输超文本到本地浏览器的传送协议。

1、简单快速:客户向服务器请求服务时,只需传送请求方法和路径。

2、灵活:HTTP允许传输任意类型的数据对象。正在传输的类型由Content-Type加以标记。

3.无连接:无连接的含义是限制每次连接只处理一个请求。服务器处理完客户的请求,并收到客户的应答后,即断开连接。采用这种方式可以节省传输时间。

4.无状态:HTTP协议是无状态协议。无状态是指协议对于事务处理没有记忆能力。缺少状态意味着如果后续处理需要前面的信息,则它必须重传,这样可能导致每次连接传送的数据量增大。另一方面,在服务器不需要先前信息时它的应答就较快。

5、支持B/S及C/S模式。

2.HTTP与HTTPS

HTTP与HTTPS的区别以及如何实现安全性:https安全,效率低,要安装证书,申请证书会产生费用,可以防止运营商劫持;

https内容传输的加密上使用的是对称加密,非对称加密只作用在证书验证阶段。

为什么内容传输用的是对称加密:

首先:非对称加密的加解密效率是非常低的,而 http 的应用场景中通常端与端之间存在大量的交互,非对称加密的效率是无法接受的。

另外:在 HTTPS 的场景中只有服务端保存了私钥,一对公私钥只能实现单向的加解密,所以 HTTPS 中内容传输加密采取的是对称加密,而不是非对称加密。


HTTPS用的是对称加密还是非对称加密

3.http statusCode(状态码)

1xx:指示信息,表示请求已经接收,继续处理。

201-206都表示服务器成功处理了请求的状态代码,说明网页可以正常访问。

300-3007表示的意思是:要完成请求,您需要进一步进行操作。通常,这些状态代码是永远重定向的。

4XXHTTP状态码表示请求可能出错,会妨碍服务器的处理。 (客户端错误

500至505表示的意思是:服务器在尝试处理请求时发生内部错误。这些错误可能是服务器本身的错误,而不是请求出错。

4.TCP与UDP

TCP与UDP的区别:

1.基于连接与无连接;

2.对系统资源的要求(TCP较多,UDP少);

3.UDP程序结构较简单;

4.流模式与数据报模式 ;

5.TCP保证数据正确性,UDP可能丢包,TCP保证数据顺序,UDP不保证。

5.数字证书、数字签名等

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值