IT数码 购物 网址 头条 软件 日历 阅读 图书馆
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
图片批量下载器
↓批量下载图片,美女图库↓
图片自动播放器
↓图片自动播放器↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁
 
   -> 网络协议 -> 2021SC@SDUSC Zxing开源代码(十一)URL请求处理 -> 正文阅读

[网络协议]2021SC@SDUSC Zxing开源代码(十一)URL请求处理


前言

在上次的博客中,我们分析了如果扫描图书的ISBN码后,所进行的处理操作。但是对于其中连接网络,打开网页URL的部分并没有展开分析。这部分功能主要是通过一个叫作 HttpHelper 的类来实现的,因此本次代码分析将以其为重点展开。


一、HttpURLConnection

在Android开发中网络请求是最常用的操作之一, Android SDK中对HTTP也提供了很好的支持,其中就包括标准Java接口(java.NET) —-HttpURLConnection,可以实现简单的基于URL请求、响应功能

HttpURLConnection的使用步骤:
在这里插入图片描述

对于HttpURLConnection的理解:

  • 任何网络连接都需要经过Socket才能连接,HttpURLConnection使用中并没有设置Socket,所以说HttpURLConnection并不是底层的连接,而是在底层连接上的一个请求
  • 虽然底层的网络连接可以被多个HttpURLConnection实例共享,但每一个HttpURLConnection实例只能发送一个请求。请求结束之后,应该调用HttpURLConnection实例的 InputStream 或 OutputStream的close() 方法以释放请求的网络资源。不过对于持久化连接,需要用 disconnect() 方法关闭底层连接的socket。
  • HttpURLConnection 只是一个抽象类,只能通过 url.openConection() 方法创建具体的实例。严格来说,openConection() 方法返回的是 URLConnection 的子类。根据 url 对象的不同,如可能不是 http:// 开头的,那么 openConection() 返回的可能就不是 HttpURLConnection

二、代码分析

在全局代码中,一共有多处使用到了 HttpHelper,这些调用类都涉及根据URL打开网页的操作,而其中调用了 HttpHelper 的方法 downloadViaHttp(String uri, ContentType type),来获取网页请求结果
在这里插入图片描述

downloadViaHttp

在 HttpHelper 中,downloadViaHttp 进行了方法重载,外部类调用的方法都是

  public static CharSequence downloadViaHttp(String uri, ContentType type) throws IOException {
    return downloadViaHttp(uri, type, Integer.MAX_VALUE);
  }

其中参数分别为:

参数含义
uri检索的URL地址
typeContentType类是HTTP支持的内容类型,有:HTML/JSON/XML/TEXT

重载的方法多了一个参数 int maxChars 来表示读取到的最大字符数,在该方法中,其根据 ContentType ,来将不同类型解析为了字符串格式,以便提交

  public static CharSequence downloadViaHttp(String uri, ContentType type, int maxChars) throws IOException {
    String contentTypes;
    switch (type) {
      case HTML:
        contentTypes = "application/xhtml+xml,text/html,text/*,*/*";
        break;
      case JSON:
        contentTypes = "application/json,text/*,*/*";
        break;
      case XML:
        contentTypes = "application/xml,text/*,*/*";
        break;
      default: // Includes TEXT
        contentTypes = "text/*,*/*";
    }
    return downloadViaHttp(uri, contentTypes, maxChars);
  }

而最后调用的 downloadViaHttp 方法,则真正的进行了网络请求

private static CharSequence downloadViaHttp(String uri, String contentTypes, int maxChars) throws IOException

其首先创建了URL对象,而后获取 HttpURLConnection 对象实例,这里的 safelyOpenConnection 继承了 HttpURLConnection,其主要是一些异常处理操作,来排除建立的对象非 HttpURLConnection 实例的情况(如果 url 不是 http:// 开头的,那么 openConection() 返回的可能就不是 HttpURLConnection)

      URL url = new URL(uri);
      HttpURLConnection connection = safelyOpenConnection(url);

创建对象后,需要设置 http 请求头;同时设置所有的 http 连接自动处理重定向

      connection.setInstanceFollowRedirects(true); 
      connection.setRequestProperty("Accept", contentTypes);
      connection.setRequestProperty("Accept-Charset", "utf-8,*");
      connection.setRequestProperty("User-Agent", "ZXing (Android)");

而后获取状态码

int responseCode = safelyConnect(connection);

根据状态码不同进行不同的操作:
在这里插入图片描述
对于 HttpURLConnection.HTTP_MOVED_TEMP 的情况:

          case HttpURLConnection.HTTP_MOVED_TEMP:
          // 在返回的Response的Location字段可以得到重定向地址的URL
            String location = connection.getHeaderField("Location");
            if (location != null) {
              uri = location;
              // 重定向计数
              redirects++;
              continue;
            }
            throw new IOException("No Location");

这里需要注意重定向的页面不能过多,在方法一开始也进行了限制

private static CharSequence downloadViaHttp(String uri, String contentTypes, int maxChars) throws IOException {
    int redirects = 0;
    while (redirects < 5) {
    ......
    }
    throw new IOException("Too many redirects");
}

对于 HttpURLConnection.HTTP_OK 的情况:
其调用了 consume 方法,来获得服务器返回的输入流,并将其作为结果返回

  private static CharSequence consume(URLConnection connection, int maxChars) throws IOException {
    // 获取服务器返回数据的编码格式
    String encoding = getEncoding(connection);
    StringBuilder out = new StringBuilder();
    // 读取返回的输入流
    try (Reader in = new InputStreamReader(connection.getInputStream(), encoding)) {
      char[] buffer = new char[1024];
      int charsRead;
      while (out.length() < maxChars && (charsRead = in.read(buffer)) > 0) {
        out.append(buffer, 0, charsRead);
      }
    }
    return out;
  }

总结

通过本次代码分析,了解了Zxing项目在处理URL请求时的操作,同时熟悉了Android开发中网络请求的流程。到这里,整个 Zxing 项目有关结果处理的重点部分就基本分析完了。接下来将会把重点放在在 Zxing 安卓端使用编码功能所进行的处理操作

  网络协议 最新文章
使用Easyswoole 搭建简单的Websoket服务
常见的数据通信方式有哪些?
Openssl 1024bit RSA算法---公私钥获取和处
HTTPS协议的密钥交换流程
《小白WEB安全入门》03. 漏洞篇
HttpRunner4.x 安装与使用
2021-07-04
手写RPC学习笔记
K8S高可用版本部署
mySQL计算IP地址范围
上一篇文章      下一篇文章      查看所有文章
加:2021-11-28 11:37:38  更:2021-11-28 11:38:18 
 
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁

360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年11日历 -2024/11/26 9:46:08-

图片自动播放器
↓图片自动播放器↓
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
图片批量下载器
↓批量下载图片,美女图库↓
  网站联系: qq:121756557 email:121756557@qq.com  IT数码