Featured image of post 浏览器301重定向响应流程分析

浏览器301重定向响应流程分析

浏览器在访问 HTTP 协议非 HTTPS 的站点时,通常会发生 301 重定向,整个请求响应流程是怎样的?让我们深入分析一下

浏览器在访问 HTTP 协议非 HTTPS 的站点时,通常会发生 301 重定向,那么整个请求响应流程是怎样的?接下来我们深入分析一下。

分析

首先,我们明白,这是一个 HTTP 层面的行为,底层依赖 TCP 协议进行可靠传输。

[!tips] 前置知识 HTTP 端口为 80,HTTPS 端口为 443 301 是 HTTP 响应状态码,表示永久重定向,即请求的资源已永久移动到新的位置。

理论分析

一、初始请求阶段

1
用户输入URL → DNS解析 → TCP三次握手 → 发送HTTP请求
  1. 用户输入 URL:用户在浏览器地址栏输入一个 URL(比如 http://example.com )并按下回车。
  2. DNS 解析:浏览器解析 URL 中的域名,通过 DNS 获取对应的 IP 地址。如果涉及到重定向,可能在 DNS 层面就有 CNAME 等记录。
  3. 建立 TCP 连接:浏览器根据 IP 地址和端口 (默认 80 或 443)与服务器建立 TCP 连接。这一步是 TCP 协议的工作,包括三次握手。
  4. 发送 HTTP 请求:通过已建立的 TCP 连接,浏览器发送 HTTP 请求。例如,一个 GET 请求到根路径/。

客户端请求报文示例:

1
2
GET / HTTP/1.1
Host: example.com

二、服务器响应阶段

1
服务器处理 → 判断需重定向 → 生成301响应 → 通过TCP回传
  1. 服务器处理请求:服务器收到请求后,判断是否需要重定向到新的 URL。
  2. 服务器发送一个 HTTP 响应,状态码为 301,并在响应头中包含 Location: https://example.com(假设跳转到 HTTPS)。

服务器响应示例:

1
2
3
4
HTTP/1.1 301 Moved Permanently
Location: https://example.com/
Content-Type: text/html
Content-Length: ...

服务器是如何判断的呢?以 Nginx 为例:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
server {
    listen 80;
    server_name example.com;
    
    # 对HTTP请求重定向到HTTPS
    return 301 https://$server_name$request_uri;
}

server {
    listen 443 ssl;
    server_name example.com;
    
    ssl_certificate /path/to/cert;
    ssl_certificate_key /path/to/key;
    
    location / {
        root   html;
        index  index.html;
    }
}

三、浏览器处理阶段

1
收到301响应 → 解析新URL → (可能的新TCP连接) → 发送新请求
  1. 浏览器处理重定向:浏览器收到 301 响应后,会从响应头中读取 Location 字段,获取新的 URL,然后自动向这个新 URL 发起新的请求。注意:对于 301 状态码,浏览器通常会缓存重定向信息,下次访问原 URL 时直接跳转到新 URL,而不必再向原 URL 发送请求。
  2. 向新 URL 发起请求:浏览器使用新 URL,可能重新进行 DNS 解析(如果域名变了)、建立 TCP 新连接(如果需要),然后发送 HTTP 请求。
  3. 服务器响应新请求:服务器返回正常的 200 状态码响应和网页内容。
  4. 浏览器渲染:浏览器收到响应后,渲染页面。

如果是 HTTP 到 HTTPS 的重定向:

1
http://example.com:80 → 301 → https://example.com:443

必然会新建 TCP 连接,增加 TLS 握手。

TCP 协议层的分析

TCP 连接管理分析

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
sequenceDiagram
    Client->>Server: SYN (原始请求连接)
    Server->>Client: SYN-ACK
    Client->>Server: ACK + HTTP请求
    Server->>Client: 301响应
    alt 同一主机/端口
        Client->>Server: 重用连接发送新请求
    else 不同主机/端口
        Client->>Server: FIN (关闭连接)
        Client->>NewServer: 新建TCP连接
    end

另外,顺便一提,对性能的影响:

  • 额外 RTT:每次新建 TCP 连接增加 1 个 RTT(三次握手)
  • TLS 成本:HTTPS 重定向增加 TLS 握手(2-3 个 RTT)

调试分析

我们可以使用工具,进行直观的分析。

  1. 使用 cURL 工具追踪
1
curl -v -L http://example.com  # -L自动跟随重定向

输出显示 TCP 连接建立、请求响应全过程。

这里以访问 baidu.com 为例:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
curl -v -L http://baidu.com
* Host baidu.com:80 was resolved.
* IPv6: (none)
* IPv4: 110.242.74.102, 124.237.177.164, 111.63.65.247, 111.63.65.103
*   Trying 110.242.74.102:80...
* Established connection to baidu.com (110.242.74.102 port 80) from 192.168.68.228 port 12061 
* using HTTP/1.x
> GET / HTTP/1.1
> Host: baidu.com
> User-Agent: curl/8.16.0
> Accept: */*
> 
* Request completely sent off
< HTTP/1.1 301 Moved Permanently
< Location: http://www.baidu.com/
< Date: Sat, 20 Dec 2025 10:15:39 GMT
< Content-Length: 56
< Content-Type: text/html; charset=utf-8
* Ignoring the response-body
* setting size while ignoring
< 
* Connection #0 to host baidu.com:80 left intact
* Issue another request to this URL: 'http://www.baidu.com/'
* Host www.baidu.com:80 was resolved.
* IPv6: (none)
* IPv4: 220.181.111.232, 220.181.111.1
*   Trying 220.181.111.232:80...
* Established connection to www.baidu.com (220.181.111.232 port 80) from 192.168.68.228 port 12064 
* using HTTP/1.x
> GET / HTTP/1.1
> Host: www.baidu.com
> User-Agent: curl/8.16.0
> Accept: */*
> 
* Request completely sent off
< HTTP/1.1 200 OK
< Cache-Control: private, no-cache, no-store, proxy-revalidate, no-transform
< Content-Length: 2381
< Content-Type: text/html
< Pragma: no-cache
< Server: bfe
< Set-Cookie: BDORZ=27315; max-age=86400; domain=.baidu.com; path=/
< Date: Sat, 20 Dec 2025 10:15:39 GMT
< 
<!DOCTYPE html>
<!--STATUS OK--><html> <head><meta http-equiv=content-type content=text/html;charset=utf-8><meta http-equiv=X-UA-Compatible content=IE=Edge><meta content=always name=referrer><link rel=stylesheet type=text/css href=http://s1.bdstatic.com/r/www/cache/bdorz/baidu.min.css><title>百度一下,你就知道</title> </html>
* Connection #1 to host www.baidu.com:80 left intact
  1. Chrome DevTools 观察

Network 面板查看“状态”一列显示 HTTP 状态码,“连接 ID"字段查看 TCP 连接重用情况。

总结

通过分析 HTTP 301 重定向流程,我们进一步了解 HTTP 通信交互流程,HTTP 协议基于请求-响应模式,底层基于 TCP 协议提供可靠性的通信。理解和掌握这些机制,能帮助我们遇到问题时,能有一个清晰的解决方向。

Licensed under CC BY-NC-SA 4.0