Halo(海外VPS)用 Cloudflare Workers 加速:把“随机红省份”变成稳定秒开(第一阶段)
背景:当买了一台国外的普通线路 VPS 后,建站后发现网站测速全红,访客也反映不挂梯子经常转上几十秒甚至也进不去,即使是CN2 GIA的线路,可能偏远地区新疆等也是黄色高延迟
所以第一阶段的核心不是换机房、换线路,而是:
把 Halo 生成的 HTML 交给 Cloudflare 缓存,并且让缓存键稳定一致
一、修正 Halo 地址
很多人以为 Halo 后台“外部访问地址”能改,其实 Halo2 后台可能是只读的;真正生效的是启动参数:
--halo.external-url=...
如果你仍然是这种:
http://localhost:8090/
那就会出现一种非常致命的情况:
- 你访问的是
https://www.xxx.com - 但 Halo 输出的 canonical、链接、API 地址仍然是旧域名/localhost
- Cloudflare 看到“同内容不同 URL/跳转链”,缓存会碎、命中率会乱
1.1 SSH连接,进入 halo 目录,修改 docker-compose.yml
cd /root/data/docker_data/halo
nano docker-compose.yml
- --halo.external-url=http://localhost:8090/
改成你的最终访问域名(推荐统一用 www + https):
- --halo.external-url=https://www.jinruncheng.blog/
⚠️ 注意末尾的
/:建议保留,避免 Halo 生成链接时出现奇怪的拼接。
1.2 重启 Halo
docker compose down
docker compose up -d
建议等 20~30 秒,让 Halo 完全起来。
二、创建 Worker
2.1 进入域名面板
- Cloudflare 首页 → Websites → 点击你的域名
2.2 创建 Worker(新版位置)
在域名左侧菜单找:
- Compute (Workers) →
Create application→ 选择 Worker →Start with Hello World
三、替换 Worker 代码
把默认 Hello World 全删,粘贴下面这份(核心逻辑:绕过后台/API/登录态/非GET/静态资源,只缓存游客 HTML),再点右上角保存
(Halo 专用代码)
export default {
async fetch(request, env, ctx) {
const url = new URL(request.url);
// 不缓存后台
if (url.pathname.startsWith("/console")) return fetch(request);
// 不缓存 API
if (url.pathname.startsWith("/apis")) return fetch(request);
// 不缓存登录态
const cookie = request.headers.get("cookie") || "";
if (cookie.includes("token=") || cookie.includes("JSESSIONID")) return fetch(request);
// 只处理 GET
if (request.method !== "GET") return fetch(request);
// 静态资源交给 CF 默认处理
if (url.pathname.match(/\.(js|css|png|jpg|jpeg|gif|webp|svg|ico|woff|woff2)$/i)) {
return fetch(request);
}
// 只缓存 HTML(更稳,避免误缓存其他类型)
const accept = request.headers.get("accept") || "";
const isHtml = accept.includes("text/html");
if (!isHtml) return fetch(request);
// 缓存 Key(可选:这里保持原样,不做参数清洗)
const cacheKey = new Request(url.toString(), request);
const cache = caches.default;
// 查缓存
let response = await cache.match(cacheKey);
if (response) return response;
// 回源 + 强缓存策略
response = await fetch(request, {
cf: {
cacheEverything: true,
cacheTtl: 86400, // 1天
cacheTtlByStatus: {
"200-299": 86400,
"404": 60,
"500-599": 0,
},
},
});
// 写入 Cache API
const newResponse = new Response(response.body, response);
newResponse.headers.set("Cache-Control", "public, max-age=86400");
ctx.waitUntil(cache.put(cacheKey, newResponse.clone()));
return newResponse;
},
};
四、绑定 Worker Route
回到你的域名(Website)页面:
- Rules → Workers Routes → Add route
填写(以我的旧博客 www.jinruncheng.blog 为例):
- Route:
www.jinruncheng.blog/* - Worker:选择你刚创建的那个
- Environment:
production
✅ 推荐只先绑定
www:减少“根域名 ↔ www”混用导致的缓存碎片。
(后续你想 apex 也走同样策略,再加一条jinruncheng.blog/*也行,但第一阶段建议先统一入口。)
五、关闭冲突功能
如果你同时开着一些“自动 HTML 缓存/优化”,会和 Worker 的策略打架,导致:
- 你以为在缓存
- 实际命中却乱
- 甚至缓存到不该缓存的内容
按你之前对话里的思路,建议至少做这些:
5.1 Speed → Optimization
关闭(如果你有的话):
- APO
- HTML caching(或类似自动 HTML 缓存项)
- Early Hints(可选)
5.2 Caching(缓存) → Configuration(配置)
把:
- Browser Cache TTL(浏览器缓存) → 设为 5分钟(或者其他或者**Respect Existing Headers),**看个人偏好
第一阶段我们要的是:让 Worker 输出的 Cache-Control 生效,而不是被别的规则覆盖。
六、清缓存
你刚改过 external-url、又刚上 Worker,Cloudflare 边缘可能还残留旧缓存/旧跳转链。
在 Cloudflare 里:
- 还是在Caching(缓存)里面点击Purge Cache清楚缓存,Purge Everything清除所有内容
七、验证是否成功
7.1 测速验证(要测两轮)
测速网站如 itdog 经常第一次把你打回源(红),第二次才体现缓存命中(绿/浅绿)。
你会看到典型规律:
| 次数 | 现象 |
|---|---|
| 第 1 次 | 部分省份慢(MISS 回源) |
| 第 2 次 | 明显稳定、整体变绿(HIT 增多) |
| 第 3 次 | 更趋于稳定 |
7.2 浏览器验证(最靠谱)
用无痕窗口打开一篇文章页:
- Fn,F12 → Network → 点 HTML 文档 → 看 Response Headers
你要看到类似:
cf-cache-status: HIT(第二次访问更容易出现)- 或至少第一次是
MISS,第二次HIT
八、常见坑(第一阶段最容易踩的)
坑 1:external-url 没改对,导致“缓存命中率永远不稳”
症状:
- 你明明上了 Worker
- 但全国依旧随机红
- 或者总出现奇怪的跳转链(www ↔ apex ↔ http ↔ https)
✅ 处理:
- external-url 必须是 最终访问域名
- 建议统一
https://www.xxx/
坑 2:Route 绑错地方
症状:
- Worker 代码部署了
- 访问站点完全没变化
✅ 处理:
- 4.1必须在 域名 → Rules → Workers Routes 绑定
- Route 写
www.xxx/*(第一阶段先统一入口)
完成:第一阶段完成后的“合理预期”
完成后你应该能得到:
- 游客访问文章页:明显更快
- 国内测速:整体更绿、更稳定(但不保证“全绿”,可能新疆还是红色)
- 仍然可能存在少量节点偶发 MISS(这是第二阶段才要解决的)
文献参考:
评论区