你有没有想过,为什么深夜打开一个远在千里之外的网站,图片还是“唰”地一下就出来了?这背后站着一群不起眼的“社区前置仓”。想象你所在的城市有一个巨大的总仓(源站),里面堆着全城所有商品,但你为了一瓶酱油每次都要开车进城,来回一小时,谁也不乐意。于是电商平台在你小区楼下开了个小仓库(CDN 边缘节点),把最常买的蔬菜、饮料提前备好。你下楼三分钟取货;万一小仓库缺货,才让骑手去总仓调一趟货(回源)。CDN(Content Delivery Network,内容分发网络)做的就是这件事:把内容从遥远的源站搬运到离用户最近的边缘节点,再通过“调度员”告诉你该去哪家取货、货架上没货时如何去总仓补货。这篇文章会用这套“前置仓”的视角,把 CDN 的原理、调度、缓存、指标、HTTPS 协同、更新策略和故障排查一次讲透。

岗位关联

掌握 CDN 原理,是后端与 AI 工程化从业者面对大规模在线服务的必修课。它直接决定交付性能、缓存一致性、运营成本与故障排查效率,是区分“能调通接口”和“能设计高可用架构”的分水岭。

目录
  1. 可视化演示
  2. 边缘缓存原理
  3. 全局调度服务
  4. 回源与分发链路
  5. 性能指标量化
  6. HTTP/HTTPS协同
  7. 缓存更新策略
  8. 故障排查与调优
  9. AI 应用场景
  10. Python 演示
  11. 常见误区
  12. 面试题

可视化演示

\u5C55\u793ACDN\u8FB9\u7F18\u5206\u53D1\u67B6\u6784\uFF1A\u7528\u6237\u901A\u8FC7DNS\u5C31\u8FD1\u8C03\u5EA6\u5230\u6700\u4F18\u8FB9\u7F18\u8282\u70B9\uFF0C\u547D\u4E2D\u7F13\u5B58\u76F4\u63A5\u8FD4\u56DE\uFF0C\u672A\u547D\u4E2D\u56DE\u6E90\u83B7\u53D6\u3002

本节配有交互动效(进入视口后自动加载,约 3KB)。

CDN\u8FB9\u7F18\u5206\u53D1\u4E0EDNS\u8C03\u5EA6 \u6E90\u7AD9\u5B58\u50A8\u539F\u59CB\u5185\u5BB9\uFF0C\u8FB9\u7F18\u8282\u70B9\u5206\u5E03\u5728\u5404\u5730\u5C31\u8FD1\u670D\u52A1\u7528\u6237 DNS\u667A\u80FD\u89E3\u6790\u7528\u6237\u5730\u7406\u4F4D\u7F6E\uFF0C\u8FD4\u56DE\u6700\u4F18\u8FB9\u7F18\u8282\u70B9IP \u7F13\u5B58\u547D\u4E2D\u76F4\u63A5\u8FD4\u56DE\uFF0C\u672A\u547D\u4E2D\u56DE\u6E90\u62C9\u53D6\u5E76\u7F13\u5B58\u5230\u8FB9\u7F18 RT = min(dist(User, Edge_i)) \u52A8\u6001\u52A0\u901F\u901A\u8FC7\u667A\u80FD\u8DEF\u7531\u4F18\u5316\u56DE\u6E90\u8DEF\u5F84\uFF0C\u51CF\u5C11\u8DE8\u533A\u5EF6\u8FDF

边缘缓存原理

把 CDN 想成开在你小区门口的前置仓。城市总仓(源站)囤着全城的货,可每次为了一瓶酱油都要开车进城,来回一个钟头,谁受得了?前置仓把最常买的货复制到你家楼下,下楼三分钟拿货——这就是 CDN 最朴素的价值:用空间的复制,换时间的缩短。你在网上看到的图片、CSS、JS、视频,都属于“高频访问但内容不常变”的货,天生适合被提前摆到离用户最近的地方。

网站上的静态资源并不需要每次都回源站取。CDN 是一张由大量边缘节点组成的网,每个边缘节点就是一台“小前置仓”,存着源站内容的副本。用户请求到达后,CDN 会把这个请求导向最近的节点:若该节点有副本,直接返回(缓存命中);若没有,节点再去源站取一次,并把副本留在本地(缓存未命中)。这样一来,原本要跨省跨运营商的长途数据搬运,被缩短成了“下楼取个快递”。

衡量这段路程节省了多少,可以用一个简单模型:CDN 加速后的总响应时间等于 DNS 解析时间、用户到边缘节点的往返时延和传输时间之和。相较之下,直接访问源站时,往返时延变成用户到源站的洲际距离,数值高出一个量级。

你家楼下的前置仓再近,也不可能把全城货物都搬来。它只要把“爆款”留在身边,就足以让绝大多数订单不再进城。这个“爆款占比”就是后面的命中率,也是下一节“调度员”要重点解决的分配问题。

T总响应=TDNS+2×RTT用户→边缘+T传输\displaystyle T_{\text{总响应}} = T_{\text{DNS}} + 2 \times RTT_{\text{用户→边缘}} + T_{\text{传输}}
  1. D N S 解析耗时浏览器需要先把域名解析成 IP 地址,相当于查地图找到最近前置仓的位置,一般耗时 10 到 100 毫秒。
    TDNST_{\text{DNS}}
  2. 往返时延 R T T用户到边缘节点一个来回的时间,走本地运营商网络通常只有 5 到 30 毫秒。
    RTT用户→边缘RTT_{\text{用户→边缘}}
  3. 乘以 2 的含义TCP 建连加 HTTP 请求响应至少需要一次完整来回,这里简化为一去一回两次传输开销。
    2×RTT用户→边缘2 \times RTT_{\text{用户→边缘}}
  4. 传输时间内容从边缘节点传到用户浏览器的下载耗时,取决于带宽和文件大小。
    T传输T_{\text{传输}}

全局调度服务

楼下的前置仓可能不止一家,买菜 App 怎么决定把你分给哪家?它看两件事:哪家离你最近,哪家现在最不挤。CDN 里的“调度员”叫 GSLB(全球负载均衡),它在你输入网址后、还没连上服务器之前,就替你拍板了。

用户在浏览器输入一个 CDN 加速的域名,本地 DNS 服务器一层层向上递归查询,最终会找到 CDN 厂商的权威 DNS。权威 DNS 背后站着 GSLB:它会根据用户来源 IP 判断地理位置和运营商,再综合各边缘节点的健康状态与负载,返回一个“最优节点”的 IP。这个机制也叫智能 DNS 解析或流量调度。如果某个节点突然宕机,GSLB 会把它从候选名单里摘掉,流量自动改道附近其他节点,这就是故障转移。

调度的本质是一个带约束的最优化问题:在所有候选边缘节点里,挑出一个综合代价最小的。代价由两部分构成——节点离用户的网络距离,以及节点当前的繁忙程度。权重系数决定了调度策略更偏向“离得近”还是“更空闲”。

调度员把每个用户带向最合适的仓,边缘节点的货就能多卖出去、少去总仓调货。可是,总仓的货到底怎么补到前置仓?这就要说到回源与分发链路。

Nodebest=arg⁡min⁡i∈N(α⋅RTTi+β⋅Loadi)\displaystyle \text{Node}_{\text{best}} = \arg\min_{i \in \mathcal{N}} \left( \alpha \cdot RTT_i + \beta \cdot \text{Load}_i \right)
  1. 候选节点集合所有可供当前用户选择、且状态健康的边缘节点,也就是“附近几家都营业的前置仓”。
    N\mathcal{N}
  2. 网络时延项第 i 个边缘节点到用户的往返时延,代表“这家仓离我有多远”。
    RTTiRTT_i
  3. 负载项第 i 个节点当前的繁忙程度,代表“这家仓现在排队的人多不多”。
    Loadi\text{Load}_i
  4. 权重系数alpha 和 beta 分别给距离和负载加权,调整整个网络更看重体验还是更看重成本。
    α⋅RTTi+β⋅Loadi\alpha \cdot RTT_i + \beta \cdot \text{Load}_i
  5. 取最小值在所有候选中挑出综合分最小的一项,即“不绕路又不排队”的最优仓。
    arg⁡min⁡i∈N\arg\min_{i \in \mathcal{N}}

回源与分发链路

前置仓的货不是凭空冒出来的,总仓每天要往各个社区补货。在 CDN 里,边缘节点向源站要数据的过程叫“回源”。回源不是每次都要发生:边缘节点上有货,就直接给用户;没有货,才去源站拉取,而且拉回来后会把货物留在货架上,供后续用户取用。这就是“缓存未命中 + 回源 + 回填”的标准流程。

大型 CDN 的货架不止一层,常见的是多级缓存:最靠近用户的 L1 边缘节点,上面是区域级的 L2 节点,再往上才是源站。L1 没命中,先去 L2 取;L2 还没有,才真正回源站。每一层都在玩同一个游戏:努力让下一层少被惊扰。热门的“爆款内容”会逐级上浮到离用户最远的一层,而冷门内容则留在源站等待按需调取。

整个系统的平均响应时间,是命中场景与回源场景的加权平均。命中率越高,平均耗时越贴近边缘节点的快速度;命中率越低,平均耗时就越接近源站的慢路径,性能差距立竿见影。

多级缓存就像“总仓—区域转运站—社区前置仓”的三级互补体系。离用户最近的货架成本最高,所以只放最畅销的货;放不下、又没把握畅销的,就放在区域转运站。这样层层兜底,既省钱又高效。可怎么知道系统运行得好不好?需要一把“体检尺”——性能指标。

Tavg=h×Tedge+(1−h)×Torigin\displaystyle T_{\text{avg}} = h \times T_{\text{edge}} + (1 - h) \times T_{\text{origin}}
  1. 命中率 h请求被边缘缓存直接应答的比例,取值 0 到 1 之间,越高越好。
    hh
  2. 边缘响应时间缓存命中时,边缘节点返回内容给用户的耗时,通常只有几十毫秒。
    TedgeT_{\text{edge}}
  3. 回源响应时间回源时完整拉取内容的总耗时,包含源站处理与跨网传输,往往数百毫秒。
    ToriginT_{\text{origin}}
  4. 加权求和按命中与未命中的比例加权平均,得出一次请求的期望耗时。
    h×Tedge+(1−h)×Toriginh \times T_{\text{edge}} + (1 - h) \times T_{\text{origin}}
  5. 代入算例h = 0.9,边缘 10ms,回源 210ms,则平均耗时 = 9 + 21 = 30ms,比直连源站快约 7 倍。
    Tavg=0.9×10+0.1×210=30msT_{\text{avg}} = 0.9 \times 10 + 0.1 \times 210 = 30\text{ms}

性能指标量化

前置仓店长每天盯三个数字:现场卖出多少(命中)、需要调货多少(回源)、顾客从下单到收货多久(延迟)。CDN 运维也盯着一组等价指标:命中率、回源率、首字节时间(TTFB),以及更严格的 P95/P99 延迟。

命中率指缓存命中请求数占总请求数的比例,回源率则是未命中回源请求的占比。在“命中或回源”的二分视角下,两者加起来是 100%。首字节时间(TTFB)是用户发出请求到收到第一个字节的时间,能最直接地反映 CDN 是否真的起到了加速作用。运维中还会看 P95 延迟:把一天内所有请求的耗时排序,排在 95% 位置的那个值——它比平均值更能暴露长尾慢请求。

命中率是前置仓的存货周转率,回源率是每天往总仓跑的趟数。把这两个数压住,用户看到的速度自然就快。但别忘了,静态资源走得快还不够,还要走得更稳——尤其在 HTTPS 加密时代,握手环节常常比传输本身更耗时间。

HitRate=HitsHits+Misses×100%,BOR=MissesHits+Misses×100%\displaystyle \text{HitRate} = \frac{\text{Hits}}{\text{Hits} + \text{Misses}} \times 100\%, \quad \text{BOR} = \frac{\text{Misses}}{\text{Hits} + \text{Misses}} \times 100\%
  1. 命中次数由边缘缓存直接响应的请求数,代表“前置仓当场出货的订单量”。
    Hits\text{Hits}
  2. 未命中次数边缘没有缓存、需要回源处理的请求数,代表“要跑总仓调货的订单量”。
    Misses\text{Misses}
  3. 总请求数命中与未命中之和,也就是一天内全部用户请求。
    Hits+Misses\text{Hits} + \text{Misses}
  4. 化成百分比乘以 100% 让比例更直观,便于设监控阈值。
    ×100%\times 100\%
  5. 两者互补关系在简单二分模型里,命中率与回源率相加恒等于 100%。
    HitRate+BOR=100%\text{HitRate} + \text{BOR} = 100\%

HTTP/HTTPS协同

前置仓送货讲究安全签收:包裹要贴防拆封条,收件人要对验身份。HTTPS 就是包裹上的“验签流程”,每次建立连接都要多几轮“对暗号”。CDN 在协议层做的优化,总结起来就是两句话:减少验签的轮数,让一车多拉几家的货。

HTTP 层面,源站通过响应头告诉 CDN 与浏览器“这包菜能不能缓存、能放多久、怎么验证”。Cache-Control 的 max-age 决定保鲜时长,ETag 和 Last-Modified 提供“版本比对”依据。HTTPS 层面,TLS 1.2 完整握手需要两个 RTT,TLS 1.3 压缩到一个 RTT,再配合会话恢复甚至能做到 0-RTT 握手。CDN 还普遍支持 HTTP/2 多路复用和 HTTP/3 + QUIC:前者让一个连接同时传输多个资源,后者把传输搬到 UDP 上、减少队头阻塞。

无论协议怎么演进,用户能感知的速度都围绕一个公式展开:首字节时间等于“握手轮数 × 每轮时延”再加上实际传输耗时。CDN 把用户安排到最近的边缘节点,RTT 值本来就小,若再配合 TLS 1.3 减少握手轮数,首字节时间会被压缩得相当可观。

CDN 就是站在用户身边的前置仓,把复杂的验签流程压到最短,把每辆配送车的装载率提到最高,让每一秒都花在实际传输上。不过,货架上的东西放久了会过期,源站也可能换了新包装——这就轮到缓存更新策略登场。

T首字节=N握手轮数×RTT+T传输\displaystyle T_{\text{首字节}} = N_{\text{握手轮数}} \times RTT + T_{\text{传输}}
  1. 握手轮数从 TCP 建连到 TLS 握手、再到发出 HTTP 请求所需的 RTT 次数,TLS 1.2 约 3 轮,TLS 1.3 约 2 轮。
    N握手轮数N_{\text{握手轮数}}
  2. 单轮往返时延客户端到服务器的一个网络来回时间,越近越小。
    RTTRTT
  3. 握手总耗时轮数与单轮时延相乘,得到“对暗号”环节的总开销。
    N握手轮数×RTTN_{\text{握手轮数}} \times RTT
  4. 传输耗时握手完成后实际下载内容的时间,由带宽和文件大小决定。
    T传输T_{\text{传输}}
  5. CDN 的加速来源边缘节点让 RTT 变小,TLS 1.3 让轮数变少,双管齐下首字节自然更快。
    T首字节↓=N少×RTT小+T传输T_{\text{首字节}} \downarrow = N_{\text{少}} \times RTT_{\text{小}} + T_{\text{传输}}

缓存更新策略

前置仓的生鲜都有保鲜期,过期必须下架;如果源站已经换了新包装,楼下还在卖旧包装,顾客就要投诉了。TTL 就是货架上的“保鲜期标签”,主动刷新是“强制撤旧换新”,缓存预热则是“大促前提前大批量备货”。

当内容被缓存时,CDN 会给它盖一个时间戳并设置 TTL(生存时间)。到期后,下一次请求会强制回源拉取新内容。若源站已经更新但 TTL 还没到,用户就会拿到旧版本——这就是俗称的“脏数据”。解决方案有三类:缩短 TTL 让新鲜度优先;对发布后的 URL 做主动刷新,立即清掉边缘节点的旧副本;更优雅的是引入 URL 指纹(如 app.a1b2c3.js),新版本对应新 URL,旧缓存自动失效,永不冲突。预热则把即将发布的资源提前推到边缘,避免上线瞬间的“回源洪峰”。

过期判定本质上是一个时间比较:从缓存写入到现在经过的时间,是否已经超过允许的 TTL。如果超了,就判为过期,重新回源;如果没超,就继续让缓存“服役”。

把缓存当成“有保质期的货物”后,新鲜度和性能就成了一场权衡:想要更快就调长 TTL,想要更精确就用 URL 指纹让新旧版本各走各路。可一旦线上真的出问题,用户连不上、内容不对,又该如何下手?最后一块拼图是故障排查与调优。

is_expired={true,(Tnow−Tcached)≥TTLfalse,otherwise\displaystyle \text{is\_expired} =\begin{cases}\text{true}, & (T_{\text{now}} - T_{\text{cached}}) \ge \text{TTL} \\\text{false}, & \text{otherwise}\end{cases}
  1. 当前时间戳服务器此刻的系统时间,用来与写入时间做差。
    TnowT_{\text{now}}
  2. 缓存写入时间内容被存入边缘节点的时刻。
    TcachedT_{\text{cached}}
  3. 缓存已存活时长两个时间相减,得到内容在货架上存放了多久。
    Tnow−TcachedT_{\text{now}} - T_{\text{cached}}
  4. 生存期限允许内容在缓存中存活的最长时间,超过则判过期。
    TTL\text{TTL}
  5. 条件判断货架时间已超保质期就换新,否则继续使用旧缓存。
    (Tnow−Tcached)≥TTL(T_{\text{now}} - T_{\text{cached}}) \ge \text{TTL}

故障排查与调优

某天前置仓突然爆单,顾客投诉收货慢。店长的排查思路是:是定位把顾客导错仓了吗(调度问题)、货架显示有货但实际空了(缓存脏数据)、还是总仓断供(源站故障)?CDN 排障也遵循同样的逻辑:沿着“用户 → DNS → 调度 → 边缘节点 → 回源”这条链路逐段测量,找到瓶颈点。

常见故障五花八门:命中率骤降,往往是源站缓存头丢失或 URL 带了随机参数,导致每个请求都像“新顾客”——前置仓根本没机会备货;回源超时或 504,通常是源站过载或边缘到源站的网络抖动;脏数据则是 TTL 太长、刷新不及时。排查第一步,可以用浏览器开发者工具或 curl 查看响应头:X-Cache 字段显示 HIT/MISS,Age 显示缓存存活时间,Via 显示经过了哪些节点,据此一眼定位问题发生在哪一段。调优手段包括收敛 URL 参数、延长静态资源 TTL、为大促热点做预热,并配合监控告警盯住命中率、回源率、P95 延迟和 5xx 比例。

端到端用户感知的耗时可以被拆成四个可测环节:DNS 解析、连接建立、首字节返回、内容下载。每一段都有对应的测量手段,哪一段异常就修哪一段——这就是 CDN 排障的基本方法论。

故障排查就像给前置仓做体检:每个环节都有对应的“体检指标”,没有玄学。只要把 RTT、状态码和响应头拆开看,任何异常都会现出原形。CDN 的全部智慧,说到底就是“让货离人更近、让仓更聪明、让排查有据可依”。

T用户感知=TDNS+T连接+TTTFB+T下载\displaystyle T_{\text{用户感知}} = T_{\text{DNS}} + T_{\text{连接}} + T_{\text{TTFB}} + T_{\text{下载}}
  1. DNS 耗时从输入网址到拿到边缘节点 IP 的时间,用 dig 或 nslookup 可测。
    TDNST_{\text{DNS}}
  2. 连接耗时TCP 三次握手加 TLS 握手的时间,用 curl 的 time_connect 可观测。
    T连接T_{\text{连接}}
  3. 首字节时间发出请求到收到第一个字节的时间,curl 的 time_starttransfer 就是它。
    TTTFBT_{\text{TTFB}}
  4. 下载耗时从第一个字节到最后全部到达的时间,受带宽与文件大小影响。
    T下载T_{\text{下载}}
  5. 分段定位法总耗时 = 四段之和,哪段明显超标,瓶颈就在那一段。
    T用户感知=TDNS+T连接+TTTFB+T下载T_{\text{用户感知}} = T_{\text{DNS}} + T_{\text{连接}} + T_{\text{TTFB}} + T_{\text{下载}}

AI 应用场景

AI 大模型 Web 应用的静态资源分发

阶段:模型部署与线上服务

解决的问题:大模型聊天应用的前端 JS、CSS、字体和静态图表动辄数 MB,若全部由中心机房直接响应,跨地域用户的加载延迟会非常高,直接影响首屏体验。

具体案例:某 AI 公司每次发布新版本时,把前端构建产物上传到对象存储,并配置 CDN 加速。文件名带上内容哈希,CDN 缓存时间设为一年;发布新版本时只上传新哈希文件,浏览器和 CDN 自然加载新版本,旧版本在后台慢慢淘汰。

AI 电商大促热点预取

阶段:业务流量预测与资源准备

解决的问题:大促前用户集中访问商品页、活动页,若热点 URL 没有提前缓存到边缘,瞬间的流量会直接打穿源站,造成雪崩。

具体案例:算法团队用时序模型预测未来一小时的 TopK 热门商品页 URL,在活动开始前通过 CDN 预热接口把页面资源提前灌入各边缘节点。活动当天命中率稳定在 95% 以上,源站压力下降 80%。

边缘 AI 推理与缓存联动

阶段:在线推理

解决的问题:OCR、人脸检测等场景对延迟极敏感,中心机房距离用户远,RTT 动辄几十毫秒,难以满足实时性要求。

具体案例:在 CDN 边缘节点上部署轻量级 AI 模型,先执行基础识别并把结果缓存到边缘;置信度低的“疑难样本”再回源站调用大模型二次判断。这样既保证了低延迟,又控制了大模型的调用成本。

Python 演示

python52 行
import randomimport time  class EdgeCache:    """模拟 CDN 边缘节点缓存: 带 TTL 与容量限制的简单字典"""     def __init__(self, capacity=8, ttl=5.0):        self.cache = {}        self.capacity = capacity        self.ttl = ttl        self.hits = 0        self.misses = 0     def get(self, key):        now = time.time()        if key in self.cache:            value, stored_at = self.cache[key]            if now - stored_at < self.ttl:                self.hits += 1                return value, "hit"            del self.cache[key]        self.misses += 1        value = self.fetch_origin(key)        if len(self.cache) >= self.capacity:            self.cache.pop(next(iter(self.cache)))        self.cache[key] = (value, now)        return value, "miss"     @staticmethod    def fetch_origin(key):        time.sleep(0.02)  # 模拟源站处理延迟        return f"data({key})"  def main():    random.seed(42)    edge = EdgeCache(capacity=8, ttl=5.0)    latencies = []    for i in range(100):        key = f"img-{i % 15}.jpg"        start = time.time()        _, status = edge.get(key)        latencies.append(time.time() - start)    total = edge.hits + edge.misses    print(f"边缘命中率: {edge.hits / total * 100:.1f}%")    print(f"回源率: {edge.misses / total * 100:.1f}%")    print(f"平均请求耗时: {sum(latencies) / len(latencies) * 1000:.1f}ms")  if __name__ == "__main__":    main()
目的:实现一个简易 CDN 边缘缓存,动态演示命中/未命中判断、TTL 过期与容量淘汰逻辑,最后输出命中率、回源率与平均延迟,帮助理解 CDN 性能公式。
  1. if now - stored_at < self.ttl:判断缓存是否还在保鲜期内,未过期则直接命中返回。
  2. self.hits += 1命中计数器加一,用于最后计算命中率。
  3. value = self.fetch_origin(key)缓存未命中或已过期时回源取数,等价于前置仓向总仓调货。
  4. self.cache.pop(next(iter(self.cache)))缓存超出容量时淘汰最旧条目,模拟边缘节点容量受限。
  5. random.seed(42)固定随机种子,让结果可复现,方便对比不同 TTL 配置。
  6. key = f"img-{i % 15}.jpg"用 15 个资源的循环访问制造热点,让部分 key 可以被复用。

常见误区

误区动态接口每次返回内容都不一样,CDN 拿它没办法,所以只要涉及动态请求就一定要直连源站。

正解CDN 也能做动态加速。它可以把静态壳(JS/CSS)交给边缘缓存,把动态 API 走优化后的回源链路;还能在边缘节点上跑计算逻辑,直接返回加工结果。常规架构中“静态走 CDN、动态走专线回源”的组合也能显著改善整体体验。

为何常见:人们对 CDN 的印象大多来自图片视频加速,容易忽略它在协议与链路层面的优化能力。

误区加个 CNAME 指向 CDN,剩下全交给厂商,不用关心源站响应头。

正解CDN 是否缓存、缓存多久,主要听源站返回的 Cache-Control 和 Expires。如果源站返回 no-cache 或不带缓存头,CDN 不敢擅自缓存。想命中率高,先要在源站把响应头配正确,再进行 URL 收敛和参数归一化。

为何常见:把 CDN 当成一个自动缓存的黑盒,忽略了它本质上是“遵纪守法”的中间人。

误区在 CDN 控制台点了“刷新”,用户立刻就能看到源站的新内容,两个动作是同一件事。

正解刷新只是把边缘节点上的旧副本作废,让下一次请求强制回源。源站的代码发布、数据库更新是另一条链路。正确顺序是“先发布源站,再刷新 CDN”,否则刷新后回源取到的还是旧内容。

为何常见:把 CDN 缓存管理和源站发布这两个独立操作混为一谈。

误区看到命中率 99% 就认为这是完美状态,越高越好。

正解命中率高可能意味着 TTL 设得过长,源站更新后用户还在看旧数据——高命中率背后的“脏数据”更可怕。正确做法是结合业务对新鲜度的要求,给不同资源设置差异化 TTL,并用 URL 指纹让静态资源“长缓存、秒更新”。

为何常见:只盯单一指标容易自我满足,忽略了数据新鲜度与性能之间的平衡。

面试题

Q1. CDN 的核心作用是什么?

单选题 · easy

  • A.加密所有用户数据
  • B.把内容复制到离用户更近的边缘节点,缩短访问延迟← 正确答案
  • C.代替源站服务器执行业务逻辑
  • D.将用户数据永久存储在云端

答案:B。CDN 的本质是内容分发与就近缓存,就像小区楼下的前置仓把货备在用户身边。A 是 HTTPS 的职责,C 属于边缘计算但不是 CDN 的核心定位,D 与 CDN 无关。

Q2. CDN 通常通过什么机制把用户引导到最近的边缘节点?

单选题 · easy

  • A.TCP 重定向
  • B.HTTP 302 跳转
  • C.DNS 解析与 GSLB 调度← 正确答案
  • D.ARP 广播

答案:C。用户解析域名时,CDN 的权威 DNS 让 GSLB 根据地理位置和负载返回最优节点 IP,整个过程在“查地图”阶段就完成了。TCP/302/ARP 都不是 CDN 做全局调度的手段。

Q3. 下列哪个响应头用于控制浏览器和 CDN 的缓存行为?

单选题 · easy

  • A.Cache-Control← 正确答案
  • B.Content-Length
  • C.Connection
  • D.Referer

答案:A。Cache-Control 的 max-age/no-cache 等指令直接决定内容能否被缓存以及缓存多久,相当于前置仓货架上的“保鲜期标签”。其余选项分别描述长度、连接和来源,与缓存控制无关。

Q4. 某 CDN 命中率为 90%,边缘命中耗时 10ms,回源耗时 210ms,平均响应时间约为多少?

单选题 · mid

  • A.30ms← 正确答案
  • B.50ms
  • C.60ms
  • D.210ms

答案:A。代入加权平均公式:0.9×10 + 0.1×210 = 9 + 21 = 30ms。90% 的请求走快路径,只有 10% 走慢路径,平均耗时被显著拉低,这正是 CDN 的价值。

Q5. 源站已经更新了文件,但 CDN 仍向用户返回旧版本,最可能的原因是什么?

单选题 · mid

  • A.缓存 TTL 尚未过期,边缘节点仍持有旧副本← 正确答案
  • B.DNS 记录被删除
  • C.源站没有开启 HTTPS
  • D.边缘节点的 IP 发生了变化

答案:A。TTL 未过期时,CDN 不会主动回源,旧副本继续“服役”,类似于前置仓的牛奶没到保质期就不会下架。DNS 删除会导致无法访问,源站 HTTPS 和节点 IP 变化都不会造成旧内容。

Q6. 关于 TLS 1.3 相比 TLS 1.2 的优势,下列说法正确的是?

单选题 · mid

  • A.TLS 1.3 不需要证书
  • B.TLS 1.3 握手轮数更少,连接时延更低← 正确答案
  • C.TLS 1.3 只能配合 HTTP/3 使用
  • D.TLS 1.3 完全不需要 RTT

答案:B。TLS 1.3 把完整握手压缩到 1 个 RTT,并支持 0-RTT 会话恢复,相当于把“对暗号”从两轮变一轮。它仍然需要证书,也不局限于 HTTP/3,更不可能完全免掉网络往返。

Q7. 用户到 CDN 边缘节点的 RTT 为 20ms,从 TCP 建连到 TLS 1.2 握手完成再发出 HTTP 请求共约 4 个 RTT。从开始连接到收到首个字节的理论最短时间约为多少?

单选题 · hard

  • A.20ms
  • B.40ms
  • C.80ms← 正确答案
  • D.160ms

答案:C。4 个 RTT 乘以 20ms 等于 80ms。握手轮数 × 单轮时延就是连接阶段的理论耗时。CDN 之所以快,一方面让节点离用户近(RTT 小),另一方面用 TLS 1.3 减少轮数。

Q8. 以下哪些措施可以提高 CDN 命中率?

多选题 · mid

  • A.在源站正确配置 Cache-Control 缓存头← 正确答案
  • B.给静态资源 URL 追加随机参数
  • C.延长静态资源的 TTL← 正确答案
  • D.每次请求都拼接唯一签名

答案:AC。正确的缓存头告诉 CDN “这包菜可以放货架”,延长 TTL 让货架时间更久。B 和 D 会让每个 URL 都被当成新商品,CDN 无法复用缓存,命中率反而下降。

Q9. 关于 CDN 缓存更新机制,下列正确的说法有?

多选题 · mid

  • A.主动刷新是立即让边缘节点作废旧内容← 正确答案
  • B.TTL 过期后,下一次访问才会触发回源← 正确答案
  • C.URL 指纹可以让新版本自动对应新地址← 正确答案
  • D.刷新浏览器本地缓存就能更新 CDN 缓存

答案:ABC。刷新、TTL 过期和 URL 指纹是缓存更新的三大手段。D 描述的是浏览器本地缓存,与 CDN 边缘节点无关,刷新浏览器并不能指挥远端的“前置仓”下架商品。

Q10. 用户访问 CDN 加速网站时出现 504,可能的原因包括哪些?

多选题 · hard

  • A.边缘节点缓存过期,回源请求超时← 正确答案
  • B.源站服务器过载或宕机← 正确答案
  • C.边缘节点到源站之间的网络出现异常← 正确答案
  • D.浏览器本地 DNS 缓存被清空

答案:ABC。504 本质是“前置仓向总仓调货迟迟未回”。缓存过期触发回源、源站自身故障、链路抖动都会让回源超时。浏览器 DNS 缓存清空只会增加解析耗时,不会导致 504。