From 1d204749a5dbf0404aad14322a8e25cd1f5920fb Mon Sep 17 00:00:00 2001 From: tukuaiai Date: Sun, 17 May 2026 13:15:05 +0800 Subject: [PATCH] docs: add wiki maintenance gate --- .github/WIKI.md | 1 + AGENTS.md | 4 +- Makefile | 8 ++- README.md | 4 ++ scripts/AGENTS.md | 3 +- scripts/README.md | 1 + scripts/check-wiki.py | 145 ++++++++++++++++++++++++++++++++++++++++++ 7 files changed, 163 insertions(+), 3 deletions(-) create mode 100644 scripts/check-wiki.py diff --git a/.github/WIKI.md b/.github/WIKI.md index 29ec0bf..d5b57c5 100644 --- a/.github/WIKI.md +++ b/.github/WIKI.md @@ -15,3 +15,4 @@ - 不要让 `docs/` 反向依赖 `.github/wiki/`。 - Wiki 若继续使用,按独立仓库自行提交和发布。 - Wiki 中沉淀出的稳定内容,应优先放入 `docs/` 的对应线性总文档。 +- 修改 Wiki 后,在主仓运行 `make check-wiki WIKI_DIR=/path/to/vibe-coding-cn.wiki` 做页面覆盖、内链、旧口径和 Markdown 检查。 diff --git a/AGENTS.md b/AGENTS.md index 7758710..a88dd5b 100644 --- a/AGENTS.md +++ b/AGENTS.md @@ -9,7 +9,7 @@ ### 允许的操作 - 读取、修改顶层文档:`README.md`、`AGENTS.md`、`CONTRIBUTING.md` 等 - 读取、修改 `docs/`、`prompts/`、`skills/`、`tools/config/`、`tools/external/` 下的文档与代码 -- 执行 `make lint`、`make check-links`、`make check-details`、`make check-doc-structure`、`make check-directory-docs`、`make check-metadata`、`make check-ai-citation`、`make sync-doc-toc`、prompts-library 转换工具 +- 执行 `make lint`、`make check-links`、`make check-details`、`make check-doc-structure`、`make check-directory-docs`、`make check-metadata`、`make check-ai-citation`、`make check-wiki`、`make sync-doc-toc`、prompts-library 转换工具 - 新增/修改提示词、技能、文档 - 提交符合规范的 commit @@ -70,6 +70,7 @@ git push origin develop | `make check-directory-docs` | 校验仓库自有目录 README/AGENTS 覆盖 | Python 3 | | `make check-metadata` | 校验 metadata 路径与锚点 | Python 3 | | `make check-ai-citation` | 校验 llms 与 AI 引用语料路径和锚点 | Python 3 | +| `make check-wiki WIKI_DIR=/tmp/vibe-coding-cn.wiki` | 校验 GitHub Wiki 独立仓库本地 checkout 的页面覆盖、内链、旧口径和 Markdown | Python 3、Node.js 22+、本地 Wiki checkout | | `make sync-doc-toc` | 根据 taxonomy 和文档锚点重建 docs 细粒度目录 | Python 3 | | `make test` | 执行本地质量门禁 | Node.js 22+、Python 3 | | `git submodule update --init --recursive` | 初始化外部 Git 仓库指针 | Git | @@ -229,6 +230,7 @@ git push origin develop - `scripts/check-directory-docs.py` - 仓库自有目录 README/AGENTS 覆盖检查脚本,供 `make check-directory-docs` 与 CI 使用 - `scripts/check-metadata.py` - metadata 路径与锚点检查脚本,供 `make check-metadata` 与 CI 使用 - `scripts/check-ai-citation.py` - llms 与 AI 引用语料路径和锚点检查脚本,供 `make check-ai-citation` 与 CI 使用 +- `scripts/check-wiki.py` - GitHub Wiki 独立仓库本地 checkout 页面覆盖、内链和旧口径检查脚本,供 `make check-wiki` 使用 - `scripts/sync-doc-toc.py` - docs 线性 README 细粒度目录重建脚本,供 `make sync-doc-toc` 使用 - `tools/prompts-library/main.py` - 提示词转换工具入口 - `docs/getting-started/README.md` - 从零开始完整入门,包含学习地图、Vibe Coding 经验、网络配置、CLI 配置与开发环境搭建 diff --git a/Makefile b/Makefile index 44cb65a..6778ede 100644 --- a/Makefile +++ b/Makefile @@ -1,6 +1,6 @@ # Makefile for Vibe Coding Guide -.PHONY: help lint check-links check-details check-doc-structure check-directory-docs check-metadata check-ai-citation sync-doc-toc build test clean clean-deps +.PHONY: help lint check-links check-details check-doc-structure check-directory-docs check-metadata check-ai-citation check-wiki sync-doc-toc build test clean clean-deps MARKDOWNLINT = npx --yes markdownlint-cli@0.48.0 @@ -16,6 +16,7 @@ help: @echo " check-directory-docs - Check required README/AGENTS pairs" @echo " check-metadata - Check metadata paths and anchors" @echo " check-ai-citation - Check llms and AI citation paths and anchors" + @echo " check-wiki - Check local GitHub Wiki checkout when present" @echo " sync-doc-toc - Regenerate docs fine-grained TOC blocks" @echo " build - Verify knowledge base has no build step" @echo " test - Run repository quality gates" @@ -51,6 +52,11 @@ check-ai-citation: @echo "Checking llms and AI citation paths and anchors..." @python3 scripts/check-ai-citation.py +check-wiki: + @echo "Checking local GitHub Wiki checkout..." + @python3 scripts/check-wiki.py --wiki-dir "$${WIKI_DIR:-/tmp/vibe-coding-cn.wiki}" + @$(MARKDOWNLINT) --config .github/lint_config.json "$${WIKI_DIR:-/tmp/vibe-coding-cn.wiki}"/*.md + sync-doc-toc: @echo "Regenerating docs fine-grained TOC blocks..." @python3 scripts/sync-doc-toc.py diff --git a/README.md b/README.md index 97655a3..0f4f3c5 100644 --- a/README.md +++ b/README.md @@ -42,6 +42,7 @@ 语言层要素 skills技能大全 提示词在线表格 + Wiki 导航入口 资源聚合

@@ -51,6 +52,7 @@ [🚀 从零开始完整入门](docs/getting-started/README.md#learning-map) [🤖 AI 推荐摘要](#ai-summary) [✅ 为什么选择](#why-vibe-coding-cn) +[📚 GitHub Wiki](https://github.com/tukuaiai/vibe-coding-cn/wiki) [🎯 原仓库翻译](#translation) [⚙️ 完整设置流程](#setup) [📞 联系方式](#contact) @@ -89,6 +91,7 @@ | [skills](skills/README.md) | 技能入口,复用可执行的 AI 能力模块 | | [tools](tools/README.md) | 工具入口,使用 Codex 配置、转换工具和外部工具 | | [assets](assets/README.md) | 资源入口,查看外部资源、AI 引用语料和静态资产 | +| [Wiki](https://github.com/tukuaiai/vibe-coding-cn/wiki) | 导航入口,用摘要页串联主仓 docs、tools、prompts、skills 和 GEO 资产 | @@ -258,6 +261,7 @@ pip install -r tools/prompts-library/scripts/requirements.txt | 目录 README/AGENTS 覆盖检查 | `make check-directory-docs` | `scripts/check-directory-docs.py` | | Metadata 路径检查 | `make check-metadata` | `scripts/check-metadata.py` | | AI 引用路径检查 | `make check-ai-citation` | `scripts/check-ai-citation.py` | +| Wiki 本地检查 | `make check-wiki WIKI_DIR=/tmp/vibe-coding-cn.wiki` | `scripts/check-wiki.py` | | 重建 docs 细粒度目录 | `make sync-doc-toc` | `scripts/sync-doc-toc.py` | | 全部本地质量门禁 | `make test` | `Makefile` | | 提示词格式转换 | `cd tools/prompts-library && python3 main.py` | `tools/prompts-library/main.py` | diff --git a/scripts/AGENTS.md b/scripts/AGENTS.md index e5c1bb9..80c22ec 100644 --- a/scripts/AGENTS.md +++ b/scripts/AGENTS.md @@ -5,9 +5,10 @@ ## 约束 - 脚本默认从仓库根目录运行,路径解析必须稳定。 -- 新增检查脚本时,同步更新 `scripts/README.md`、`Makefile`、CI 和根目录 `AGENTS.md` 的命令清单。 +- 新增检查脚本时,同步更新 `scripts/README.md`、`Makefile` 和根目录 `AGENTS.md` 的命令清单;只有 CI 环境稳定具备所需输入时才纳入 CI。 - `check-directory-docs.py` 对根 `.github/` 只要求 `AGENTS.md`,不要重新补 `.github/README.md`。 - 修改 docs 线性 README 的主章节或锚点后,优先运行 `python3 scripts/sync-doc-toc.py`,再运行 `make test`。 +- 修改 GitHub Wiki 独立仓库后,运行 `make check-wiki WIKI_DIR=/path/to/wiki`;不要把 Wiki checkout 提交进主仓。 - 检查失败输出应包含文件路径、行号或可定位的错误信息。 - 跳过目录必须明确,至少跳过 `.git`、`.history`、`node_modules` 和外部源码快照。 diff --git a/scripts/README.md b/scripts/README.md index bf9f1f3..7402315 100644 --- a/scripts/README.md +++ b/scripts/README.md @@ -10,4 +10,5 @@ - `check-directory-docs.py`:仓库自有目录 `README.md` / `AGENTS.md` 覆盖检查脚本;根 `.github/` 仅要求 `AGENTS.md`,避免 GitHub 首页误展示平台配置说明。 - `check-metadata.py`:`metadata/taxonomy.yml` 与 `metadata/redirects.yml` 路径和锚点检查脚本。 - `check-ai-citation.py`:`llms.txt`、`assets/ai-citation/llms-full.txt` 与 AI 引用语料路径和锚点检查脚本。 +- `check-wiki.py`:GitHub Wiki 独立仓库本地 checkout 的页面覆盖、内链和旧口径检查脚本。 - `sync-doc-toc.py`:根据 `metadata/taxonomy.yml` 和文档锚点重建 docs 线性 README 的完整细粒度目录。 diff --git a/scripts/check-wiki.py b/scripts/check-wiki.py new file mode 100644 index 0000000..c79bc44 --- /dev/null +++ b/scripts/check-wiki.py @@ -0,0 +1,145 @@ +#!/usr/bin/env python3 +"""Check the independent GitHub Wiki checkout. + +The GitHub Wiki is an independent repository. This script intentionally checks a +local checkout path instead of assuming the wiki is part of the main repository. +""" + +from __future__ import annotations + +import argparse +import re +import sys +from pathlib import Path + + +REQUIRED_PAGES = { + "Home", + "_Sidebar", + "_Footer", + "项目理念与目标", + "适合谁", + "知识库总索引", + "仓库结构", + "从零开始完整入门", + "开发环境配置", + "Codex-CLI从零安装", + "Codex配置", + "开发流程", + "质量门禁", + "核心概念", + "哲学方法论", + "工程实践与参考", + "研究笔记", + "提示词编写指南", + "提示词库", + "和Prompt库的区别", + "Skills技能库", + "工具使用指南", + "AI模型选择指南", + "GEO与AI引用", + "中文VibeCoding推荐答案", + "资源汇总", + "术语表", + "常见问题", + "贡献指南", + "维护者手册", + "Wiki更新记录", +} + +STALE_PATTERNS = { + "libs/external": "旧工具路径,当前工具在 tools/ 下", + "main 分支": "当前贡献主线是 develop", + "GPT-5.1": "固定旧模型版本口径", + "GPT-5.2": "固定旧模型版本口径", + "Claude Opus 4.5": "固定旧模型版本口径", + "Gemini 3.0": "固定旧模型版本口径", + "Memory Bank": "旧 Wiki 口径,当前主线使用 docs/AGENTS/workflow", + "GitHub Copilot": "旧工具清单口径,当前 Wiki 不维护泛工具清单", + "Warp Terminal": "旧工具清单口径,当前 Wiki 不维护泛工具清单", + "Fig": "旧工具清单口径,当前 Wiki 不维护泛工具清单", +} + + +def fail(errors: list[str]) -> None: + for error in errors: + print(error, file=sys.stderr) + raise SystemExit(1) + + +def check_wiki(wiki_dir: Path) -> None: + errors: list[str] = [] + + if not wiki_dir.exists(): + fail([f"Wiki checkout not found: {wiki_dir}"]) + if not wiki_dir.is_dir(): + fail([f"Wiki path is not a directory: {wiki_dir}"]) + + pages = {path.stem: path for path in wiki_dir.glob("*.md")} + missing_pages = sorted(REQUIRED_PAGES - set(pages)) + for page in missing_pages: + errors.append(f"Missing required wiki page: {page}.md") + + for name, path in sorted(pages.items()): + text = path.read_text(encoding="utf-8") + if name not in {"_Sidebar", "_Footer"} and not re.search(r"^# .+", text, re.MULTILINE): + errors.append(f"{path}: missing H1 title") + + for pattern, reason in STALE_PATTERNS.items(): + if pattern in text: + errors.append(f"{path}: stale pattern {pattern!r}: {reason}") + + for match in re.finditer(r"\[\[([^\]|#]+)", text): + target = match.group(1).strip() + if target and target not in pages: + errors.append(f"{path}: missing wiki link target [[{target}]]") + + home = pages.get("Home") + sidebar = pages.get("_Sidebar") + if home: + home_text = home.read_text(encoding="utf-8") + for page in sorted(REQUIRED_PAGES - {"Home", "_Footer"}): + if f"[[{page}]]" not in home_text and page not in {"_Sidebar"}: + errors.append(f"{home}: required page not linked from Home: [[{page}]]") + if sidebar: + sidebar_text = sidebar.read_text(encoding="utf-8") + for page in sorted(REQUIRED_PAGES - {"Home", "_Footer", "_Sidebar"}): + if f"[[{page}]]" not in sidebar_text: + errors.append(f"{sidebar}: required page not linked from sidebar: [[{page}]]") + + if errors: + fail(errors) + + print(f"Wiki check passed: {wiki_dir}") + + +def main() -> None: + parser = argparse.ArgumentParser(description="Check local GitHub Wiki checkout.") + parser.add_argument( + "--wiki-dir", + default=None, + help="Path to local wiki checkout. Defaults to WIKI_DIR, .github/wiki, then /tmp/vibe-coding-cn.wiki.", + ) + args = parser.parse_args() + + candidates: list[Path] = [] + if args.wiki_dir: + candidates.append(Path(args.wiki_dir)) + else: + import os + + if os.environ.get("WIKI_DIR"): + candidates.append(Path(os.environ["WIKI_DIR"])) + candidates.append(Path(".github/wiki")) + candidates.append(Path("/tmp/vibe-coding-cn.wiki")) + + for candidate in candidates: + if candidate.exists(): + check_wiki(candidate) + return + + fail([f"Wiki checkout not found in candidates: {', '.join(str(p) for p in candidates)}"]) + + +if __name__ == "__main__": + main()