@docsector/docsector-reader 0.12.3 β 0.13.0
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.
- package/README.md +58 -0
- package/bin/docsector.js +9 -1
- package/package.json +1 -1
- package/src/index.js +14 -1
- package/src/quasar.factory.js +46 -0
package/README.md
CHANGED
|
@@ -26,6 +26,7 @@ Transform Markdown content into beautiful, navigable documentation sites β wit
|
|
|
26
26
|
- π€ **LLM Bot Detection** β Automatically serves raw Markdown to known AI crawlers (GPTBot, ClaudeBot, PerplexityBot, GrokBot, and others)
|
|
27
27
|
- πΊοΈ **Sitemap Generation** β Automatic `sitemap.xml` generation at build time with all page URLs (requires `siteUrl` in config)
|
|
28
28
|
- π€ **AI-Friendly robots.txt** β Scaffold includes a `robots.txt` explicitly allowing 23 AI crawlers (GPTBot, ClaudeBot, PerplexityBot, GrokBot, etc.)
|
|
29
|
+
- π **Homepage Link Headers** β Auto-generated `Link` response headers for agent discovery (`service-doc`, `service-desc`, `describedby`) per RFC 8288 / RFC 9727
|
|
29
30
|
- π **MCP Server** β Auto-generated [MCP](https://modelcontextprotocol.io) server at `/mcp` for AI assistant integration (Claude Desktop, VS Code, etc.)
|
|
30
31
|
- π **llms.txt / llms-full.txt** β Auto-generated [llms.txt](https://llmstxt.org) index and full-content file for LLM discovery (requires `siteUrl` in config)
|
|
31
32
|
|
|
@@ -153,6 +154,56 @@ export default {
|
|
|
153
154
|
|
|
154
155
|
---
|
|
155
156
|
|
|
157
|
+
## π Link Headers (Agent Discovery)
|
|
158
|
+
|
|
159
|
+
Docsector Reader adds homepage `Link` response headers at build time for agent discovery, following [RFC 8288](https://www.rfc-editor.org/rfc/rfc8288) and [RFC 9727](https://www.rfc-editor.org/rfc/rfc9727#section-3).
|
|
160
|
+
|
|
161
|
+
Default relations emitted on homepage (`/` and `/index.html`):
|
|
162
|
+
|
|
163
|
+
- `rel="service-doc"` β `</>`
|
|
164
|
+
- `rel="service-desc"` β `</mcp>` (only when `mcp` is enabled)
|
|
165
|
+
- `rel="describedby"` β `</llms.txt>` (only when `siteUrl` is configured, i.e. `llms.txt` is generated)
|
|
166
|
+
|
|
167
|
+
Generated in:
|
|
168
|
+
|
|
169
|
+
- `dist/spa/_headers`
|
|
170
|
+
|
|
171
|
+
### Optional configuration
|
|
172
|
+
|
|
173
|
+
```javascript
|
|
174
|
+
export default {
|
|
175
|
+
// ...other config
|
|
176
|
+
|
|
177
|
+
linkHeaders: {
|
|
178
|
+
enabled: true,
|
|
179
|
+
serviceDoc: '/',
|
|
180
|
+
serviceDesc: '/mcp',
|
|
181
|
+
describedBy: '/llms.txt'
|
|
182
|
+
}
|
|
183
|
+
}
|
|
184
|
+
```
|
|
185
|
+
|
|
186
|
+
Set any target to `null` or `false` to disable that relation.
|
|
187
|
+
|
|
188
|
+
### Validate
|
|
189
|
+
|
|
190
|
+
```bash
|
|
191
|
+
npx docsector build
|
|
192
|
+
cat dist/spa/_headers
|
|
193
|
+
```
|
|
194
|
+
|
|
195
|
+
Or scan discoverability:
|
|
196
|
+
|
|
197
|
+
```bash
|
|
198
|
+
curl -X POST https://isitagentready.com/api/scan \
|
|
199
|
+
-H 'Content-Type: application/json' \
|
|
200
|
+
-d '{"url":"https://YOUR-SITE.com"}'
|
|
201
|
+
```
|
|
202
|
+
|
|
203
|
+
Check `checks.discoverability.linkHeaders.status` equals `"pass"`.
|
|
204
|
+
|
|
205
|
+
---
|
|
206
|
+
|
|
156
207
|
## οΏ½π Quick Start
|
|
157
208
|
|
|
158
209
|
### π¦ Install
|
|
@@ -288,6 +339,13 @@ export default {
|
|
|
288
339
|
editBaseUrl: 'https://github.com/org/repo/edit/main/src/pages'
|
|
289
340
|
},
|
|
290
341
|
|
|
342
|
+
linkHeaders: {
|
|
343
|
+
enabled: true,
|
|
344
|
+
serviceDoc: '/',
|
|
345
|
+
serviceDesc: '/mcp',
|
|
346
|
+
describedBy: '/llms.txt'
|
|
347
|
+
},
|
|
348
|
+
|
|
291
349
|
languages: [
|
|
292
350
|
{ image: '/images/flags/united-states-of-america.png', label: 'English (US)', value: 'en-US' },
|
|
293
351
|
{ image: '/images/flags/brazil.png', label: 'PortuguΓͺs (BR)', value: 'pt-BR' }
|
package/bin/docsector.js
CHANGED
|
@@ -23,7 +23,7 @@ const packageRoot = resolve(__dirname, '..')
|
|
|
23
23
|
const args = process.argv.slice(2)
|
|
24
24
|
const command = args[0]
|
|
25
25
|
|
|
26
|
-
const VERSION = '0.
|
|
26
|
+
const VERSION = '0.13.0'
|
|
27
27
|
|
|
28
28
|
const HELP = `
|
|
29
29
|
Docsector Reader v${VERSION}
|
|
@@ -133,6 +133,14 @@ export default {
|
|
|
133
133
|
// toolSuffix: 'my_docs'
|
|
134
134
|
// },
|
|
135
135
|
|
|
136
|
+
// @ Homepage Link headers for agent discovery (optional)
|
|
137
|
+
// linkHeaders: {
|
|
138
|
+
// enabled: true,
|
|
139
|
+
// serviceDoc: '/',
|
|
140
|
+
// serviceDesc: '/mcp',
|
|
141
|
+
// describedBy: '/llms.txt'
|
|
142
|
+
// },
|
|
143
|
+
|
|
136
144
|
// @ Languages
|
|
137
145
|
languages: [
|
|
138
146
|
{
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@docsector/docsector-reader",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.13.0",
|
|
4
4
|
"description": "A documentation rendering engine built with Vue 3, Quasar v2 and Vite. Transform Markdown into beautiful, navigable documentation sites.",
|
|
5
5
|
"productName": "Docsector Reader",
|
|
6
6
|
"author": "Rodrigo de Araujo Vieira",
|
package/src/index.js
CHANGED
|
@@ -44,6 +44,11 @@
|
|
|
44
44
|
* @param {Object} [config.mcp] - MCP (Model Context Protocol) server settings
|
|
45
45
|
* @param {string} config.mcp.serverName - Server name for MCP identification (e.g. 'my-docs')
|
|
46
46
|
* @param {string} config.mcp.toolSuffix - Suffix for tool names (e.g. 'my_docs' β search_my_docs)
|
|
47
|
+
* @param {Object} [config.linkHeaders] - Homepage Link headers for agent discovery
|
|
48
|
+
* @param {boolean} [config.linkHeaders.enabled=true] - Enables homepage Link headers generation
|
|
49
|
+
* @param {string|null|false} [config.linkHeaders.serviceDoc='/'] - Target URI for rel="service-doc"
|
|
50
|
+
* @param {string|null|false} [config.linkHeaders.serviceDesc='/mcp'] - Target URI for rel="service-desc" (only emitted when MCP is enabled)
|
|
51
|
+
* @param {string|null|false} [config.linkHeaders.describedBy='/llms.txt'] - Target URI for rel="describedby" (only emitted when llms.txt is generated)
|
|
47
52
|
* @returns {Object} Resolved Docsector configuration
|
|
48
53
|
*/
|
|
49
54
|
export function createDocsector (config = {}) {
|
|
@@ -83,7 +88,15 @@ export function createDocsector (config = {}) {
|
|
|
83
88
|
|
|
84
89
|
defaultLanguage: config.defaultLanguage || 'en-US',
|
|
85
90
|
|
|
86
|
-
mcp: config.mcp || null
|
|
91
|
+
mcp: config.mcp || null,
|
|
92
|
+
|
|
93
|
+
linkHeaders: {
|
|
94
|
+
enabled: true,
|
|
95
|
+
serviceDoc: '/',
|
|
96
|
+
serviceDesc: '/mcp',
|
|
97
|
+
describedBy: '/llms.txt',
|
|
98
|
+
...config.linkHeaders
|
|
99
|
+
}
|
|
87
100
|
}
|
|
88
101
|
}
|
|
89
102
|
|
package/src/quasar.factory.js
CHANGED
|
@@ -665,6 +665,52 @@ function createMarkdownBuildPlugin (projectRoot) {
|
|
|
665
665
|
}
|
|
666
666
|
console.log(`\x1b[36m[docsector]\x1b[0m Added _headers rule for .md files`)
|
|
667
667
|
|
|
668
|
+
// Add homepage Link headers for agent discovery (RFC 8288 / RFC 9727)
|
|
669
|
+
const linkHeadersConfig = config.linkHeaders || {}
|
|
670
|
+
const linkHeadersEnabled = linkHeadersConfig.enabled !== false
|
|
671
|
+
|
|
672
|
+
if (linkHeadersEnabled) {
|
|
673
|
+
const homepageLinks = []
|
|
674
|
+
|
|
675
|
+
const serviceDocHref = linkHeadersConfig.serviceDoc === undefined
|
|
676
|
+
? '/'
|
|
677
|
+
: linkHeadersConfig.serviceDoc
|
|
678
|
+
if (serviceDocHref) {
|
|
679
|
+
homepageLinks.push({ rel: 'service-doc', href: serviceDocHref })
|
|
680
|
+
}
|
|
681
|
+
|
|
682
|
+
const serviceDescHref = linkHeadersConfig.serviceDesc === undefined
|
|
683
|
+
? '/mcp'
|
|
684
|
+
: linkHeadersConfig.serviceDesc
|
|
685
|
+
if (config.mcp && serviceDescHref) {
|
|
686
|
+
homepageLinks.push({ rel: 'service-desc', href: serviceDescHref })
|
|
687
|
+
}
|
|
688
|
+
|
|
689
|
+
const describedByHref = linkHeadersConfig.describedBy === undefined
|
|
690
|
+
? '/llms.txt'
|
|
691
|
+
: linkHeadersConfig.describedBy
|
|
692
|
+
if (siteUrl && describedByHref) {
|
|
693
|
+
homepageLinks.push({ rel: 'describedby', href: describedByHref })
|
|
694
|
+
}
|
|
695
|
+
|
|
696
|
+
if (homepageLinks.length > 0) {
|
|
697
|
+
const linkLines = homepageLinks.map(({ rel, href }) => ` Link: <${href}>; rel="${rel}"`).join('\n')
|
|
698
|
+
const homepageRule = ['/','/index.html']
|
|
699
|
+
.map(path => `${path}\n${linkLines}`)
|
|
700
|
+
.join('\n\n') + '\n'
|
|
701
|
+
|
|
702
|
+
const currentHeaders = readFileSync(headersPath, 'utf-8')
|
|
703
|
+
const hasAgentLinks = currentHeaders.includes('rel="service-doc"')
|
|
704
|
+
|| currentHeaders.includes('rel="service-desc"')
|
|
705
|
+
|| currentHeaders.includes('rel="describedby"')
|
|
706
|
+
|
|
707
|
+
if (!hasAgentLinks) {
|
|
708
|
+
writeFileSync(headersPath, currentHeaders.trimEnd() + '\n\n' + homepageRule)
|
|
709
|
+
console.log(`\x1b[36m[docsector]\x1b[0m Added homepage Link headers for agent discovery`)
|
|
710
|
+
}
|
|
711
|
+
}
|
|
712
|
+
}
|
|
713
|
+
|
|
668
714
|
// Generate MCP server if configured
|
|
669
715
|
if (config.mcp) {
|
|
670
716
|
const mcpConfig = config.mcp
|