【web server】HTTP协议如何解析or封装

本文涉及的产品
公共DNS(含HTTPDNS解析),每月1000万次HTTP解析
全局流量管理 GTM,标准版 1个月
云解析 DNS,旗舰版 1个月
简介: 【web server】HTTP协议如何解析or封装

HTTP协议(关于HTTP协议之前的文章有写过)如何解析or封装?

首先来看下这块的处理过程,有一个整体的概念:

void Http::process() {
  //主线程读完数据后,来到这里处理
  HTTP_CODE read_ret = process_read();
  if (read_ret == NO_REQUEST) {
    //解析完数据发现客户端没有请求,直接退出
    return ;
  }
  //如果有请求,根据刚才解析的结果,封装报文
  bool write_ret = process_write(read_ret);
  if (!write_ret) {
    close_conn();
  }
  //告诉主线程,报文已经封装好了,可以发送了!
  modfd(s_iEpollfd, m_iSockFd, EPOLLOUT);
}

主线程读数据:

bool Http::read() {
  if (m_read_idx >= READ_BUFFER_SIZE) {
    return false;
  }
  int bytes_read = 0;
  while (true) {
    bytes_read = recv(m_iSockFd, m_read_buf + m_read_idx, READ_BUFFER_SIZE - m_read_idx, 0);
    if (bytes_read == -1) {
      if (errno == EAGAIN || errno == EWOULDBLOCK) {
        break;
      }
      return false;
    } else if (bytes_read == 0) {
      return false;
    }
    m_read_idx += bytes_read;
  }
  return true;
}

读到的正是这样一行一行的数据:

将数据循环读到m_read_buf中,接着开始处理读到的数据:

Http::HTTP_CODE Http::process_read() 
{
  ...
  while (...) {
    //拿到每一行数据
    text = get_line();
    switch (m_check_state) {
        case CHECK_STATE_REQUESTLINE: {
          //处理请求行
          parse_request_line(text);
          ...
          break;
        }
        case CHECK_STATE_HEADER: {
          //处理头部字段
          parse_headers(text);
          ...
          break;
        }
        default: {
          return INTERNAL_ERROR;
        }
    }
  }
}

用一个变量m_check_state来表示分析状态:

enum CHECK_STATE {
  CHECK_STATE_REQUESTLINE = 0, //当前正在分析请求行
  CHECK_STATE_HEADER  //当前正在分析头部字段
};

以便在parse_request_line之后改变状态,之后进入parse_headers中处理。

分析请求行和头部字段,可以了解到当前客户端要请求的资源的信息以及客户端一些信息。

若在解析的过程中发现客户端请求了页面,则在服务端找到该文件,并写入内存,等待发送,比如在do_request

Http::HTTP_CODE Http::do_request() {
  ...
  //若解析出的请求行中有“/”则默认返回index.html首页面
  if (strcmp(m_url, "/") == 0) {
    strcat(m_url, "index.html");
  }
  //处理其他,比如服务端没有资源,返回404.html 等等
  ...
  //若资源存在,读到内存中,等待发送
}

解析请求行和头部字段后,发现需要返回资源,便按照响应报文的格式封装报文并发送:

bool Http::process_write(HTTP_CODE ret) {
  switch (ret) {
    ...
    case NO_RESOURCE: {
      add_status_line(404, error_404_title);
      add_headers(strlen(error_404_form));
      add_content(error_404_form);
      break;
    }
    case FILE_REQUEST: {
      add_status_line(200, ok_200_title);
      add_headers(file.size());
      add_content(file);
      break;
    }
    default: {
      return false;
    }
  }
  return true;
}

add_status_line用来添加状态行,add_headers用来添加头部字段(之后添加一行空行),add_content用来添加内容。

至此,响应报文也就封装完成了,之后通知主线程发送报文即可。

相关文章
|
24天前
|
缓存 安全 网络安全
代理协议解析:如何根据需求选择HTTP、HTTPS或SOCKS5?
本文详细介绍了HTTP、HTTPS和SOCKS5三种代理协议的特点、优缺点以及适用场景。通过对比和分析,可以根据具体需求选择最合适的代理协议。希望本文能帮助您更好地理解和应用代理协议,提高网络应用的安全性和性能。
56 17
|
1月前
|
网络协议 网络安全 数据安全/隐私保护
HTTP 协议浅析
通过对HTTP协议的深入了解,开发者可以更好地设计和优化Web应用,提高数据传输效率和用户体验。
109 21
|
2月前
|
缓存 网络协议 前端开发
Web 性能优化|了解 HTTP 协议后才能理解的预加载
本文旨在探讨和分享多种预加载技术及其在提升网站性能、优化用户体验方面的应用。
Web 性能优化|了解 HTTP 协议后才能理解的预加载
|
2月前
|
XML JSON 前端开发
HTTP协议,Content-Type格式介绍篇
通过理解和正确使用Content-Type头字段,可以确保数据在网络上传输时的正确性和高效性,提升网络应用的可靠性和用户体验
131 28
|
2月前
|
XML JSON 前端开发
HTTP协议,Content-Type格式介绍篇
通过理解和正确使用Content-Type头字段,可以确保数据在网络上传输时的正确性和高效性,提升网络应用的可靠性和用户体验。
241 25
|
2月前
|
安全 网络协议 网络安全
解析HTTP代理服务器不稳定致使掉线的关键原因
随着数字化发展,网络安全和隐私保护成为核心需求。HTTP代理服务器掉线原因主要包括:1. 网络问题,如本地网络不稳定、路由复杂;2. 服务器质量差、IP资源不稳定;3. 用户配置错误、超时或请求频率异常;4. IP失效或协议不兼容。这些问题会影响连接稳定性。
87 8
|
2月前
|
XML JSON 前端开发
HTTP协议,Content-Type格式介绍篇
通过理解和正确使用Content-Type头字段,可以确保数据在网络上传输时的正确性和高效性,提升网络应用的可靠性和用户体验。
293 18
|
3月前
|
前端开发 网络协议 安全
【网络原理】——HTTP协议、fiddler抓包
HTTP超文本传输,HTML,fiddler抓包,URL,urlencode,HTTP首行方法,GET方法,POST方法
|
6月前
|
监控 安全 搜索推荐
设置 HTTPS 协议以确保数据传输的安全性
设置 HTTPS 协议以确保数据传输的安全性
|
3月前
|
网络协议 安全 网络安全
探索网络模型与协议:从OSI到HTTPs的原理解析
OSI七层网络模型和TCP/IP四层模型是理解和设计计算机网络的框架。OSI模型包括物理层、数据链路层、网络层、传输层、会话层、表示层和应用层,而TCP/IP模型则简化为链路层、网络层、传输层和 HTTPS协议基于HTTP并通过TLS/SSL加密数据,确保安全传输。其连接过程涉及TCP三次握手、SSL证书验证、对称密钥交换等步骤,以保障通信的安全性和完整性。数字信封技术使用非对称加密和数字证书确保数据的机密性和身份认证。 浏览器通过Https访问网站的过程包括输入网址、DNS解析、建立TCP连接、发送HTTPS请求、接收响应、验证证书和解析网页内容等步骤,确保用户与服务器之间的安全通信。
199 3

推荐镜像

更多