nuxt-ai-ready 0.5.0 → 0.5.2
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/dist/module.json
CHANGED
package/dist/module.mjs
CHANGED
|
@@ -374,11 +374,11 @@ function setupPrerenderHandler(pageDataPath, siteInfo, llmsTxtConfig) {
|
|
|
374
374
|
}));
|
|
375
375
|
const errorRoutes = entries.filter((e) => e._error).map((e) => e.route);
|
|
376
376
|
const jsonContent = JSON.stringify({ pages, errorRoutes });
|
|
377
|
-
const
|
|
378
|
-
await mkdir(
|
|
379
|
-
const
|
|
380
|
-
await writeFile(
|
|
381
|
-
logger.debug(`Wrote ${pages.length} pages to
|
|
377
|
+
const publicDataDir = join(nitro.options.output.publicDir, "__ai-ready");
|
|
378
|
+
await mkdir(publicDataDir, { recursive: true });
|
|
379
|
+
const publicJsonPath = join(publicDataDir, "pages.json");
|
|
380
|
+
await writeFile(publicJsonPath, jsonContent, "utf-8");
|
|
381
|
+
logger.debug(`Wrote ${pages.length} pages to __ai-ready/pages.json`);
|
|
382
382
|
}
|
|
383
383
|
}
|
|
384
384
|
const llmsStats = await prerenderRoute(nitro, "/llms.txt");
|
|
@@ -573,6 +573,8 @@ export {}
|
|
|
573
573
|
const prerenderCacheDir = join(nuxt.options.rootDir, "node_modules/.cache/nuxt-seo/ai-ready/routes");
|
|
574
574
|
const pageDataPath = join(nuxt.options.buildDir, ".data/ai-ready/page-data.jsonl");
|
|
575
575
|
nuxt.hooks.hook("nitro:config", (nitroConfig) => {
|
|
576
|
+
nitroConfig.experimental = nitroConfig.experimental || {};
|
|
577
|
+
nitroConfig.experimental.asyncContext = true;
|
|
576
578
|
nitroConfig.virtual = nitroConfig.virtual || {};
|
|
577
579
|
nitroConfig.virtual["#ai-ready-virtual/read-page-data.mjs"] = `
|
|
578
580
|
import { readFile } from 'node:fs/promises'
|
|
@@ -591,12 +593,6 @@ export async function readPageDataFromFilesystem() {
|
|
|
591
593
|
`;
|
|
592
594
|
nitroConfig.virtual["#ai-ready-virtual/page-data.mjs"] = `export const pages = []
|
|
593
595
|
export const errorRoutes = []`;
|
|
594
|
-
nitroConfig.serverAssets = nitroConfig.serverAssets || [];
|
|
595
|
-
nitroConfig.serverAssets.push({
|
|
596
|
-
baseName: "ai-ready-data",
|
|
597
|
-
dir: "./.nitro/ai-ready-data"
|
|
598
|
-
// Placeholder, actual data written during prerender
|
|
599
|
-
});
|
|
600
596
|
});
|
|
601
597
|
nuxt.options.runtimeConfig["nuxt-ai-ready"] = {
|
|
602
598
|
version: version || "0.0.0",
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { createError, eventHandler, setHeader } from "h3";
|
|
2
|
-
import { useRuntimeConfig
|
|
2
|
+
import { useRuntimeConfig } from "nitropack/runtime";
|
|
3
3
|
import { getErrorRoutes, getPages, getPagesList } from "../utils/pageData.js";
|
|
4
4
|
export default eventHandler(async (event) => {
|
|
5
5
|
const runtimeConfig = useRuntimeConfig(event)["nuxt-ai-ready"];
|
|
@@ -19,16 +19,16 @@ export default eventHandler(async (event) => {
|
|
|
19
19
|
} else {
|
|
20
20
|
mode = "production";
|
|
21
21
|
}
|
|
22
|
-
const pages = await getPages();
|
|
23
|
-
const pagesList = await getPagesList();
|
|
24
|
-
const errorRoutes = await getErrorRoutes();
|
|
22
|
+
const pages = await getPages(event);
|
|
23
|
+
const pagesList = await getPagesList(event);
|
|
24
|
+
const errorRoutes = await getErrorRoutes(event);
|
|
25
25
|
let source;
|
|
26
26
|
if (isDev) {
|
|
27
27
|
source = "empty (dev mode returns empty Map)";
|
|
28
28
|
} else if (isPrerender) {
|
|
29
29
|
source = "#ai-ready-virtual/read-page-data.mjs (reads from filesystem)";
|
|
30
30
|
} else {
|
|
31
|
-
source = "
|
|
31
|
+
source = "fetch('/__ai-ready/pages.json') (public directory)";
|
|
32
32
|
}
|
|
33
33
|
let pageDataModuleInfo = { available: false, pagesCount: 0, errorRoutesCount: 0 };
|
|
34
34
|
let readPageDataModuleInfo = { available: false, note: "" };
|
|
@@ -51,12 +51,28 @@ export default eventHandler(async (event) => {
|
|
|
51
51
|
} catch {
|
|
52
52
|
readPageDataModuleInfo = { available: false, note: "Module not available" };
|
|
53
53
|
}
|
|
54
|
-
|
|
55
|
-
|
|
54
|
+
let publicData = null;
|
|
55
|
+
let jsonFileSource = "fetch('/__ai-ready/pages.json')";
|
|
56
|
+
const cfEnv = event.context?.cloudflare?.env;
|
|
57
|
+
if (cfEnv?.ASSETS?.fetch) {
|
|
58
|
+
try {
|
|
59
|
+
const response = await cfEnv.ASSETS.fetch(new Request("https://assets.local/__ai-ready/pages.json"));
|
|
60
|
+
if (response.ok) {
|
|
61
|
+
publicData = await response.json();
|
|
62
|
+
jsonFileSource = "env.ASSETS.fetch('/__ai-ready/pages.json')";
|
|
63
|
+
}
|
|
64
|
+
} catch {
|
|
65
|
+
}
|
|
66
|
+
}
|
|
67
|
+
if (!publicData) {
|
|
68
|
+
publicData = await globalThis.$fetch("/__ai-ready/pages.json", {
|
|
69
|
+
baseURL: "/"
|
|
70
|
+
}).catch(() => null);
|
|
71
|
+
}
|
|
56
72
|
const jsonFileStatus = {
|
|
57
|
-
available: !!
|
|
58
|
-
pageCount:
|
|
59
|
-
source:
|
|
73
|
+
available: !!publicData,
|
|
74
|
+
pageCount: publicData?.pages?.length ?? 0,
|
|
75
|
+
source: jsonFileSource
|
|
60
76
|
};
|
|
61
77
|
const issues = [];
|
|
62
78
|
const suggestions = [];
|
|
@@ -65,10 +81,10 @@ export default eventHandler(async (event) => {
|
|
|
65
81
|
suggestions.push("Run `nuxi generate` or `nuxi build --prerender` to generate page data");
|
|
66
82
|
} else if (mode === "production" && pages.size === 0) {
|
|
67
83
|
if (!jsonFileStatus.available) {
|
|
68
|
-
issues.push("Production mode with no page data -
|
|
84
|
+
issues.push("Production mode with no page data - /__ai-ready/pages.json not found");
|
|
69
85
|
suggestions.push("Run `nuxi generate` or `nuxi build --prerender` to generate the page data");
|
|
70
86
|
} else {
|
|
71
|
-
issues.push("
|
|
87
|
+
issues.push("pages.json exists but returned empty page data");
|
|
72
88
|
suggestions.push("Check if pages were prerendered correctly");
|
|
73
89
|
}
|
|
74
90
|
} else if (mode === "prerender" && pages.size === 0) {
|
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import type { H3Event } from 'h3';
|
|
1
2
|
/** Page entry from virtual module */
|
|
2
3
|
export interface PageEntry {
|
|
3
4
|
route: string;
|
|
@@ -18,8 +19,8 @@ export interface PageListItem {
|
|
|
18
19
|
headings?: string;
|
|
19
20
|
}
|
|
20
21
|
/** Read page data - returns page data indexed by route */
|
|
21
|
-
export declare function getPages(): Promise<Map<string, PageEntry>>;
|
|
22
|
+
export declare function getPages(event?: H3Event): Promise<Map<string, PageEntry>>;
|
|
22
23
|
/** Get error routes detected during prerender */
|
|
23
|
-
export declare function getErrorRoutes(): Promise<Set<string>>;
|
|
24
|
+
export declare function getErrorRoutes(event?: H3Event): Promise<Set<string>>;
|
|
24
25
|
/** Get pages as flat list for MCP consumption */
|
|
25
|
-
export declare function getPagesList(): Promise<PageListItem[]>;
|
|
26
|
+
export declare function getPagesList(event?: H3Event): Promise<PageListItem[]>;
|
|
@@ -1,20 +1,29 @@
|
|
|
1
|
-
import {
|
|
2
|
-
|
|
1
|
+
import { useEvent } from "nitropack/runtime";
|
|
2
|
+
function getEventFromContext(providedEvent) {
|
|
3
|
+
if (providedEvent)
|
|
4
|
+
return providedEvent;
|
|
5
|
+
try {
|
|
6
|
+
return useEvent();
|
|
7
|
+
} catch {
|
|
8
|
+
return void 0;
|
|
9
|
+
}
|
|
10
|
+
}
|
|
11
|
+
export async function getPages(event) {
|
|
3
12
|
if (import.meta.dev)
|
|
4
13
|
return /* @__PURE__ */ new Map();
|
|
5
14
|
if (import.meta.prerender)
|
|
6
15
|
return (await readPrerenderedData()).pages;
|
|
7
|
-
return (await readServerAssets()).pages;
|
|
16
|
+
return (await readServerAssets(getEventFromContext(event))).pages;
|
|
8
17
|
}
|
|
9
|
-
export async function getErrorRoutes() {
|
|
18
|
+
export async function getErrorRoutes(event) {
|
|
10
19
|
if (import.meta.dev)
|
|
11
20
|
return /* @__PURE__ */ new Set();
|
|
12
21
|
if (import.meta.prerender)
|
|
13
22
|
return (await readPrerenderedData()).errorRoutes;
|
|
14
|
-
return (await readServerAssets()).errorRoutes;
|
|
23
|
+
return (await readServerAssets(getEventFromContext(event))).errorRoutes;
|
|
15
24
|
}
|
|
16
|
-
export async function getPagesList() {
|
|
17
|
-
const pages = await getPages();
|
|
25
|
+
export async function getPagesList(event) {
|
|
26
|
+
const pages = await getPages(event);
|
|
18
27
|
return Array.from(pages.values()).map((p) => ({
|
|
19
28
|
route: p.route,
|
|
20
29
|
title: p.title || p.route,
|
|
@@ -22,9 +31,23 @@ export async function getPagesList() {
|
|
|
22
31
|
headings: p.headings || void 0
|
|
23
32
|
}));
|
|
24
33
|
}
|
|
25
|
-
async function readServerAssets() {
|
|
26
|
-
|
|
27
|
-
const
|
|
34
|
+
async function readServerAssets(event) {
|
|
35
|
+
let data = null;
|
|
36
|
+
const cfEnv = event?.context?.cloudflare?.env;
|
|
37
|
+
if (cfEnv?.ASSETS?.fetch) {
|
|
38
|
+
try {
|
|
39
|
+
const response = await cfEnv.ASSETS.fetch(new Request("https://assets.local/__ai-ready/pages.json"));
|
|
40
|
+
if (response.ok) {
|
|
41
|
+
data = await response.json();
|
|
42
|
+
}
|
|
43
|
+
} catch {
|
|
44
|
+
}
|
|
45
|
+
}
|
|
46
|
+
if (!data) {
|
|
47
|
+
data = await globalThis.$fetch("/__ai-ready/pages.json", {
|
|
48
|
+
baseURL: "/"
|
|
49
|
+
}).catch(() => null);
|
|
50
|
+
}
|
|
28
51
|
if (!data)
|
|
29
52
|
return { pages: /* @__PURE__ */ new Map(), errorRoutes: /* @__PURE__ */ new Set() };
|
|
30
53
|
return {
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "nuxt-ai-ready",
|
|
3
3
|
"type": "module",
|
|
4
|
-
"version": "0.5.
|
|
4
|
+
"version": "0.5.2",
|
|
5
5
|
"description": "Best practice AI & LLM discoverability for Nuxt sites.",
|
|
6
6
|
"author": {
|
|
7
7
|
"name": "Harlan Wilton",
|
|
@@ -65,6 +65,8 @@
|
|
|
65
65
|
"@nuxtjs/sitemap": "7.5.0",
|
|
66
66
|
"@vitest/coverage-v8": "^4.0.16",
|
|
67
67
|
"@vueuse/nuxt": "^14.1.0",
|
|
68
|
+
"agents": "^0.3.0",
|
|
69
|
+
"ai": "^6.0.3",
|
|
68
70
|
"better-sqlite3": "^12.5.0",
|
|
69
71
|
"bumpp": "^10.3.2",
|
|
70
72
|
"eslint": "^9.39.2",
|