@relvehq/agent-ready 0.0.0-stage → 0.2.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (82) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +338 -3
  3. package/SETUP.md +337 -0
  4. package/dist/bin/agent-ready.d.ts +23 -0
  5. package/dist/bin/agent-ready.js +350 -0
  6. package/dist/cli/init.d.ts +70 -0
  7. package/dist/cli/init.js +366 -0
  8. package/dist/core/accept.d.ts +8 -0
  9. package/dist/core/accept.js +76 -0
  10. package/dist/core/config.d.ts +145 -0
  11. package/dist/core/config.js +103 -0
  12. package/dist/core/convert.d.ts +22 -0
  13. package/dist/core/convert.js +334 -0
  14. package/dist/core/detect.d.ts +30 -0
  15. package/dist/core/detect.js +82 -0
  16. package/dist/core/easy.d.ts +19 -0
  17. package/dist/core/easy.js +117 -0
  18. package/dist/core/enrich.d.ts +30 -0
  19. package/dist/core/enrich.js +155 -0
  20. package/dist/core/llms.d.ts +11 -0
  21. package/dist/core/llms.js +71 -0
  22. package/dist/core/report.d.ts +15 -0
  23. package/dist/core/report.js +46 -0
  24. package/dist/core/resolve.d.ts +43 -0
  25. package/dist/core/resolve.js +204 -0
  26. package/dist/core/respond.d.ts +18 -0
  27. package/dist/core/respond.js +59 -0
  28. package/dist/core/sitemap.d.ts +31 -0
  29. package/dist/core/sitemap.js +140 -0
  30. package/dist/index.d.ts +14 -0
  31. package/dist/index.js +76 -0
  32. package/dist/next/dashboard.d.ts +14 -0
  33. package/dist/next/dashboard.js +56 -0
  34. package/dist/next/index.d.ts +42 -0
  35. package/dist/next/index.js +100 -0
  36. package/dist/next/route.d.ts +26 -0
  37. package/dist/next/route.js +167 -0
  38. package/dist/node/index.d.ts +8 -0
  39. package/dist/node/index.js +191 -0
  40. package/dist/proof/audit.d.ts +47 -0
  41. package/dist/proof/audit.js +253 -0
  42. package/dist/proof/bots.d.ts +24 -0
  43. package/dist/proof/bots.js +60 -0
  44. package/dist/proof/dashboard.d.ts +8 -0
  45. package/dist/proof/dashboard.js +77 -0
  46. package/dist/proof/hits.d.ts +18 -0
  47. package/dist/proof/hits.js +51 -0
  48. package/dist/proof/jsonl.d.ts +5 -0
  49. package/dist/proof/jsonl.js +80 -0
  50. package/dist/proof/stats.d.ts +39 -0
  51. package/dist/proof/stats.js +127 -0
  52. package/dist/refine/check.d.ts +17 -0
  53. package/dist/refine/check.js +134 -0
  54. package/dist/refine/extract.d.ts +7 -0
  55. package/dist/refine/extract.js +120 -0
  56. package/dist/refine/file-store.d.ts +6 -0
  57. package/dist/refine/file-store.js +87 -0
  58. package/dist/refine/model.d.ts +30 -0
  59. package/dist/refine/model.js +105 -0
  60. package/dist/refine/prompts.d.ts +49 -0
  61. package/dist/refine/prompts.js +178 -0
  62. package/dist/refine/refine.d.ts +38 -0
  63. package/dist/refine/refine.js +75 -0
  64. package/dist/refine/run.d.ts +52 -0
  65. package/dist/refine/run.js +66 -0
  66. package/dist/refine/types.d.ts +17 -0
  67. package/dist/refine/types.js +8 -0
  68. package/dist/wp/relve-agent-ready/includes/class-relve-ar-admin.php +363 -0
  69. package/dist/wp/relve-agent-ready/includes/class-relve-ar-converter.php +762 -0
  70. package/dist/wp/relve-agent-ready/includes/class-relve-ar-llms.php +192 -0
  71. package/dist/wp/relve-agent-ready/includes/class-relve-ar-markdown-builder.php +447 -0
  72. package/dist/wp/relve-agent-ready/includes/class-relve-ar-negotiation.php +334 -0
  73. package/dist/wp/relve-agent-ready/includes/class-relve-ar-response.php +226 -0
  74. package/dist/wp/relve-agent-ready/includes/class-relve-ar-router.php +421 -0
  75. package/dist/wp/relve-agent-ready/includes/class-relve-ar-settings.php +115 -0
  76. package/dist/wp/relve-agent-ready/includes/class-relve-ar-store.php +543 -0
  77. package/dist/wp/relve-agent-ready/includes/index.php +2 -0
  78. package/dist/wp/relve-agent-ready/index.php +2 -0
  79. package/dist/wp/relve-agent-ready/readme.txt +75 -0
  80. package/dist/wp/relve-agent-ready/relve-agent-ready.php +70 -0
  81. package/dist/wp/relve-agent-ready/uninstall.php +24 -0
  82. package/package.json +64 -6
package/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2026 Relve
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
package/README.md CHANGED
@@ -1,3 +1,338 @@
1
- # Temporary Holding Version
2
-
3
- This version is a temporary placeholder for this package. An operational version to replace this has been submitted for review and is awaiting a staged release.
1
+ # @relvehq/agent-ready
2
+
3
+ Make your site agent-ready. When an AI agent (ChatGPT, Claude, Perplexity,
4
+ Copilot…) asks for one of your pages as Markdown, it gets a clean, small
5
+ Markdown version instead of 50,000+ tokens of HTML. Browsers get exactly what
6
+ they got before.
7
+
8
+ - **Serve**: Markdown on `Accept: text/markdown`, on `<page>.md` and on
9
+ `?format=md`, plus a generated [`/llms.txt`](https://llmstxt.org). No AI
10
+ runs per request: it is plain code, in milliseconds.
11
+ - **Refine** (optional, with your own prompt files): an AI model writes a
12
+ better Markdown file for each page ahead of time, a script checks every
13
+ number and URL against the page,
14
+ and unchanged pages are skipped on the next run.
15
+ - **Proof**: a free checker that scores any site out of 100, and a dashboard
16
+ of which AI agents read which pages.
17
+
18
+ On a real tool page: raw HTML 97,944 tokens, a generic converter 4,618, a
19
+ refined file 1,695.
20
+
21
+ **Start here:** the onboarding guide at <https://relvehq.com/agent-ready>
22
+ (every stack, the WordPress plugin download, and how to test it).
23
+
24
+ ## Requirements
25
+
26
+ - Node.js 20 or newer
27
+ - For the Next.js adapter: Next.js 13.4+ with the App Router
28
+ - Anything else: the core is plain `Request` / `Response` (see "Other frameworks")
29
+
30
+ ## Quick start: one command
31
+
32
+ In your project's root:
33
+
34
+ ```
35
+ npx @relvehq/agent-ready init
36
+ ```
37
+
38
+ It detects Next.js, Node servers and WordPress, and sets up the one it finds:
39
+
40
+ | It finds | It does |
41
+ |---|---|
42
+ | `app/` or `src/app/` and `next` in `package.json` | writes the Next.js files (below) |
43
+ | `wp-config.php` or `wp-content/` | copies the bundled plugin to `wp-content/plugins/relve-agent-ready/`, then tells you to activate it and tick Enabled on Settings > Agent Ready (an existing copy is kept unless you add `--force`) |
44
+ | `express`, `connect`, `polka`, `fastify`, `@nestjs/core`, `h3` or `nitropack` in `package.json` | writes nothing; prints the exact lines for that framework and the env vars |
45
+ | none of these | prints what it looked for and the guide's URL, and exits 1 |
46
+
47
+ `--stack next|node|wordpress` skips detection; `--dry-run` shows the plan and
48
+ writes nothing. Step-by-step for every stack: [SETUP.md](./SETUP.md).
49
+
50
+ ### Next.js
51
+
52
+ ```
53
+ npm install @relvehq/agent-ready
54
+ npx agent-ready init
55
+ ```
56
+
57
+ `init` looks at your project (`app/` or `src/app/`, TypeScript or JavaScript)
58
+ and writes:
59
+
60
+ | File | What it holds |
61
+ |---|---|
62
+ | `agent-ready.config.ts` | `export default createAgentReady()`, smart defaults |
63
+ | `middleware.ts` | `export default withAgentReady(agentReady)` and the matcher (only when you have no middleware yet) |
64
+ | `app/%5F%5Fmd/[[...path]]/route.ts` | the internal route that builds the Markdown (`%5F` is `_`) |
65
+ | `.env.local` | `AGENT_READY_ENABLED=1` and `NEXT_PUBLIC_SITE_URL=http://localhost:3000` |
66
+
67
+ It never edits a file you already have. If you have a middleware, it prints
68
+ the two lines to add:
69
+
70
+ ```ts
71
+ import { withAgentReady } from "@relvehq/agent-ready/next";
72
+ import agentReady from "./agent-ready.config";
73
+ export default withAgentReady(agentReady, yourMiddleware);
74
+ // and add to your matcher: "/((?!_next/).+\\.md)", "/llms.txt"
75
+ ```
76
+
77
+ Running `init` again changes nothing; `--dry-run` shows the plan.
78
+
79
+ Check it with the dev server running:
80
+
81
+ ```
82
+ curl -i -H "Accept: text/markdown" http://localhost:3000/
83
+ curl -i http://localhost:3000/index.md
84
+ curl -i http://localhost:3000/llms.txt
85
+ ```
86
+
87
+ In production set `AGENT_READY_ENABLED=1` and `NEXT_PUBLIC_SITE_URL=https://your-site.com`
88
+ on your host. Without a site URL the package stays off (it never fails your build).
89
+
90
+ ### Node server and WordPress
91
+
92
+ For a Node server, `init` prints the lines for your framework (Express,
93
+ Connect, Polka, Nest: `app.use(...)`; Fastify through `@fastify/middie`;
94
+ Nitro and h3 through `fromNodeMiddleware`), and the two env vars:
95
+ `AGENT_READY_ENABLED=1` and `SITE_URL=https://your-site.com`. See "Other
96
+ frameworks" below. For WordPress, the plugin ships inside this package
97
+ (without its tests), so `init` needs no download.
98
+
99
+ ### What `createAgentReady()` works out on its own
100
+
101
+ | Setting | Default |
102
+ |---|---|
103
+ | `site` | the first set of `NEXT_PUBLIC_SITE_URL`, `SITE_URL`, `NEXT_PUBLIC_APP_URL`, `URL` (Netlify), `VERCEL_PROJECT_PRODUCTION_URL`, `VERCEL_URL` |
104
+ | `enabled` | `AGENT_READY_ENABLED` is `1` or `true` |
105
+ | `exclude` | `/api`, `/_next`, auth and admin paths, plus common private pages (account, checkout, cart, dashboard, settings, billing…) and yours; `excludeCommon: false` drops the common list |
106
+ | `llms` | `/llms.txt` built from your `sitemap.xml`; `llms: false` for none |
107
+ | `onHit` | sends each visit to a dashboard when `AGENT_READY_KEY` and `AGENT_READY_ENDPOINT` are set |
108
+
109
+ Anything you pass wins:
110
+
111
+ ```ts
112
+ export default createAgentReady({
113
+ exclude: ["/members"],
114
+ templates: { "/blog/:slug": async ({ params }) => renderPostMarkdown(params.slug) },
115
+ });
116
+ ```
117
+
118
+ ## How an agent asks
119
+
120
+ | Ask | Example |
121
+ |---|---|
122
+ | `Accept` header | `Accept: text/markdown`, preferred over (or tied with) `text/html` |
123
+ | `.md` URL | `/pricing.md`, `/index.md` for `/` |
124
+ | query | `/pricing?format=md` |
125
+
126
+ A browser's `Accept`, a bare `*/*`, or `text/markdown` with a lower q-value
127
+ than `text/html` is not a Markdown request. The user agent is never used to
128
+ choose what to serve: that would be cloaking.
129
+
130
+ ## How it works
131
+
132
+ 1. **Detect** (middleware, Edge): is this a Markdown request? If not, nothing changes.
133
+ 2. **Rewrite** to the internal route `/__md/<path>`; the public URL stays the same.
134
+ 3. **Resolve** (Node route), first hit wins:
135
+ 1. a **template** for the route (`"/blog/:slug"`), written from your data
136
+ 2. a **stored** file (`store.get(path)`), e.g. one written by `refine`
137
+ 3. **convert**: fetch the page's own HTML (public, no cookies) and turn its
138
+ main content into Markdown (Readability + turndown, GFM tables). Under 200
139
+ characters of real text is discarded.
140
+ 4. nothing usable: an `Accept` request gets the normal HTML page, a `.md`
141
+ request gets a 404
142
+ 4. **Enrich**: YAML front matter (title, canonical, source), facts from JSON-LD, token count.
143
+ 5. **Respond**:
144
+
145
+ ```
146
+ Content-Type: text/markdown; charset=utf-8
147
+ Vary: Accept
148
+ Link: <https://your-site.com/pricing>; rel="canonical"
149
+ X-Robots-Tag: noindex (search engines keep indexing the HTML page)
150
+ x-markdown-tokens: 314
151
+ ETag: W/"…" (If-None-Match → 304)
152
+ Cache-Control: see "Caching"
153
+ x-agent-ready-source: native | stored | convert
154
+ ```
155
+
156
+ 6. **Measure**: one `HitEvent` per request to `onHit`, fire-and-forget.
157
+
158
+ ## Caching behind a CDN
159
+
160
+ Most CDNs (CloudFront included) don't vary their cache on `Accept`, so:
161
+
162
+ - Responses negotiated by `Accept` use `negotiatedCacheControl`, default
163
+ `private, max-age=300`. A shared cache never stores them, so a browser is
164
+ never served Markdown.
165
+ - `.md`, `?format=md` and `llms.txt` are their own URLs and use `cacheControl`,
166
+ default `public, s-maxage=300, stale-while-revalidate=86400`.
167
+ - If the CDN already has the HTML page cached, an `Accept` request may get that
168
+ HTML. Safe, just not Markdown. `.md` URLs always work; reliable negotiation
169
+ needs `Accept` in the CDN cache key.
170
+
171
+ ## Refine: better Markdown, written ahead of time
172
+
173
+ ```
174
+ npx agent-ready refine --site https://your-site.com --prompts ./prompts --sitemap --limit 20 --dry-run
175
+ npx agent-ready refine --site https://your-site.com --prompts ./prompts --site-name "Your Name" --sitemap --limit 20
176
+ ```
177
+
178
+ For each page: fetch it, extract its text, links, JSON-LD and a fingerprint;
179
+ skip it if the fingerprint matches the saved file; otherwise fill the prompt,
180
+ call the model once, check the result, retry once with the problems listed,
181
+ and save `<out>/<path>.md` plus `<out>/<path>.json` (default out:
182
+ `.agent-ready/md`). `--dry-run` only reads pages: no model call, nothing written.
183
+
184
+ | Setting | |
185
+ |---|---|
186
+ | `OPENAI_API_KEY` | OpenAI, default model `gpt-4o` |
187
+ | `ANTHROPIC_API_KEY` | Claude, default model `claude-opus-5-5` |
188
+ | `AGENT_READY_MODEL` | any other model id, e.g. `gpt-4o-mini` |
189
+
190
+ Keys are read from `.env.local` and `.env`. Serve the files from the route
191
+ file (`fileStore` is Node only, so keep it out of `agent-ready.config.ts`,
192
+ which the Edge middleware imports):
193
+
194
+ ```ts
195
+ // app/%5F%5Fmd/[[...path]]/route.ts
196
+ import { createMarkdownRoute } from "@relvehq/agent-ready/next/route";
197
+ import { fileStore } from "@relvehq/agent-ready/refine/file-store";
198
+ import agentReady from "../../../agent-ready.config";
199
+ export const { GET, HEAD } = createMarkdownRoute({ ...agentReady, store: fileStore(".agent-ready/md") });
200
+ export const runtime = "nodejs";
201
+ export const dynamic = "force-dynamic";
202
+ ```
203
+
204
+ On serverless hosts (Vercel, Amplify) the folder must be bundled with the
205
+ route (`outputFileTracingIncludes`); see [SETUP.md](./SETUP.md).
206
+
207
+ **The check** rejects a file when a number or URL in it is not on the page, a
208
+ required section is missing, it has more or fewer than one H1, HTML tags, a
209
+ wrong fingerprint, or it is over the token budget. It cannot catch a reworded
210
+ claim, so read a sample before you switch on.
211
+
212
+ **The prompt.** The package ships none. Point `refine` at a folder of prompt
213
+ files with `--prompts <dir>` (several: `a,b`) or the `AGENT_READY_PROMPTS`
214
+ variable (`.env.local`, `.env` or the shell); without one it stops before
215
+ fetching anything. A prompt file is Markdown with `## SYSTEM`, `## USER`
216
+ (`{{PAGE_URL}}`, `{{PAGE_TEXT}}`, `{{PAGE_LINKS}}`, `{{JSON_LD}}`,
217
+ `{{SOURCE_HASH}}`) and a `## Settings` table (`page_type`, `version`,
218
+ `required_sections`, `token_budget`). A `page_type` of `page` takes every
219
+ path no other prompt claims; for it the code guesses the page's kind from its
220
+ URL and JSON-LD (home, product, pricing, article, docs, listing, event, about,
221
+ contact, legal, other) and passes the guess as `{{PAGE_KIND_HINT}}`.
222
+
223
+ ## Proof
224
+
225
+ ### Free checker
226
+
227
+ ```
228
+ npx agent-ready check https://any-site.com/pricing
229
+ npx agent-ready check any-site.com --json
230
+ ```
231
+
232
+ Read-only. Scores the site out of 100 (A to F): Markdown for `Accept` (25),
233
+ a `.md` URL (15), `/llms.txt` (15), robots.txt letting AI answer bots in (15),
234
+ a sitemap (10), JSON-LD (10), `Vary: Accept` (5), a canonical (5). Each failing
235
+ check says what to do, and it compares the tokens an agent reads today with
236
+ what agent-ready would serve. In code: `auditSite(url)`.
237
+
238
+ ### Dashboard
239
+
240
+ ```ts
241
+ // agent-ready.config.ts
242
+ import { createAgentReady, memoryHitStore } from "@relvehq/agent-ready";
243
+ export const hits = memoryHitStore();
244
+ export default createAgentReady({ hits });
245
+
246
+ // app/agent-ready-dashboard/route.ts
247
+ import { createDashboardRoute } from "@relvehq/agent-ready/next/dashboard";
248
+ import { hits } from "../../agent-ready.config";
249
+ export const { GET } = createDashboardRoute({ store: hits, site: "your-site.com" });
250
+ export const dynamic = "force-dynamic";
251
+ ```
252
+
253
+ Open `/agent-ready-dashboard?key=<AGENT_READY_DASHBOARD_KEY>` (add
254
+ `&format=json` for the data, `&days=7` for a shorter window). Without a key
255
+ configured the route answers 404. It shows visits per day, who is reading (AI
256
+ assistants, AI search, training bots, search engines), top pages, how agents
257
+ asked, where the Markdown came from, tokens served and response time.
258
+
259
+ A `HitStore` is two methods, `add` and `list`. `memoryHitStore()` suits a
260
+ long-running server; `jsonlHitStore(file)` (`@relvehq/agent-ready/proof/jsonl`)
261
+ writes a log that `npx agent-ready stats --log <file>` summarises. On
262
+ serverless hosts (Vercel, Amplify) memory and local files don't last between
263
+ requests: implement `HitStore` on your database.
264
+
265
+ ## Other frameworks
266
+
267
+ Express, Connect, Polka, Fastify (via `@fastify/middie`) or a plain `http`
268
+ server: one middleware. Mount it before your static files and routes:
269
+
270
+ ```ts
271
+ import express from "express";
272
+ import { createAgentReady } from "@relvehq/agent-ready";
273
+ import { agentReadyNode } from "@relvehq/agent-ready/node";
274
+
275
+ const app = express();
276
+ app.use(agentReadyNode(createAgentReady({ site: "https://your-site.com" })));
277
+ // app.use(express.static("public")); your routes...
278
+ ```
279
+
280
+ It answers Markdown requests and calls `next()` for everything else (and for
281
+ an `Accept` request when no Markdown is available, so the page's HTML is
282
+ served). Plain `http`: `http.createServer((req, res) => md(req, res, () => app(req, res)))`.
283
+
284
+ On other runtimes (Bun, Deno, Workers, Hono…) the core uses only `Request` and
285
+ `Response`. Detect, enrich and respond run anywhere; `resolveMarkdown` (its
286
+ convert step) needs Node, so on Edge-only runtimes use templates and a store
287
+ with `fallback: "none"`:
288
+
289
+ ```ts
290
+ import { defineAgentReady, wantsMarkdown, enrich, markdownResponse } from "@relvehq/agent-ready";
291
+ import { resolveMarkdown } from "@relvehq/agent-ready/core/resolve"; // Node only
292
+
293
+ const cfg = defineAgentReady({ site: "https://your-site.com", enabled: true });
294
+ const d = wantsMarkdown(request);
295
+ if (d.markdown) {
296
+ const r = await resolveMarkdown(cfg, { path: d.path, search: d.search, request });
297
+ if (r.doc) {
298
+ const { body, tokens } = enrich(r.doc, { canonical: cfg.site + d.path, sourceUrl: r.sourceUrl, source: r.source! });
299
+ return markdownResponse(body, { request, canonical: cfg.site + d.path, tokens, cacheControl: cfg.cacheControl });
300
+ }
301
+ }
302
+ ```
303
+
304
+ `@relvehq/agent-ready` and `@relvehq/agent-ready/next` are Edge-safe.
305
+ `/node`, `/next/route`, `/core/resolve`, `/core/convert` and `/refine/*` need Node.
306
+
307
+ ## Config reference (`defineAgentReady` / `createAgentReady`)
308
+
309
+ | Key | Default | Notes |
310
+ |---|---|---|
311
+ | `site` | required (`createAgentReady`: from env) | public origin, for canonicals and absolute links |
312
+ | `enabled` | `false` | boolean or `(request) => boolean` |
313
+ | `exclude` | `[]` | path prefixes or RegExps, added to the always-excluded list |
314
+ | `templates` | `{}` | `{ "/blog/:slug": fn }`, first matching pattern wins |
315
+ | `store` | `null` | `{ get(path) }` |
316
+ | `fallback` | `"convert"` | `"none"` serves only templates and stored files |
317
+ | `cacheControl` | `public, s-maxage=300, stale-while-revalidate=86400` | `.md`, `?format=md`, llms.txt |
318
+ | `negotiatedCacheControl` | `private, max-age=300` | `Accept` requests |
319
+ | `llms` | `null` (`createAgentReady`: from the sitemap) | `{ path, title, summary, details, entries }` |
320
+ | `onHit` | `null` | `(HitEvent) => void` |
321
+ | `internalPrefix` | `/__md` | rewrite target |
322
+ | `fetchTimeoutMs` | `8000` | page fetch for convert |
323
+ | `minChars` | `200` | quality gate for convert |
324
+
325
+ ## Commands
326
+
327
+ ```
328
+ agent-ready init [--stack next|node|wordpress] [--dry-run] [--force] [--cwd <dir>]
329
+ agent-ready check <url> [--json]
330
+ agent-ready refine --site <origin> (--paths /a,/b | --sitemap) --prompts <dir> [--site-name <name>]
331
+ [--out <dir>] [--limit <n>] [--force] [--concurrency <n>] [--dry-run]
332
+ agent-ready stats --log <hits.jsonl> [--days <n>] [--json]
333
+ ```
334
+
335
+ ## License
336
+
337
+ MIT © [Relve](https://relvehq.com). Built by the team behind Relve, the AI
338
+ tools and market intelligence platform.