http协议详解
前言
对于http协议,每个人都或多或少地会用到它,因为浏览器的地址栏就有,比如 http://www.baidu.com
HTTP协议
1.http协议简介
HTTP协议是Hyper Text Transfer Protocol(超文本传输协议)的缩写,是用于从万维网(WWW:World Wide Web )服务器传输超文本到本地浏览器的传送协议。
- 应用层协议
- 基于TCP/IP
- 默认端口号:80
- 可用来传递数据(HTML文件, 图片文件, 查询结果等)
2.网站访问过程

首先由Client向Server发起请求,发送HTTP request。
Server收到请求后,进行响应,发送HTTP response。
整个过程可以归纳如下:
- Client向Server发送HTTP request
- 服务器发送状态码,比如"HTTP/1.1 200 OK\r\n\r\n"
- 服务器发送网页文件(HTTP response)
3.http请求消息
消息包括以下格式:请求行+请求头部+空行+请求数据,总共四个部分

举例:
请求行:
POST /examples HTTP/1.1\r\n //请求方式,请求路径和协议版本
请求头:
Accept: application/x-ms-application, image/jpeg, application/xaml+xml, image/gif, image/pjpeg, application/x-ms-xbap, */* //客户端向服务器端表示,我能支持什么类型的数据
Referer: http://localhost:8080/examples/servlets/servlet/RequestParamExample //告诉服务器我是从哪一个页面链接过来的
Accept-Language: zh-CN //支持语言格式
User-Agent: Mozilla/4.0 (compatible; MSIE 8.0; Windows NT 6.1; WOW64; Trident/4.0; SLCC2; .NET CLR 2.0.50727; .NET CLR 3.5.30729; .NET CLR 3.0.30729; Media Center PC 6.0; .NET4.0C; .NET4.0E) //客户端信息
Content-Type: application/x-www-form-urlencoded //提交的数据类型。经过urlencoding编码的form表单的数据
Accept-Encoding: gzip, deflate //gzip, deflate为压缩算法
Host: localhost:8080 //服务器地址
Content-Length: 31 //数据长度
Connection: Keep-Alive //Keep-Alive保持连接
Cache-Control: no-cache //对缓存的操作
请求体:
firstname=zhang&lastname=sansan //发送给服务器的数据
4.请求方式
请求方式在请求头中的第一个字段
序号 | 方法 | 描述 |
---|---|---|
1 | GET(常用) | 请求指定的页面信息,并返回实体主体。 请求信息包含在URL中 |
2 | POST(常用) | 向指定资源提交数据进行处理请求(例如提交表单或者上传文件)。请求数据被包含在请求体中。 |
3 | HEAD | 类似于 GET 请求,只不过返回的响应中没有具体的内容,用于获取报头 |
4 | PUT | 从客户端向服务器传送的数据取代指定的文档的内容。 |
5 | DELETE | 请求服务器删除指定的页面。 |
6 | CONNECT | HTTP/1.1 协议中预留给能够将连接改为管道方式的代理服务器。 |
7 | OPTIONS | 允许客户端查看服务器的性能。 |
8 | TRACE | 回显服务器收到的请求,主要用于测试或诊断。 |
9 | PATCH | 是对 PUT 方法的补充,用来对已知资源进行局部更新 。 |
比如:
https://www.baidu.com/s?ie=UTF-8&wd=滴滴 //GET方式,数据包含在URL中
从上面的URL可以得到信息:
- ie的值为"UTF-8"
- wd的值为"滴滴"
Server根据这些请求的数据,经过一定的程序逻辑,返回响应页面。
5.状态码
再次回顾网页访问的过程:
- Client向Server发送HTTP request
- 服务器发送状态码,比如"HTTP/1.1 200 OK\r\n\r\n"
- 服务器发送网页文件(HTTP response)
状态码用于告知Client当前的Server状态。
状态码分类与常见状态码:
1xx //信息提示
100 continue 继续发送
2** //成功状态码
200 OK(请求成功)
3** //重定向
301 永久重定向(搜索引擎会将排名等信息转移到新域名)
302 临时重定向(搜索引擎不会将排名等信息转移到新域名)
4** //客户端错误
403 Forbidden(客户端没有权限访问此资源)
404 NotFound(资源不存在)
499 (请求未完成,但客户端主动断开了连接,这是nginx引入的非标状态码)
5** //服务器错误
500 服务器内部出错(如Bug)
502 错误网关(网关向后端请求错误)
503 服务不可用(服务器无法处理请求,比如过载)
504 网关超时(网关向后端请求超时)
滴滴官网的404界面:

6.http响应
http响应头部和请求的头部类似:响应行+响应头+响应体
响应体为网页文件等资源
响应行:
HTTP/1.1 200 OK //协议版本,状态码,OK对应状态码
响应头:
Server: Apache-Coyote/1.1 //服务器类型,这里是Tomcat
Content-Type: text/html;charset=ISO-8859-1 //返回数据类型
Content-Length: 673 //返回数据长度
Date: Fri, 17 Feb 2017 02:53:02 GMT //响应时间
响应头 | 说明 |
---|---|
Allow | 服务器支持哪些请求方法(如GET、POST等)。 |
Content-Encoding | 文档的编码(Encode)方法。只有在解码之后才可以得到Content-Type头指定的内容类型。利用gzip压缩文档能够显著地减少HTML文档的下载时间。Java的GZIPOutputStream可以很方便地进行gzip压缩,Servlet应该通过查看Accept-Encoding头(即request.getHeader(“Accept-Encoding”))检查浏览器是否支持gzip,为支持gzip的浏览器返回经gzip压缩的HTML页面,为其他浏览器返回普通页面。 |
Content-Length | 表示内容长度。 |
Content-Type | 表示后面的文档属于什么类型。比如text/html。 |
Date | 当前的时间。 |
Expires | 文档过期时间,过期后浏览器可不再缓存 |
Last-Modified | 文档的最后改动时间。客户可以通过If-Modified-Since请求头提供一个日期,该请求将被视为一个条件GET,只有改动时间迟于指定时间的文档才会返回,否则返回一个304(Not Modified)状态。 |
Location | 重定向后的位置。比如301永久重定向和302临时重定向 |
Refresh | 表示浏览器应该在多少时间之后刷新文档,以秒计。 |
Server | 服务器名字。 |
Set-Cookie | 设置和页面关联的Cookie。 |
7.http协议特点
(1) 媒体独立
所有类型的数据都可以通过http协议传输。传输的类型由Content-Type标明。
(2) http协议是无状态的
无状态是指协议对于事务处理没有记忆能力。缺少状态意味着如果后续处理需要前面的信息,则它必须重传,这样可能导致每次连接传送的数据量增大。
cookie和session技术让服务器有了记忆。




(3) http是无连接的
无连接的含义是限制每次连接只处理一个请求。服务器处理完客户的请求,并收到客户的应答后,即断开连接。
早期的服务器资源有限,采用无连接的方式以便腾出资源处理其他请求。
无连接产生的问题:
随着时间的推移,网页中嵌入了图片和其他元素,并且是以链接的方式嵌入。这就说明,客户端在请求完网页文件后,紧接着又会向服务器请求图片等静态资源。这样的话,无连接+多次请求就极大的浪费了带宽等资源(都浪费在TCP上了)。
如何解决?
- 使用Keepalive长连接。
8.http长连接
在HTTP/1.0中,默认使用的是短连接。
从HTTP/1.1起,默认使用长连接。
使用长连接的HTTP协议,会在响应头有加入这行代码:Connection:keep-alive
在使用长连接的情况下,当一个网页打开完成后,客户端和服务器之间用于传输HTTP数据的 TCP连接不会关闭,如果客户端再次访问这个服务器上的网页,会继续使用这一条已经建立的连接。Keep-Alive不会永久保持连接,一段时间后会断开。
比如:客户端和服务器之间会继续使用这个通道传输图片等资源。
服务器会和客户端保持一段空闲连接,在此期间他们可以无需连接即可传输数据。空闲时间到期后(默认2h),服务器会发送探测多个报文给客户端,如果都没有回应或回应断开连接的报文,则断开连接。

HTTP协议的长连接和短连接,实质上是TCP协议的长连接和短连接。
可以看到,长连接可以省去较多的TCP建立和关闭的操作,减少浪费,节约时间。对于频繁请求资源的客户来说,较适用长连接。
9.HTTP2.0
新的二进制格式(Binary Format)
HTTP1.x的解析是基于文本。基于文本协议的格式解析存在天然缺陷,文本的表现形式有多样性,要做到健壮性考虑的场景必然很多,二进制则不同,只认0和1的组合。基于这种考虑HTTP2.0的协议解析决定采用二进制格式,实现方便且健壮。
多路复用(MultiPlexing)
即连接共享,即每一个request都是是用作连接共享机制的。一个request对应一个id,这样一个连接上可以有多个request,每个连接的request可以随机的混杂在一起,接收方可以根据request的 id将request再归属到各自不同的服务端请求里面。
header压缩
如上文中所言,对前面提到过HTTP1.x的header带有大量信息,而且每次都要重复发送,HTTP2.0使用encoder来减少需要传输的header大小,通讯双方各自cache一份header fields表,既避免了重复header的传输,又减小了需要传输的大小。
服务端推送(server push)
同SPDY一样,HTTP2.0也具有server push功能。
详细解释可以看这里:https://www.cnblogs.com/heluan/p/8620312.html
10.Web Socket
这是HTML5的协议
传统http只能由客户端请求,服务端回应。如果客户端定时请求,则会造成很大资源浪费。
Web Socket可以握手,实现真正的双向传输。这样有数据更新的时候服务端可以及时发送数据,也不会造成资源浪费。
详细介绍可是看这里:https://www.liaoxuefeng.com/wiki/1022910821149312/1103303693824096
Web Socket握手过程:
首先,WebSocket连接必须由浏览器发起,因为请求协议是一个标准的HTTP请求,格式如下:
GET ws://localhost:3000/ws/chat HTTP/1.1
Host: localhost
Upgrade: websocket
Connection: Upgrade
Origin: http://localhost:3000
Sec-WebSocket-Key: client-random-string
Sec-WebSocket-Version: 13
解释:
GET请求的地址不是类似
/path/
,而是以ws://
开头的地址;
请求头Upgrade: websocket
和Connection: Upgrade
表示这个连接将要被转换为WebSocket连接;
Sec-WebSocket-Key
是用于标识这个连接,并非用于加密数据;
Sec-WebSocket-Version
指定了WebSocket的协议版本。
服务端回应:
HTTP/1.1 101 Switching Protocols
Upgrade: websocket
Connection: Upgrade
Sec-WebSocket-Accept: server-random-string
11.Linux网络优化
由于长连接会占用大量资源,典型的就是出现大量的TIME_WAIT。
可以通过下面的命令查看TIME_WAIT等状态的数量:
netstat -ant|awk '/^tcp/ {++S[$NF]} END {for(a in S) print (a,S[a])}'
推荐配置:
vim /etc/sysctl.conf
#TCP的配置
net.ipv4.tcp_syn_retries=2 #最多发起2次SYN请求(默认为5)
net.ipv4.tcp_fin_timeout=30 #FIN_WAIT_2时间
net.ipv4.tcp_max_syn_backlog = 4096 #SYN队列长度(默认为1024),增加以容纳更多等待连接数
net.ipv4.tcp_tw_reuse = 1 #开启TIME-WAIT sockets重用机制(默认为0,即关闭),可重新用于新的TCP连接
net.ipv4.tcp_tw_recycle = 1 #开启TIME-WAIT sockets快速回收(默认为0,即关闭)
net.ipv4.tcp_syncookies = 1 #当SYN等待队列溢出时,启用cookies来处理(默认为0,即关闭),可以防范少量SYN攻击
#http的keepalive长连接的配置
net.ipv4.tcp_keepalive_time=1200 #空连接可以保持1200s
net.ipv4.tcp_keepalive_probes=5 #空连接结束后发送探测报文的个数(都未回应则断开连接)
net.ipv4.tcp_keepalive_intvl=20 #每个探测包的间隔时间
#其他配置
net.core.netdev_max_backlog=3000 #每个网络接口接收数据包的速率比内核处理这些包的速率快时,允许送到队列的数据包的最大数目
sysctl -p #加载内核文件
HTTPS协议
- 超文本传输安全协议,Hypertext Transfer Protocol Secure
- HTTPS经由HTTP进行通信,但利用SSL/TLS来加密数据包。
背景:
- http协议是不安全的,所有的数据都是明文传输的。
- http的明文传输使得密码等信息可以通过抓包轻松得到。
1. SSL/TLS协议
HTTPS就是在应用层和传输层中间加了一道验证的门槛以保证数据安全:

什么是SSL/TLS?
- SSL(Secure Socket Layer) 安全套接层
- TLS(Transport Layer Security) 传输层安全
- TLS与SSL在传输层对网络连接进行加密。
1996年 NetScape 公司发布 SSL v3.0;
1999年互联网标准化组织ISOC接替NetScape公司,发布了SSL的升级版TLS 1.0版。
2006年和2008年,TLS进行了两次升级,分别为TLS 1.1版和TLS 1.2版。
SSL 及其继任者 TLS 是为网络通信提供安全及数据完整性的一种安全协议。
2. SSL/TLS协议基本过程
(1) 客户端向服务器端索要并验证公钥。
(2) 双方协商生成"对话密钥"。
(3) 双方采用"对话密钥"进行加密通信。
前两步,又称为"握手阶段"。

注意点:
- 握手阶段使用非对称加密。
- 数据传输阶段使用对称加密。
背景知识:
- 非对称加密中:公钥加密,私钥解密。(私钥只有Server有,公钥在证书中)
- 对称加密中: 双方秘钥相同,既可加密,也可解密。 对称加密非常快,而非对称加密非常慢。
问题1:为什么要使用对称加密?
- 对称加密非常快,而非对称加密非常慢。
问题2:为什么不直接使用对称秘钥?
- 不能直接发送对称秘钥,这样就会被第三方获取。
- 因为随机数a和b都是明文,所以随机数c不能被第三方得到。
- 为了能让Server得到c,使用公钥加密该随机数,这样只有Server可以解析。
问题3:公钥从哪里来,可否伪造?
- 私钥签名,公钥验签,所以不可伪造。
- 公钥在证书中。
- 客户端会查看Server的证书,若可信则继续协议过程,若不可信则拦截。计算机中保存了一些可信的CA机构,若此证书是可信的CA机构颁发的,则信任,否则不信任(会提示用户,依然可以访问)。
- 可以通过手动导入证书的方式信任此证书。
问题4:HTTP不安全为什么还要用呢?
- 可以在前端实现加密。
- 使用https需要额外的运维、计算和证书购买成本。
- HTTPS连接服务器端资源占用高
- HTTPS协议握手费时
- SSL证书费用成本
- http访问速度快
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 阿里最新开源QwQ-32B,效果媲美deepseek-r1满血版,部署成本又又又降低了!
· SQL Server 2025 AI相关能力初探
· AI编程工具终极对决:字节Trae VS Cursor,谁才是开发者新宠?
· 开源Multi-agent AI智能体框架aevatar.ai,欢迎大家贡献代码
· Manus重磅发布:全球首款通用AI代理技术深度解析与实战指南