一次“秒开”变成“转菊花”的线上事故

上周运营在群里炸锅:

"东南亚用户打开活动页要 7 秒,国内只要 1 秒,是不是 CDN 挂了?"

第一反应是 CDN 节点问题,结果 curl 一看,TLS 握手 30 ms,首包却 2.8 s ------典型的 DNS 拖后腿。

最后发现是新买的 .app 域名没开 EDNS0-Client-Subnet,权威 DNS 把新加坡用户解析到美国去了。

要根治,得先把 DNS 协议从"输入网址"到"拿到 IP"整条链路拆个透。


解决方案:把一次域名解析拆成 5 张"车票"

🔍 关键决策点

  • 第 2 步没加 ECS,权威 DNS 只能按递归出口 IP(北京)返回最近节点,导致新加坡绕路。
  • 第 8 步 CNAME 链太长,每多一跳就加一次 RTT。

原理剖析:三层报文结构,一层比一层"黑盒"

层级 协议字段 作用 常见坑
传输层 UDP 53 / TCP 53 0-RTT vs 可靠传输 截断后 fallback TCP 多一次 RTT
应用层 QR、Opcode、RD、RA、RCODE 控制递归/权威行为 RCODE=2 SERVFAIL 时浏览器会重试 3 次
扩展层 EDNS0-Client-Subnet 把用户真实网段带给权威 长度 > 512 字节时部分老旧防火墙直接丢包

抓包片段(tcpdump -nn -s0 -vvv port 53)

yaml 复制代码
;; ->>HEADER<<- opcode: QUERY, status: NOERROR, id: 0x1234
;; flags: qr rd ra; QUERY: 1, ANSWER: 2, AUTHORITY: 0, ADDITIONAL: 1
;; OPT PSEUDOSECTION: EDNS: version: 0, flags:; udp: 4096
;; CLIENT-SUBNET: 116.12.34.0/24/24

看到 CLIENT-SUBNET 就说明 ECS 生效,权威 DNS 能按用户真实地理位置返回最优 A 记录。


应用扩展:一条"秒开"配置模板

我们在 CDN 控制台 + 权威 DNS 做了三件事,把东南亚首包降到 300 ms:

bash 复制代码
# 1. 权威 DNS 打开 ECS 支持(以 NS1 为例)
curl -X PUT https://api.nsone.net/v1/zones/xxx.com/api \
  -d '{"edns_client_subnet":true}'

# 2. 缩短 CNAME 链
api.xxx.com 60 IN A 1.2.3.4   # 直接 A 记录,不再 CNAME 到 CDN 二级域名

# 3. 运营商递归 DNS 预热
dig @8.8.8.8 api.xxx.com      # 上线前手动触发全球递归缓存

环境适配说明

  • 国内用户走 114.114.114.114,海外走 8.8.8.8,两边 TTL 设 60 s,方便灰度回滚。
  • 老旧安卓 4.x 不支持 ECS,需要单独在边缘节点做 GeoIP fallback。

对比主流"加速"方案

方案 原理 延迟收益 实施成本
ECS 把用户子网带给权威 100-300 ms 改权威 DNS 配置
HTTPDNS 绕过本地递归,直接 HTTP 拿结果 50-200 ms 客户端集成 SDK
DoH/DoT 加密防劫持,复用 HTTP/2 多路复用 0-50 ms 升级系统解析库

最终组合:

  • 国内 App 内嵌 HTTPDNS 兜底;
  • 海外浏览器走 DoH(Cloudflare 1.1.1.1);
  • 权威 DNS 全量开 ECS。

举一反三:三个变体场景思路

  1. 灰度发布

    在权威 DNS 把 10% 流量解析到新版本 IP,TTL 设 30 s,出问题 30 秒全局回滚。

  2. 多活容灾

    利用 DNS 的 weighted 记录,主站 100 权重,灾备 0 权重;故障时一键把灾备调到 100,无需改 CDN。

  3. 防劫持

    客户端预埋一份"可信 IP 列表",如果 DNS 返回的 A 记录不在列表里,立即切换到 DoH 重查,并上报异常。


小结

  • DNS 不是"黑魔法",而是一张 5 跳的车票,每一跳都能量化。
  • 打开 ECS、缩短 CNAME、预热递归缓存,是跨国业务的三板斧。
  • 把 DNS 指标(解析耗时、TTL、ECS 命中率)接进 Prometheus,比"用户说慢"提前 5 分钟发现异常。
相关推荐
影子信息10 分钟前
vue3 组件生命周期,watch和computed
前端·javascript·vue.js
程序猿阿伟23 分钟前
《Angular+Spring Boot:ERP前端采购销售库存协同架构解析》
前端
90后的晨仔41 分钟前
👂《侦听器(watch)》— 监听数据变化执行副作用逻辑
前端·vue.js
曾经的三心草41 分钟前
微服务的编程测评系统6-管理员登录前端-前端路由优化
前端·微服务·状态模式
Point1 小时前
[LeetCode] 最长连续序列
前端·javascript·算法
rookiesx1 小时前
安装本地python文件到site-packages
开发语言·前端·python
支撑前端荣耀1 小时前
九、把异常当回事,代码才靠谱
前端
LotteChar1 小时前
HTML:从 “小白” 到 “标签侠” 的修炼手册
前端·html
趣多多代言人1 小时前
20分钟学会TypeScript
前端·javascript·typescript
90后的晨仔1 小时前
⚙️ 《响应式原理》— Vue 是怎么做到自动更新的?
前端·vue.js