feat(docs): 换品牌图标 + 补备案号 + 给 agent 的直读入口

三件事,都是「站点上线后看出来的」问题。

## ① 图标用的是 Material 默认,不是我们的

站上 favicon 是 mkdocs-material 自带的那张(`assets/images/favicon.png`),
与主站 introduce 不一致。改为引入主站同一份 logo:

- `docs/assets/logo.svg` —— 原样(浅色底,适合 favicon)
- `docs/assets/logo-mark.svg` —— 去掉底色矩形(否则在靛蓝页头上是个白方块)

`theme.favicon` / `theme.logo` 分别指向它们。实测子页面路径也正确
(mkdocs 生成 `../../assets/logo.svg`,不是错误的相对路径)。

## ② 缺备案号

`introduce` 底部有 ICP + 公安备案,文档站没有。Material 的 footer 只渲染
`config.copyright` 一个字符串,塞不进「两条带链接的备案」——所以覆盖了
`overrides/partials/footer.html`(`theme.custom_dir`),并顺带把许可也写进底部,
读者在任何一页都能看到,不必翻到首页。

## ③ 没有给 agent 的入口

站点是给人看的(HTML + 主题 + JS 搜索),但越来越多读者是 agent。让它们爬
HTML 既浪费 token(样板占大头)又容易漏内容。

新增 `tools/apidoc/gensite/agent.go`,随构建产出:

| 路径 | 内容 |
|---|---|
| `/llms.txt` | 站点目录:每页一行,带 URL 与一句话说明(4.3KB)|
| `/llms-full.txt` | 全部文档正文拼成一份,可一次读完(115KB)|
| `/<page>.md` | 每个页面的 Markdown 原文,含生成的 API 页(text/markdown)|

沿用 llms.txt 社区约定:`llms.txt` 读目录、`llms-full.txt` 一次读全。

**一个必须处理的坑**:mkdocs 只把 `.md` **渲染**成 HTML,不会把 Markdown
放进产物目录 —— 那样 `llms.txt` 里的链接会全部 404。所以 `build.sh` 增加了
第 4 步 `copy_agent_files`,在构建后把 23 个 Markdown 复制进 `site_build/`。

`docs/llms-full.txt` 已 gitignore:它是派生件,改任何一页都会整份重写,
进版本库只产生噪声(`llms.txt` 索引小且稳定,仍提交)。

验证:`mkdocs build --strict` 零告警;favicon/logo 可取(200,naturalWidth=400);
三页底部均含两个备案号;4 个 agent 入口均可访问且 content-type 正确。
This commit is contained in:
JianFeeeee
2026-09-24 13:27:58 +08:00
parent 9b6abe1b73
commit 255d6479ad
9 changed files with 372 additions and 8 deletions

View File

@ -0,0 +1,59 @@
{#-
footer.html 覆盖:在版权行下补**备案号**。
为什么要覆盖主题文件:Material 的 copyright 只渲染 config.copyright(一个字符串),
而备案号必须是**带链接的 HTML**且含两个条目(ICP + 公安),塞不进那个字段。
另外把「许可」写进 footer:本站内容与主站一致受 AGPL 约束,
读者在任何页面底部都能看到,不必翻到首页。
-#}
<footer class="md-footer">
{% if "navigation.footer" in features %}
{% if page.previous_page or page.next_page %}
{% if page.meta and page.meta.hide %}
{% set hidden = "hidden" if "footer" in page.meta.hide %}
{% endif %}
<nav class="md-footer__inner md-grid" aria-label="{{ lang.t('footer') }}" {{ hidden }}>
{% if page.previous_page %}
{% set direction = lang.t("footer.previous") %}
<a href="{{ page.previous_page.url | url }}" class="md-footer__link md-footer__link--prev" aria-label="{{ direction }}: {{ page.previous_page.title | e }}">
<div class="md-footer__button md-icon">
{% set icon = config.theme.icon.previous or "material/arrow-left" %}
{% include ".icons/" ~ icon ~ ".svg" %}
</div>
<div class="md-footer__title">
<span class="md-footer__direction">{{ direction }}</span>
<div class="md-ellipsis">{{ page.previous_page.title }}</div>
</div>
</a>
{% endif %}
{% if page.next_page %}
{% set direction = lang.t("footer.next") %}
<a href="{{ page.next_page.url | url }}" class="md-footer__link md-footer__link--next" aria-label="{{ direction }}: {{ page.next_page.title | e }}">
<div class="md-footer__title">
<span class="md-footer__direction">{{ direction }}</span>
<div class="md-ellipsis">{{ page.next_page.title }}</div>
</div>
<div class="md-footer__button md-icon">
{% set icon = config.theme.icon.next or "material/arrow-right" %}
{% include ".icons/" ~ icon ~ ".svg" %}
</div>
</a>
{% endif %}
</nav>
{% endif %}
{% endif %}
<div class="md-footer-meta md-typeset">
<div class="md-footer-meta__inner md-grid">
{% include "partials/copyright.html" %}
<div class="md-copyright ha-beian">
<a href="https://beian.miit.gov.cn" target="_blank" rel="noopener noreferrer">豫ICP备2024074105号-1</a>
<span class="ha-beian-sep">·</span>
<a href="https://beian.mps.gov.cn" target="_blank" rel="noopener noreferrer">豫公网安备41070202001579号</a>
</div>
{% if config.extra.social %}
{% include "partials/social.html" %}
{% endif %}
</div>
</div>
</footer>