MirSquad/make-my-site-agent-ready
GitHub: MirSquad/make-my-site-agent-ready
一款让 WordPress 站点为 AI agent 和大语言模型做好准备的插件,提供 markdown URL、站点索引、api-catalog、Agent Skills 发现和 AI 爬虫规则等功能。
Stars: 0 | Forks: 0
# Make My Site Agent-Ready — WordPress 插件
一款让您的网站为 AI agent 和语言模型做好准备的 WordPress 插件。在 `.md` URL 提供纯净的 markdown,生成 `/llms.txt` 和 `/llms-full.txt` 站点索引,提供 `/.well-known/security.txt`,发布机器可读的 `/.well-known/api-catalog`,开放 Agent Skills 发现机制,发送 `Link` 响应头来对外宣告所有这些功能,通过 `robots.txt` 中的 Content Signals 声明 AI 使用偏好,添加 AI 爬虫规则,可选择通过 JSON-LD 结构化数据将 agent 指向 markdown 替代版本(在启用时将其合并到 Yoast SEO 自身的 schema 中,因此不会产生任何重复),并为 AI agent 管理暴露 WordPress Abilities API endpoint。
## 为什么需要
AI 模型和 agent 越来越需要读取网站内容,发现可用资源,并了解网站所有者允许或不允许它们对这些内容做什么。对于第一个问题,HTML 显得过于嘈杂——导航、广告、脚本和样式都会造成干扰。而默认的 WordPress 在很大程度上并未解决发现机制和使用偏好的问题。这款插件解决了所有这三个问题:用于读取的纯净 markdown、用于发现的机器可读索引和标头,以及用于使用偏好的明确信号。
在构建最初的 `.md`/llms.txt 功能集之前,我们分析了八款现有的插件。大多数设计得过于复杂——自定义转换器、内容协商、user-agent 嗅探。这款插件始终采用更简单的方法:在保存时生成一次 markdown,提供预构建的索引,并明确声明偏好。
## 功能
### 内容访问
- **`.md` URL 后缀** — 任何文章或页面都可以通过在其 URL 后附加 `.md` 来访问(例如 `your-site.com/my-post.md`)
- **首页**位于 `/index.md`
- **YAML frontmatter** — 包含标题、日期、作者、URL、摘要、分类和标签
- **保存时预生成** — markdown 存储在 post meta 中,因此 `.md` 请求可以瞬间响应,无需任何处理
- **`/llms.txt` 站点索引** — 列出所有按分类组织的可用 markdown URL,使用 24 小时 transient 进行缓存
- **`/llms-full.txt`** — 将全站内容拼接为单个 markdown 文件,适用于需要一次性获取所有内容的 LLM
- **``** — HTML 页面包含一个指向其 markdown 版本的 link 标签
### 发现机制
- **`/.well-known/api-catalog`** (RFC 9727) — 一个 Linkset (RFC 9264) JSON 文档,在一个机器可读文件中索引 `llms.txt`、`llms-full.txt`、`security.txt`、Agent Skills 索引、sitemap 和 feed
- **Agent Skills 发现机制** — `/.well-known/agent-skills/index.json` 以及一个内置技能 (`fetch-content-as-markdown`),教导 agent 如何使用此插件的 markdown endpoint 而不是解析 HTML。提供的技能文件及其索引摘要在请求时根据同一数据源计算,因此它们永远不会出现不同步的情况。
- **`Link` 响应标头** (RFC 8288) — 每个前端响应都带有指向 api-catalog 和 Agent Skills 索引的 `Link` 标头;单篇文章/页面会添加第三个指向其 markdown 替代版本的标头。让那些只读取标头而不读取 HTML 的 agent 依然能找到这些资源。
- **结构化数据 (JSON-LD)** — 选择性开启,默认关闭。通过 `encoding`/`MediaObject` 字段将 agent 指向 markdown 替代版本。当 Yoast SEO 处于活动状态并为页面生成 schema 时,这会直接合并到 Yoast 自己的 `Article`/`WebPage` 片段中——没有重复的块,Yoast graph 中的其他内容也不会受到影响。否则(没有 Yoast,或者 Yoast 未覆盖的页面类型),则会添加一个独立的精简版 `Article`/`WebPage` JSON-LD 块。在 Settings > Agent-Ready 中启用。
### 使用偏好与爬虫规则
- **Content Signals** — 在 `robots.txt` 中的每个 AI 爬虫组下声明 `Content-Signal: search=..., ai-input=..., ai-train=...`(依据 [contentsignals.org](https://contentsignals.org/) / IETF AI Preferences 草案)。可针对每个站点独立配置:允许索引、允许实时 AI 检索、允许/拒绝模型训练使用。
- **`robots.txt` 中的 AI 爬虫规则** — 为 GPTBot、ClaudeBot、Anthropic-AI、GoogleOther、PerplexityBot 和 FacebookBot 添加明确的 `Allow: /` 条目;如果尚未存在,则添加 `Sitemap:` 指令
- **`/.well-known/security.txt`** — 提供 security.txt 文件 (RFC 9116),可通过 Settings 配置内容
### 配置与操作
- **设置页面** (Settings > Agent-Ready) — 文章类型选择器、CSS 根选择器、robots.txt 预览和额外规则文本域、security.txt 内容、Content Signals 开关、结构化数据 (JSON-LD) 开关,以及指向插件提供的所有 endpoint 的快速链接
- **批量重新生成** — 设置页面上的“Regenerate All”按钮
- **规范的 HTTP 标头** — `Content-Type: text/markdown`、`X-Robots-Tag: noindex`、`X-Content-Type-Options: nosniff`、规范链接
- **密码保护** — 受密码保护的文章在 `.md` URL 上返回 403
- **彻底卸载** — 移除所有插件数据(post meta、选项、transient)
## 工作原理
1. 当您保存文章时,插件会使用 [league/html-to-markdown](https://github.com/thephpleague/html-to-markdown) 将其渲染后的 HTML 转换为 markdown,并将其存储在 post meta 中
2. 单个重写规则会捕获所有 `.md` 请求(排除 `/.well-known/` 路径,这些路径会路由到它们各自的处理器——请参阅下文的架构说明)
3. 插件将请求解析为文章,从 meta 中读取预生成的 markdown,并附带适当的标头将其发送出去
4. `/llms.txt` endpoint 构建一个包含所有可用 markdown URL 的分类索引
5. `/llms-full.txt` endpoint 将所有文章和页面的全部内容拼接成一个单一文件
6. `/.well-known/api-catalog`、Agent Skills endpoint 和 `Content-Signal` 指令都以相同的方式生成——在请求时根据实时的站点状态计算,而不是手动维护的静态文件
由于 markdown 是在保存时生成的,因此响应 `.md` 请求本质上是一次单一的 meta 查询——没有 HTML 解析,没有 API 调用,也没有处理开销。
## 安装
1. 下载或克隆此代码仓库
2. 将 `make-my-site-agent-ready` 文件夹上传到 `wp-content/plugins/`
3. 在 WordPress 中激活插件
4. 前往 **Settings > Agent-Ready** 配置文章类型、robots.txt 规则、security.txt 内容和 Content Signals
5. 访问 **Settings > Permalinks** 并点击保存(以刷新重写规则)——在未来的插件更新后不需要这样做,仅在首次安装时需要,因为从 v1.4.0 版本开始,版本更新会自动刷新重写规则
该插件在 `vendor/` 文件夹中包含了其唯一的依赖项 (`league/html-to-markdown`)——无需运行 Composer install。
## 输出示例
**`your-site.com/hello-world.md`** 返回:
```
---
title: "Hello World"
date: "2026-01-15"
author: "Jane Doe"
url: "https://your-site.com/hello-world/"
excerpt: "Welcome to my site."
categories:
- "Uncategorized"
tags: []
---
Welcome to WordPress. This is your first post. Edit or delete it, then start writing!
```
**`your-site.com/llms.txt`** 返回一个站点索引,其中包含按分类分组的所有可用 markdown URL。
**`your-site.com/llms-full.txt`** 以拼接的 markdown 格式返回每篇已发布文章和页面的全部内容。
**`your-site.com/.well-known/api-catalog`** 返回一个 Linkset JSON 文档,索引了插件提供的每个可被发现资源。
**`your-site.com/robots.txt`** 返回,在每个 AI 爬虫组下:
```
User-agent: GPTBot
Allow: /
Content-Signal: search=yes, ai-input=yes, ai-train=no
```
**在启用结构化数据且 Yoast SEO 处于活动状态的单篇文章中**,会有一个 `encoding` 字段被直接合并到 Yoast 自身的 `Article` 片段中:
```
{
"@type": "Article",
"headline": "Hello World",
"datePublished": "2026-01-15T09:00:00+00:00",
"...": "...Yoast's other Article fields (author, publisher, wordCount, etc.), unchanged...",
"encoding": {
"@type": "MediaObject",
"contentUrl": "https://your-site.com/hello-world.md",
"encodingFormat": "text/markdown"
}
}
```
**在未启用 Yoast 的情况下**(或者对于 Yoast 未覆盖的页面类型),相同的信息将作为其独立的块发送:
```
{
"@context": "https://schema.org",
"@type": "Article",
"url": "https://your-site.com/hello-world/",
"headline": "Hello World",
"datePublished": "2026-01-15T09:00:00+00:00",
"dateModified": "2026-01-15T09:00:00+00:00",
"encoding": {
"@type": "MediaObject",
"contentUrl": "https://your-site.com/hello-world.md",
"encodingFormat": "text/markdown"
}
}
```
## 架构说明
**`.md` 全局匹配重写规则排除了 `/.well-known/`。** 提供文章/页面 `.md` URL 的宽泛规则 (`^(.+)\.md/?$`) 否则也会匹配像 `/.well-known/agent-skills/*/SKILL.md` 这样的路径,并且——取决于重写规则的注册顺序——可能会覆盖这些路径的更具体规则。全局匹配规则通过使用负向先行断言 (`^(?!\.well-known/)(.+)\.md/?$`) 进行了范围限制,因此无论插件(或其未来版本)在 `/.well-known/` 下添加了什么,都不会发生这种情况。
**`Link` 标头在 `template_redirect` 时发送,而不是在 `send_headers` 时发送。** `send_headers` 在 WordPress 解析主查询之前触发,因此此时像 `is_singular()` 这样的条件标签还不可靠。`template_redirect` 在查询解析之后触发,并且仍然有足够早的时间来设置标头。
**Content Signals 是按 AI 爬虫组发出的,从不在 `User-agent: *` 下发出。** 该组通常由 SEO 插件(在此默认为 Yoast)拥有——向其添加内容可能会面临与其他插件输出冲突的风险。
**结构化数据合并到 Yoast 的 schema 中,而不是对其进行重复。** Yoast 的 Schema Framework 已经在每个页面上声明了 type、url、title 和 dates——此插件添加的唯一新事实是指向 markdown 替代版本的 `encoding`/`MediaObject` 指针。当 Yoast 为当前页面生成 schema 片段时,该字段通过 Yoast 官方文档记录的 `wpseo_schema_article`/`wpseo_schema_webpage` 过滤器直接注入到 Yoast 自身的 `Article`/`WebPage` 片段中——无条件注册(不依赖于在插件加载时检测 Yoast,因为跨插件的加载顺序无法保证;如果 Yoast 未处于活动状态,这些过滤器根本就不会触发)。当注入不适用时,会回退为不带 `@id` 的独立块——例如没有 Yoast、Yoast 的 schema 输出被禁用,或者 Yoast 为其提供了独立 schema 的内容类型(如 WooCommerce 产品)。
## 环境要求
- WordPress 6.0+
- PHP 7.4+
## 许可证
GPL-2.0-or-later
## WordPress Abilities API
此插件为 [WordPress Abilities API](https://developer.wordpress.org/apis/abilities-api/) (WordPress 6.9+) 暴露了相应的 abilities,使其能够通过 [MCP Adapter](https://github.com/WordPress/mcp-adapter) 插件由 AI agent 进行管理。
### 环境要求
- WordPress 6.9+
- [MCP Adapter 插件](https://github.com/WordPress/mcp-adapter)
### 可用 abilities
| Ability | 访问级别 | 描述 |
|---|---|---|
| `make-my-site-agent-ready/get-settings` | 始终开启 | 返回已启用的文章类型和内容根 CSS 选择器 |
| `make-my-site-agent-ready/regenerate-files` | 始终开启(破坏性) | 为所有已发布的内容重新生成缓存的 markdown,并清除 llms.txt 和 llms-full.txt 缓存。AI 工具在运行前会要求确认。 |
标签:DLL 劫持, ffuf, Markdown, SEO优化, WordPress插件, 内容分发, 大语言模型, 文件完整性监控