网络协议
TCP/HTTP/DNS 概览。
网络协议
这一课你将能做到
- 说清楚一个 HTTP 请求从浏览器到 Nginx 再到 Spring Boot 的全链路过程
- 用 tcpdump、curl、ss 等命令抓包诊断网络问题
- 配置 HTTPS(TLS 证书)并理解握手过程,能把 HTTP 301 到 HTTPS
为什么要学
你的 Spring Boot 应用、MySQL、Redis、Nginx 跑在网络上,用户请求跨越公网、VPC、内网才能到达你的代码。网络不通?SSL 证书报错?连接超时?DNS 解析失败?不会抓包和看协议的 DevOps 等于蒙眼修车。
人话:网络协议是「两台电脑如何对话」的规则。HTTP 是浏览器和服务器之间的对话格式,TCP 是「保证对方一定收到」的快递单号机制,DNS 是把域名翻译成 IP 地址的电话簿。理解这些,排查「为什么连不上」才有方向。
先建立图像
一个完整的请求链路:
用户浏览器
│ https://www.codeforge.com/api/users
▼
DNS 解析 → 8.8.8.8 / 114.114.114.114
│ www.codeforge.com → 47.96.123.45
▼
公网 → 云服务器安全组(443 放行)→ 服务器 443 端口
│ Nginx 监听 443,做 TLS 握手
▼
Nginx
│ 反向代理 → proxy_pass http://127.0.0.1:8080
▼
Spring Boot(8080)
│ 查缓存(Redis:6379)或查数据库(MySQL:3306)
▼
JSON 响应
TCP 三次握手(建立连接)与四次挥手(断开连接):
三次握手(为了确认双方收发都正常):
客户端 → SYN → 服务端
服务端 → SYN+ACK → 客户端
客户端 → ACK → 服务端
四次挥手(双方各自收拾干净再挂电话):
客户端 → FIN → 服务端
服务端 → ACK → 客户端
服务端 → FIN → 客户端
客户端 → ACK → 服务端
跟着做
步骤 1:在服务器上确认网络拓扑
# 本机 IP 和网卡
ip addr
# 路由表:包往哪走
ip route
# DNS 配置
cat /etc/resolv.conf
# 域名解析过程追踪
dig www.codeforge.com +trace
步骤 2:确认端口监听和连接状态
# 四连问
ss -tlnp # TCP 监听端口(LISTEN)
ss -tan state established # 已建立连接
ss -s # 连接数统计
netstat -i # 网卡流量统计
连接状态的含义:
LISTEN 服务在等连接
ESTABLISHED 双方正在通信
TIME_WAIT 连接已断开,等最后确认(2MSL,约 60 秒)
CLOSE_WAIT 对方已关,我方还没关(通常是我方程序 bug)
SYN_SENT 正在发 SYN 等回应(可能连不上目标)
步骤 3:用 curl 模拟请求,调试 HTTP
# 基础 GET
curl -v https://api.codeforge.com/users?page=1
# -v 会打印完整握手和响应头,调试必备
# POST JSON
curl -X POST https://api.codeforge.com/users \
-H "Content-Type: application/json" \
-d '{"name":"alice"}' \
-w "\nHTTP_CODE: %{http_code}\nTIME: %{time_total}s\n"
# 只看响应头和状态码(不下载 body)
curl -I -s -o /dev/null -w "%{http_code}" https://api.codeforge.com/health
步骤 4:抓包分析——tcpdump 实战
# 抓 80 端口的包,保存到文件(Wireshark 能打开分析)
sudo tcpdump -i any port 80 -w /tmp/http.pcap
# 实时看 443 端口的握手过程(不存文件)
sudo tcpdump -i any port 443 -nn -X | head -30
# 只抓某个 IP 到本机 8080 的包
sudo tcpdump host 1.2.3.4 and port 8080