From 316b3945cce19d1fc13d188fa16dcc63ace3460d Mon Sep 17 00:00:00 2001
From: fylorn <249551762+fylorn@users.noreply.github.com>
Date: Thu, 1 Oct 2026 13:23:39 +0800
Subject: [PATCH] Move the pricing page to /pricing
The page is called Pricing now, so its address follows: /pricing and
/zh-CN/pricing. The old addresses are built as redirect pages (Astro's
redirects; GitHub Pages cannot answer with a redirect), marked noindex
with a canonical link to the new page, and the sitemap lists only the
new ones. Every link on the site points at the new address; no other
repository links to the old one.
The page, its component and its copy are renamed to match (PricingPage,
src/i18n/pages/pricing.ts, nav.pricing), and an unused duplicate
nav.pricing key from the old one-page site is removed.
Co-Authored-By: Claude Opus 5.5
---
astro.config.mjs | 10 ++++++++--
src/components/SiteFooter.astro | 2 +-
src/components/SiteHeader.astro | 2 +-
src/components/home/CompareEditions.astro | 2 +-
.../pages/{LicensePage.astro => PricingPage.astro} | 11 ++++++-----
src/components/pages/ThinkWatchPage.astro | 2 +-
src/content/docs/en/overview.md | 2 +-
src/content/docs/zh-CN/overview.md | 2 +-
src/i18n/index.ts | 6 ++----
src/i18n/pages/{license.ts => pricing.ts} | 6 +++---
src/lib/lastmod.ts | 4 ++--
src/pages/license.astro | 5 -----
src/pages/pricing.astro | 5 +++++
src/pages/zh-CN/license.astro | 5 -----
src/pages/zh-CN/pricing.astro | 5 +++++
15 files changed, 37 insertions(+), 32 deletions(-)
rename src/components/pages/{LicensePage.astro => PricingPage.astro} (96%)
rename src/i18n/pages/{license.ts => pricing.ts} (99%)
delete mode 100644 src/pages/license.astro
create mode 100644 src/pages/pricing.astro
delete mode 100644 src/pages/zh-CN/license.astro
create mode 100644 src/pages/zh-CN/pricing.astro
diff --git a/astro.config.mjs b/astro.config.mjs
index 3dc6242..9ad440a 100644
--- a/astro.config.mjs
+++ b/astro.config.mjs
@@ -32,6 +32,12 @@ function rehypeScrollingTables() {
// https://astro.build/config
export default defineConfig({
site: 'https://thinkwat.ch',
+ // Pages that moved. GitHub Pages cannot answer with a redirect, so each old
+ // address is built as a page that sends the browser on (and is not indexed).
+ redirects: {
+ '/license': '/pricing',
+ '/zh-CN/license': '/zh-CN/pricing',
+ },
i18n: {
defaultLocale: 'en',
locales: ['en', 'zh-CN'],
@@ -58,7 +64,7 @@ export default defineConfig({
// Product landing pages: ThinkWatch, ThinkWatch Lite, ThinkWatch Core.
const productPaths = ['/thinkwatch', '/lite', '/core'];
const isProduct = productPaths.some((p) => pathname === p || pathname === `/zh-CN${p}`);
- const isLicense = pathname === '/license' || pathname === '/zh-CN/license';
+ const isPricing = pathname === '/pricing' || pathname === '/zh-CN/pricing';
if (isHome) {
item.priority = 1.0;
@@ -76,7 +82,7 @@ export default defineConfig({
} else if (isChangelog) {
item.priority = 0.7;
item.changefreq = ChangeFreqEnum.WEEKLY;
- } else if (isLicense) {
+ } else if (isPricing) {
item.priority = 0.6;
item.changefreq = ChangeFreqEnum.MONTHLY;
} else {
diff --git a/src/components/SiteFooter.astro b/src/components/SiteFooter.astro
index 6cc29d2..ca4386d 100644
--- a/src/components/SiteFooter.astro
+++ b/src/components/SiteFooter.astro
@@ -35,7 +35,7 @@ const year = new Date().getFullYear();
diff --git a/src/components/SiteHeader.astro b/src/components/SiteHeader.astro
index 07ca3b3..2225969 100644
--- a/src/components/SiteHeader.astro
+++ b/src/components/SiteHeader.astro
@@ -26,7 +26,7 @@ const links = [
{ href: localePath(lang, "/core"), label: s.nav.core, match: "/core" },
{ href: localePath(lang, "/docs"), label: s.nav.docs, match: "/docs" },
{ href: localePath(lang, "/changelog"), label: s.nav.changelog, match: "/changelog" },
- { href: localePath(lang, "/license"), label: s.nav.license, match: "/license" },
+ { href: localePath(lang, "/pricing"), label: s.nav.pricing, match: "/pricing" },
].map((l) => ({ ...l, active: currentPath === l.match || currentPath.startsWith(l.match + "/") }));
const cleanPath = Astro.url.pathname.replace(/^\/zh-CN/, "") || "/";
diff --git a/src/components/home/CompareEditions.astro b/src/components/home/CompareEditions.astro
index 3d7b147..443ea87 100644
--- a/src/components/home/CompareEditions.astro
+++ b/src/components/home/CompareEditions.astro
@@ -47,6 +47,6 @@ const rows = ["runsAs", "builtFor", "status", "license"] as const;
))}
- {c.link}
+ {c.link}
diff --git a/src/components/pages/LicensePage.astro b/src/components/pages/PricingPage.astro
similarity index 96%
rename from src/components/pages/LicensePage.astro
rename to src/components/pages/PricingPage.astro
index a932018..2b242fd 100644
--- a/src/components/pages/LicensePage.astro
+++ b/src/components/pages/PricingPage.astro
@@ -1,19 +1,20 @@
---
-// Shared /license page. Copy lives in src/i18n/pages/license.ts.
+// Shared /pricing page: the licenses of the three products and the commercial
+// terms of ThinkWatch Enterprise. Copy lives in src/i18n/pages/pricing.ts.
import Base from "~/layouts/Base.astro";
import SiteHeader from "~/components/SiteHeader.astro";
import SiteFooter from "~/components/SiteFooter.astro";
import NeonMotion from "~/components/NeonMotion.astro";
import { getLang } from "~/i18n";
-import { licenseCopy } from "~/i18n/pages/license";
+import { pricingCopy } from "~/i18n/pages/pricing";
import { breadcrumbs, webPage } from "~/lib/structured-data";
const lang = getLang(Astro);
-const c = licenseCopy[lang];
+const c = pricingCopy[lang];
const jsonLd = [
- webPage(lang, "/license", c.meta.title, c.meta.description),
- breadcrumbs(lang, "/license", c.meta.breadcrumbHome, c.meta.breadcrumbPage),
+ webPage(lang, "/pricing", c.meta.title, c.meta.description),
+ breadcrumbs(lang, "/pricing", c.meta.breadcrumbHome, c.meta.breadcrumbPage),
];
---
diff --git a/src/components/pages/ThinkWatchPage.astro b/src/components/pages/ThinkWatchPage.astro
index 4d3e3d8..45566a6 100644
--- a/src/components/pages/ThinkWatchPage.astro
+++ b/src/components/pages/ThinkWatchPage.astro
@@ -92,7 +92,7 @@ const delay = (i: number) => `animation-delay: ${i * 90}ms;`;
{c.licenseTeaser.link}
diff --git a/src/content/docs/en/overview.md b/src/content/docs/en/overview.md
index cfda620..f14f4d5 100644
--- a/src/content/docs/en/overview.md
+++ b/src/content/docs/en/overview.md
@@ -22,4 +22,4 @@ ThinkWatch Enterprise is a self-hosted AI API and MCP gateway for organizations.
3. [Configuration](/docs/configuration): environment variables and system settings.
4. [Security](/docs/security): authentication, encryption, RBAC and the hardening checklist.
-ThinkWatch Enterprise is source-available under the Business Source License 1.1: free for non-production use, and free in production up to monthly thresholds. See [License](/license).
+ThinkWatch Enterprise is source-available under the Business Source License 1.1: free for non-production use, and free in production up to monthly thresholds. See [Pricing](/pricing).
diff --git a/src/content/docs/zh-CN/overview.md b/src/content/docs/zh-CN/overview.md
index e8fd327..9e2a209 100644
--- a/src/content/docs/zh-CN/overview.md
+++ b/src/content/docs/zh-CN/overview.md
@@ -22,4 +22,4 @@ ThinkWatch 企业版是面向组织自托管的 AI API 与 MCP 网关。组织
3. [配置说明](/zh-CN/docs/configuration):环境变量与系统设置。
4. [安全模型](/zh-CN/docs/security):认证、加密、RBAC 与加固清单。
-ThinkWatch 企业版在 Business Source License 1.1 下源码开放:非生产环境免费,生产环境在月度阈值以内免费,详见[许可证](/zh-CN/license)。
+ThinkWatch 企业版在 Business Source License 1.1 下源码开放:非生产环境免费,生产环境在月度阈值以内免费,详见[定价](/zh-CN/pricing)。
diff --git a/src/i18n/index.ts b/src/i18n/index.ts
index 4917017..5d1333c 100644
--- a/src/i18n/index.ts
+++ b/src/i18n/index.ts
@@ -17,12 +17,11 @@ const dict = {
thinkwatch: "Enterprise",
lite: "Lite",
core: "Core",
- license: "Pricing",
+ pricing: "Pricing",
how: "How it works",
features: "Features",
mcp: "MCP",
console: "Console",
- pricing: "Pricing",
quickstart: "Quick start",
docs: "Docs",
changelog: "Changelog",
@@ -248,12 +247,11 @@ const dict = {
thinkwatch: "企业版",
lite: "Lite",
core: "Core",
- license: "定价",
+ pricing: "定价",
how: "工作原理",
features: "功能特性",
mcp: "MCP",
console: "控制台",
- pricing: "定价",
quickstart: "快速开始",
docs: "文档",
changelog: "更新日志",
diff --git a/src/i18n/pages/license.ts b/src/i18n/pages/pricing.ts
similarity index 99%
rename from src/i18n/pages/license.ts
rename to src/i18n/pages/pricing.ts
index 188e33c..e8ac5ad 100644
--- a/src/i18n/pages/license.ts
+++ b/src/i18n/pages/pricing.ts
@@ -1,4 +1,4 @@
-// Copy for the /license page.
+// Copy for the /pricing page.
// Every rule, tier, price and definition here mirrors LICENSING.md in the
// ThinkWatch repository. If that file changes, update this one to match,
// and keep the numbers identical across both languages.
@@ -19,7 +19,7 @@ const tierNumbers = [
{ name: "Enterprise", tokens: "1,000,000,001 – 10,000,000,000", calls: "1,000,001 – 10,000,000", free: false },
] as const;
-export const licenseCopy = {
+export const pricingCopy = {
en: {
meta: {
title: "Pricing · ThinkWatch",
@@ -252,4 +252,4 @@ export const licenseCopy = {
},
} as const;
-export default licenseCopy;
+export default pricingCopy;
diff --git a/src/lib/lastmod.ts b/src/lib/lastmod.ts
index 0c82a83..c0a41a1 100644
--- a/src/lib/lastmod.ts
+++ b/src/lib/lastmod.ts
@@ -112,8 +112,8 @@ export function pageSources(pathname: string): string[] {
// The sections below the hero still read their copy from the shared dictionary.
"src/i18n/index.ts",
];
- case "/license":
- return ["src/components/pages/LicensePage.astro", "src/i18n/pages/license.ts"];
+ case "/pricing":
+ return ["src/components/pages/PricingPage.astro", "src/i18n/pages/pricing.ts"];
case "/changelog":
return ["src/components/pages/ChangelogPage.astro", "src/i18n/pages/changelog.ts", "src/content/changelog"];
case "/docs":
diff --git a/src/pages/license.astro b/src/pages/license.astro
deleted file mode 100644
index d47245b..0000000
--- a/src/pages/license.astro
+++ /dev/null
@@ -1,5 +0,0 @@
----
-import LicensePage from "~/components/pages/LicensePage.astro";
----
-
-
diff --git a/src/pages/pricing.astro b/src/pages/pricing.astro
new file mode 100644
index 0000000..50e66cc
--- /dev/null
+++ b/src/pages/pricing.astro
@@ -0,0 +1,5 @@
+---
+import PricingPage from "~/components/pages/PricingPage.astro";
+---
+
+
diff --git a/src/pages/zh-CN/license.astro b/src/pages/zh-CN/license.astro
deleted file mode 100644
index d47245b..0000000
--- a/src/pages/zh-CN/license.astro
+++ /dev/null
@@ -1,5 +0,0 @@
----
-import LicensePage from "~/components/pages/LicensePage.astro";
----
-
-
diff --git a/src/pages/zh-CN/pricing.astro b/src/pages/zh-CN/pricing.astro
new file mode 100644
index 0000000..50e66cc
--- /dev/null
+++ b/src/pages/zh-CN/pricing.astro
@@ -0,0 +1,5 @@
+---
+import PricingPage from "~/components/pages/PricingPage.astro";
+---
+
+