各位社区用户大家好,经过团队近三个月的持续努力,汤不热吧(tbr8.org)技术社区已于 2026 年 7 月正式完成全站边缘计算架构迁移。本次迁移将核心内容分发、API 网关、静态资源托管及图片处理等关键服务全面迁移至 Cloudflare Workers 边缘计算平台,配合 R2 对象存储与 KV 全球分布式键值存储,实现了全球用户访问延迟降低 60% 以上的显著提升。本文将详细介绍本次架构迁移的技术方案、实施过程及性能收益。
一、迁移背景与目标
随着社区用户规模的持续增长,我们原有的中心化架构面临越来越多的挑战。原先基于单区域 Kubernetes 集群部署的 WordPress 应用,虽然通过 Nginx 反向代理和 Cloudflare CDN 做了基础的内容缓存,但动态 API 请求、图片上传处理、搜索服务等仍需回源至中心机房,导致海外用户和国内偏远地区用户体验不佳。
具体痛点包括:
- 亚太地区用户首屏加载时间超过 3 秒,动态 API 请求延迟高
- 图片上传后需等待中心服务器处理缩略图和 WebP 转换,流程耗时过长
- 站内搜索回源延迟大,高峰期搜索响应时间超过 2 秒
- 全球用户分布不均,单一机房难以覆盖多地域低延迟访问
- 突发流量场景下中心化架构弹性不足,多次出现服务降级
基于以上问题,我们制定了以下迁移目标:
- 全球 P95 延迟降至 200ms 以内
- 图片处理和转换在边缘节点完成,零回源
- 搜索服务边缘化,响应时间降至 500ms 以内
- 静态资源 100% 边缘缓存,命中率 > 98%
- 架构具备自动弹性扩容能力,无需人工干预

二、整体架构设计
新架构采用「边缘优先」的设计理念,将计算和存储尽可能推送到离用户最近的 Cloudflare 边缘节点。整体架构分为三层:
2.1 边缘计算层(Cloudflare Workers)
边缘计算层是整个架构的核心,承载了以下关键功能:
- API 网关:所有 REST API 请求通过 Workers 路由分发,实现请求鉴权、限流、缓存和负载均衡
- 页面渲染加速:对 WordPress 页面进行边缘 HTML 缓存,通过 Cache API 实现 stale-while-revalidate 策略
- 图片处理服务:基于 Workers 实现 WebP/AVIF 自动转换、尺寸裁剪、质量优化,替代原先中心化 ImageMagick 处理
- 搜索代理:将搜索请求路由至边缘 KV 索引,减少回源搜索频次
核心 Workers 路由配置示例:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21 // wrangler.toml 路由配置
name = "tbr8-edge-gateway"
main = "src/gateway.ts"
compatibility_date = "2026-06-01"
[routes]
pattern = "tbr8.org/api/*"
zone_name = "tbr8.org"
[[kv_namespaces]]
binding = "SEARCH_INDEX"
id = "xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx"
[[r2_buckets]]
binding = "MEDIA_BUCKET"
bucket_name = "tbr8-media"
[vars]
ORIGIN_URL = "https://origin.tbr8.org"
CACHE_TTL = "3600"
IMG_MAX_WIDTH = "1920"
2.2 存储层(R2 + KV)
存储层由两个核心组件构成:
Cloudflare R2 对象存储:替代原先的 NFS + Nginx 静态文件服务,存储所有上传图片、附件和静态资源。R2 提供 S3 兼容 API,且出站流量免费,大幅降低了带宽成本。我们通过 Workers 在写入 R2 的同时自动生成多尺寸缩略图元数据,并写入 KV 索引。
Cloudflare KV 全球分布式键值存储:用于存储搜索索引、URL 映射表、配置热更新数据等。KV 的最终一致性模型适合读多写少的场景,全球 300+ 边缘节点均可低延迟读取。
R2 存储桶的生命周期策略配置:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21 // R2 生命周期规则 - 自动清理临时文件
{
"rules": [
{
"id": "cleanup-temp-uploads",
"prefix": "temp/",
"status": "Enabled",
"expiration": {
"days": 7
}
},
{
"id": "cleanup-processed-images",
"prefix": "processed/_tmp/",
"status": "Enabled",
"expiration": {
"days": 3
}
}
]
}
2.3 源站层(WordPress + Kubernetes)
源站层保留 WordPress 作为内容管理系统,但职责大幅缩减:
- 仅处理管理后台操作(文章编辑、评论审核等)
- 作为内容权威数据源,Workers 缓存未命中时回源获取
- Webhook 通知机制:文章发布/更新时主动刷新边缘缓存

三、关键技术实现
3.1 边缘图片处理 Pipeline
图片处理是本次迁移中技术难度最高的部分。原先基于 ImageMagick 的中心化处理流程需要 2-5 秒,迁移到 Workers 后我们使用 WASM 版本的 Sharp 库实现边缘图片处理,处理时间降至 100ms 以内。
图片处理 Worker 的核心逻辑:
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
48
49 // src/image-worker.ts
export default {
async fetch(request: Request, env: Env): Promise<Response> {
const url = new URL(request.url);
const imagePath = url.pathname.replace('/uploads/', '');
const width = parseInt(url.searchParams.get('w') || '800');
const format = request.headers.get('Accept')?.includes('image/avif')
? 'avif'
: request.headers.get('Accept')?.includes('image/webp')
? 'webp'
: 'original';
// 缓存键:路径+宽度+格式
const cacheKey = new Request(
`${url.origin}/img/${width}/${format}${imagePath}`
);
const cache = caches.default;
// 尝试命中边缘缓存
let response = await cache.match(cacheKey);
if (response) return response;
// 从 R2 获取原图
const original = await env.MEDIA_BUCKET.get(imagePath);
if (!original) return new Response('Not Found', { status: 404 });
if (format === 'original') {
response = new Response(original.body, {
headers: { 'Content-Type': original.httpMetadata?.contentType || 'image/jpeg' }
});
} else {
// 使用 WASM Sharp 处理
const processed = await processImage(
await original.arrayBuffer(),
{ width, format, quality: 80 }
);
response = new Response(processed, {
headers: {
'Content-Type': `image/${format}`,
'Cache-Control': 'public, max-age=31536000'
}
});
}
// 写入边缘缓存
await cache.put(cacheKey, response.clone());
return response;
}
};
该方案的巧妙之处在于:首次请求触发图片处理并缓存,后续相同参数的请求直接从边缘缓存返回,实现了「处理一次,全球加速」的效果。自动格式协商(AVIF > WebP > 原始格式)确保不同浏览器获得最优格式。
3.2 智能 HTML 缓存与增量刷新
WordPress 页面的边缘缓存是性能提升的关键。我们设计了基于 stale-while-revalidate 的缓存策略:
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 // src/html-cache.ts
async function handlePageRequest(
request: Request,
env: Env
): Promise<Response> {
const cache = caches.default;
const cacheKey = new Request(request.url);
// 尝试获取缓存
const cached = await cache.match(cacheKey);
if (cached) {
const age = (Date.now() - parseInt(
cached.headers.get('x-cached-at') || '0'
)) / 1000;
// 缓存未过期:直接返回
if (age < 3600) return cached;
// 缓存过期但在容忍窗口内:返回旧内容,后台刷新
if (age < 7200) {
// 异步刷新,不阻塞当前请求
env.FETCH_TRIGGER?.fetch(request);
return cached;
}
}
// 回源获取最新内容
const originResponse = await fetch(
new Request(env.ORIGIN_URL + new URL(request.url).pathname, {
headers: request.headers
})
);
const response = new Response(originResponse.body, {
headers: {
...Object.fromEntries(originResponse.headers),
'x-cached-at': Date.now().toString(),
'Cache-Control': 'public, s-maxage=3600, stale-while-revalidate=3600'
}
});
await cache.put(cacheKey, response.clone());
return response;
}
当 WordPress 后台发布新文章或更新内容时,通过 Webhook 主动清除对应 URL 的边缘缓存:
1
2
3
4
5
6
7
8
9
10
11 // WordPress 端 Webhook 触发
add_action('save_post', function($post_id) {
$permalink = get_permalink($post_id);
wp_remote_post('https://tbr8.org/api/cache/purge', [
'body' => json_encode([
'urls' => [$permalink, home_url('/')],
'secret' => defined('CF_PURGE_SECRET') ? CF_PURGE_SECRET : ''
]),
'headers' => ['Content-Type' => 'application/json']
]);
});
3.3 边缘搜索索引
站内搜索是用户高频使用的功能。我们利用 Cloudflare KV 构建了轻量级边缘搜索索引,实现方式如下:
- 文章发布时,由 Worker 提取标题、摘要、标签等文本,构建倒排索引条目写入 KV
- 搜索请求在边缘节点直接查询 KV,无需回源
- 支持中文分词(基于结巴分词 WASM 版本)和前缀匹配
- 搜索结果与 WordPress 文章 URL 映射存储在 KV 中,确保链接准确性
虽然 KV 搜索的召回率不及 Elasticsearch,但对于社区规模的文章库(数千篇)完全够用,且 P95 搜索延迟从原来的 1.8 秒降至 180ms。

四、迁移实施过程
本次迁移采用渐进式灰度策略,分四个阶段完成:
4.1 第一阶段:静态资源迁移(2 周)
将所有 WordPress 上传目录的图片和附件迁移至 R2 存储桶。使用 rclone 进行批量迁移,总计迁移约 15GB 媒体文件。迁移期间保持双写(R2 + 原有 NFS),确保数据一致性。此阶段完成后的 URL 重写规则:
1
2
3
4
5
6 # Nginx 重写规则 - 将旧图片 URL 重定向到 R2
location /wp-content/uploads/ {
rewrite ^/wp-content/uploads/(.*)$
https://media.tbr8.org/$1
redirect;
}
4.2 第二阶段:API 网关上线(3 周)
在 Cloudflare Workers 上部署 API 网关,逐步将 WordPress REST API 流量切换到 Workers 代理模式。关键配置包括请求限流(每 IP 每秒 20 次请求)、JWT 鉴权、响应缓存等。此阶段通过 Cloudflare 的 Split Testing 功能实现 10% → 50% → 100% 的渐进式流量切换。
4.3 第三阶段:图片处理边缘化(2 周)
上线边缘图片处理 Worker,替换中心化 ImageMagick 处理。由于 Workers 有 CPU 时间限制(免费版 10ms,付费版 50ms),我们选用 Bindings 版本的 Sharp WASM 库,并针对大图做了分块处理优化。对于超过 Worker 处理能力的超大图片(>10MB),设置回源降级路径。
4.4 第四阶段:HTML 缓存与搜索边缘化(3 周)
最后阶段实现页面级边缘缓存和搜索索引边缘化。此阶段最大的挑战是缓存一致性问题——确保文章更新后用户能立即看到最新内容。我们通过 Webhook 主动刷新 + 短 TTL + stale-while-revalidate 的组合策略解决了这个问题。
五、性能收益与监控数据
迁移完成后,我们通过 Cloudflare Analytics 和自建 Grafana 仪表盘持续监控各项性能指标。以下为迁移前后的对比数据:
| 指标 | 迁移前 | 迁移后 | 提升幅度 |
|---|---|---|---|
| 全球平均首屏时间 | 2.8s | 1.1s | ↓ 60.7% |
| 亚太 P95 延迟 | 3.2s | 0.9s | ↓ 71.9% |
| 图片处理平均耗时 | 3.5s | 0.08s | ↓ 97.7% |
| 搜索 P95 延迟 | 1.8s | 0.18s | ↓ 90.0% |
| 静态资源缓存命中率 | 82% | 99.2% | ↑ 17.2pp |
| 月度带宽成本 | $320 | $45 | ↓ 85.9% |
| 突发流量承载能力 | 500 QPS | 5000+ QPS | ↑ 10x |
特别值得关注的是带宽成本的降低——得益于 R2 出站流量免费的特性,以及边缘缓存命中率的提升,回源流量下降了 95%,带宽成本从月均 $320 降至 $45,年度节省约 $3,300。
六、踩过的坑与经验总结
在三个月的迁移过程中,我们遇到了不少技术挑战,以下是几个印象深刻的踩坑记录:
6.1 Workers CPU 时间限制
Cloudflare Workers 付费版有 50ms CPU 时间限制,对于复杂的图片处理任务来说非常紧张。我们的解决方案是将图片处理拆分为多个阶段:首次请求只做格式转换和基础尺寸调整(控制在 30ms 以内),更复杂的操作(如水印叠加、高级压缩)通过 Queue 异步处理。这样用户在首次请求时就能获得基础版本图片,后续请求则返回处理完成的最终版本。
6.2 KV 最终一致性问题
Cloudflare KV 采用最终一致性模型,全球传播延迟可达 60 秒。对于搜索索引更新场景,这意味着文章发布后可能存在短暂的全网搜索结果不一致。我们的解决方案是在文章发布后的 60 秒窗口内,搜索请求强制回源到中心 Elasticsearch,确保新文章立即可搜索。KV 索引更新完成后的后续搜索则走边缘路径。
6.3 WordPress 插件兼容性
部分 WordPress 插件假设所有请求都到达源站,在边缘缓存场景下出现异常。例如统计插件重复计数、评论表单 nonce 验证失败等。我们通过 Workers 对这些特定路径设置 bypass 缓存策略,确保涉及用户状态的请求始终回源。
1
2
3
4
5
6
7
8
9
10
11
12 // 特定路径缓存豁免规则
const BYPASS_PATHS = [
'/wp-admin/',
'/wp-login.php',
'/wp-comments-post.php',
'/?rest_route=/wp/v2/comments',
'/sitemap',
];
function shouldBypassCache(pathname: string): boolean {
return BYPASS_PATHS.some(p => pathname.startsWith(p));
}

七、后续规划
边缘计算架构迁移的完成只是起点,后续我们计划在以下方向继续优化:
- Workers for AI:利用 Cloudflare Workers AI 在边缘节点运行轻量级推理模型,实现文章自动标签推荐、内容摘要生成等功能
- Pages Functions 替代部分 WordPress 主题渲染:将文章详情页的 HTML 渲染逻辑迁移至 Workers,实现完全的边缘 SSR,进一步降低首屏延迟
- D1 数据库边缘化:将评论数据和用户交互数据迁移至 Cloudflare D1 边缘 SQLite 数据库,减少核心数据库回源查询
- Hyperdrive 加速 WordPress 数据库:通过 Cloudflare Hyperdrive 连接池优化数据库连接,降低回源查询延迟
- 实时协作功能:基于 Durable Objects 实现文章协同编辑和实时评论推送
八、对社区用户的影响
本次架构升级对普通用户最直观的感受包括:
- 页面加载速度显著提升:无论身处何地,打开文章页面的速度都有明显改善,特别是海外用户的体验提升最为显著
- 图片加载更流畅:自动适配最优图片格式(AVIF/WebP),图片加载速度提升 3 倍以上
- 搜索更快更准:站内搜索响应速度提升约 10 倍,且结果更加即时
- 高峰期访问更稳定:边缘架构的弹性能力确保即使在流量高峰期,网站也能保持流畅访问
如您在使用过程中遇到任何异常,请通过社区反馈渠道或直接联系管理员,我们将第一时间处理。感谢大家一直以来对汤不热吧技术社区的支持!
汤不热吧