随着您的内容发生变化(它肯定会发生变化),重定向能够为您的用户和(友好的)机器人保持连续性。
其中最显而易见的部分是用户体验。如果您点击仪表板中的链接或使用书签 URL,您会信任它将带您到正确的地方。不是 404 页面或错误的页面,而是正确的页面。重定向有助于将用户引导到正确的位置。
这同样适用于自动化体验。如果您在没有重定向的情况下移动了页面,您将失去 Google 和其他搜索引擎用于对您的页面进行排名的历史搜索权重。
我们的主要方法利用了 Workers 静态资产(Workers Static Assets),在我们 GitHub 仓库的纯文本文件 ↗中定义重定向。
这种设置允许我们为重定向使用与其他文档修改相同的工作流。我们在内容修改的同一个拉取请求中实施重定向,并可以在预览分支中测试这些修改。为了便于维护,我们尝试按产品对这些重定向进行组织,然后在每个产品内按字母顺序进行组织。
我们也非常喜欢 Pages 语法提供的灵活性。
在某些情况下,我们也使用批量重定向(Bulk redirects)。我们谨慎地使用此策略,因为在多个地方设置重定向会增加认知负荷以及进行修改时潜在的混淆。
通常,只有在其他团队向我们的网站添加大量单独重定向时,才会使用批量重定向,例如当我们之前所有的 support.cloudflare.com 内容进行迁移,并且每个区域设置(locale)都需要进行个性化重定向时。
当贡献者来自我们团队之外,且重定向的总数如此之大以至于会使我们的 __redirects 文件杂乱无章,并且超出了我们对重定向的限制时,我们会使用此方法。
我们的团队在两种情况下添加重定向:在正常内容创作过程中,以及根据数据按需添加。
在正常的内容工作期间,当您对页面执行以下操作时,您会需要添加重定向:
- 更改 URL 的任何部分(文件名、文件夹)。
- 删除页面。
我们有一些自动化工具来帮助标记需要的重定向。
另一个添加重定向的时机是当您看到文档网站的某些路径上出现大量 404 响应代码时。这些 404 响应可能是由于重定向丢失或链接输入错误造成的。
我们通过我们的 Cloudflare 分析(临时)或 Logpush 任务(更彻底,每季度一次)来识别这些状态码。
我们在 GitHub 中有两个自动化工作流来辅助重定向。
无限重定向是指两个页面不断相互重定向,使用户陷入无限循环,从而导致其浏览器崩溃。
因为这是一种极其糟糕的体验,所以我们将其作为必需的 CI GitHub Action ↗ 的一部分来进行显式检查。
我们在构建网站之后触发此检查。然后它会调用 validate-redirects.ts ↗,如果遇到以下情况则会导致构建失败:
- 无限重定向
- 重复的重定向
- 重定向目标中包含锚点链接
validate-redirects.ts
import { readFile } from "fs/promises";
async function main() {
const redirects = await readFile("public/__redirects", { encoding: "utf-8" });
let numInfiniteRedirects = 0;
let numUrlsWithFragment = 0;
let numDuplicateRedirects = 0;
const redirectSourceUrls: string[] = [];
for (const line of redirects.split("\n")) {
if (line.startsWith("#") || line.trim() === "") continue;
const [from, to] = line.split(" ");
if (from === to) {
console.log(`✘ Found infinite redirect:\n ${from} -> ${to}`);
numInfiniteRedirects++;
}
if (from.includes("#")) {
console.log(`✘ Found source URL with fragment:\n ${from}`);
numUrlsWithFragment++;
}
if (redirectSourceUrls.includes(from)) {
console.log(`✘ Found repeated source URL:\n ${from}`);
numDuplicateRedirects++;
} else {
redirectSourceUrls.push(from);
}
}
if (numInfiniteRedirects || numUrlsWithFragment || numDuplicateRedirects) {
console.log("\nDetected errors:");
if (numInfiniteRedirects > 0) {
console.log(`- ${numInfiniteRedirects} infinite redirect(s)`);
}
if (numUrlsWithFragment > 0) {
console.log(`- ${numUrlsWithFragment} source URL(s) with a fragment`);
}
if (numDuplicateRedirects > 0) {
console.log(`- ${numDuplicateRedirects} repeated source URL(s)`);
}
console.log("\nPlease fix the errors above before merging :)");
process.exit(1);
} else {
console.log("\nDone!");
}
}
main();贡献者往往很难知道他们何时应该添加重定向。我们尝试通过对任何修改或删除内容文件路径的拉取请求添加评论 ↗来帮助他们。
尽您所能将重定向组织到逻辑组(产品、按字母顺序)中。此过程有助于防止重复重定向,并有助于识别您可能正在寻找的特定重定向。
在我们的 __redirects 文件 ↗中,我们使用了大量注释来分隔不同的产品区域。在每个部分内,我们也尽可能保持重定向的字母顺序。
我们过去对批量重定向(Bulk Redirects)列表也应用了类似的原则(当那是我们的主要方法时)。我们创建了将相似产品分组在一起的列表并进行了相应标记,以便更容易找到您要寻找的重定向。
在服务器级别,您可以在 URL 路径(/page/)上触发重定向,但不能在片段(/page/#fragment)上触发。
但是,您可以将页面重定向到片段(例如,将 /page1/ 重定向到 /page2/#fragment)。
如果可能,让所有重定向将您的用户直接发送到其目的地,而不是将重定向链接在一起。
否则,可能会出现以下情况:
Page 1 --Redirect-> Page 2 --Redirect-> Page 3 --Redirect-> Page 4重定向链很糟糕,因为它们:
- 减慢了用户体验。
- 增加了出现非预期结果的可能性(无限重定向、重定向丢失、不正确的重定向)。
避免这种情况的一种方法是不断更新先前重定向的目的地。例如,假设您将此页面的名称更改为 /style-guide/how-we-docs/redirect-guidance/。
在更新重定向文件的拉取请求中,您需要更新现有的重定向,并添加一个新的重定向:
- /style-guide/redirects/ /style-guide/how-we-docs/redirects/ 301
+ /style-guide/redirects/ /style-guide/how-we-docs/redirect-guidance/ 301
+ /style-guide/how-we-docs/redirects/ /style-guide/how-we-docs/redirect-guidance/ 301