From e16f4a819f0d922a5804520b2d3a6fb59b14bc2d Mon Sep 17 00:00:00 2001 From: Hunter Bown Date: Tue, 23 Jun 2026 23:49:58 +0000 Subject: [PATCH] docs(web): add provenance / source-of-truth copy (footer, install, CNB) State plainly that GitHub is the sole canonical source across the site: - footer: a Provenance section shown on all locales (was a zh-only mirror list), starring the official GitHub link and noting that mirrors are China-network accelerators (link labels localized for EN/ZH) - install: an "Official source" label on the Mainland China network section - docs/CNB_MIRROR.md: a Provenance section that accurately describes the CNB-built SHA256 manifest, with a verification path Harvested from PR #3440 by @donglovejava. Dropped that branch's unrelated churn (stray working files, workflow edits, and a SECURITY.md contact change that regresses the current address) and preserved the current Gitee URL. Co-authored-by: donglovejava <211940267+donglovejava@users.noreply.github.com> Claude-Session: https://claude.ai/code/session_01991fnUqBbWSgiUFw33L8XX --- docs/CNB_MIRROR.md | 18 ++++++++++++++++++ web/app/[locale]/install/page.tsx | 6 ++++-- web/components/footer.tsx | 30 +++++++++++++++++++----------- 3 files changed, 41 insertions(+), 13 deletions(-) diff --git a/docs/CNB_MIRROR.md b/docs/CNB_MIRROR.md index 3582324a8..2a243f4ff 100644 --- a/docs/CNB_MIRROR.md +++ b/docs/CNB_MIRROR.md @@ -6,6 +6,24 @@ GitHub repository for users on networks where GitHub is slow or blocked `fix/*`, `rebrand/*`, and `work/v*` branch used for first-party release work, and every `v*` release tag. +## Provenance + +**GitHub is the sole canonical source.** All releases, tags, and source code +originate at `github.com/Hmbown/CodeWhale`. The CNB mirror is a read-only +replica maintained by the `Sync to CNB` workflow — it exists solely to serve +users behind GFW-blocked or slow GitHub connections. + +Every CNB release includes `codewhale-artifacts-sha256.txt` — a SHA256 manifest +of the CNB-built Linux x64 binaries, generated from the same source commit that +is tagged on GitHub. (CNB builds from source, so these checksums cover the +CNB-built artifacts, not GitHub's release assets.) Verify a downloaded binary +against it: + +```bash +# Verify a downloaded CNB binary against the CNB manifest +sha256sum -c codewhale-artifacts-sha256.txt +``` + ## How it works The mirror is maintained by the [`Sync to CNB`](../.github/workflows/sync-cnb.yml) diff --git a/web/app/[locale]/install/page.tsx b/web/app/[locale]/install/page.tsx index 5cb9c2e0e..7c0e01009 100644 --- a/web/app/[locale]/install/page.tsx +++ b/web/app/[locale]/install/page.tsx @@ -366,11 +366,13 @@ codewhale doctor`;

{isZh ? ( <> - Cargo 经清华 Tuna 镜像——添加到 ~/.cargo/config.toml: + 官方源: + GitHub Releases 为唯一官方发布源。Cargo 经清华 Tuna 镜像——添加到 ~/.cargo/config.toml: ) : ( <> - Cargo via Tsinghua Tuna mirror — add to{" "} + Official source:{" "} + GitHub Releases is the sole canonical release source. Cargo via Tsinghua Tuna mirror — add to{" "} ~/.cargo/config.toml: )} diff --git a/web/components/footer.tsx b/web/components/footer.tsx index bc96bd69d..215a10fb0 100644 --- a/web/components/footer.tsx +++ b/web/components/footer.tsx @@ -98,18 +98,26 @@ export function Footer({ locale = "en" }: { locale?: Locale }) {

{isZh ? "用心制作 · Made with care" : "Made with care · 用心制作"}
- {/* Mirror sources — prominent on zh */} - {isZh && ( -
-
镜像源 / Mirror
-
- {GITEE_ENABLED && Gitee 镜像} - CNB 镜像 - npmmirror - Tuna crates.io -
+ {/* Provenance / source-of-truth — shown on both locales */} +
+
+ {isZh ? "来源证明 · Provenance" : "Provenance · 来源证明"} +
+

+ {isZh + ? "GitHub (github.com/Hmbown/CodeWhale) 为唯一官方源码与发布源。下方镜像仅为中国大陆网络加速,内容经自动同步校验,SHA256 清单一致。" + : "GitHub (github.com/Hmbown/CodeWhale) is the sole canonical source for code and releases. Mirrors below are China-network accelerators only — content is auto-synced and verified via SHA256 manifests."} +

+
+ + {isZh ? "★ 官方 GitHub" : "★ Official GitHub"} + + {GITEE_ENABLED && {isZh ? "Gitee 镜像" : "Gitee mirror"}} + {isZh ? "CNB 镜像" : "CNB mirror"} + npmmirror + Tuna crates.io
- )} +
{cols.map((c) => (