@nuxtjs/sitemap 2.4.0 → 5.0.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 (86) hide show
  1. package/README.md +60 -593
  2. package/dist/client/200.html +11 -0
  3. package/dist/client/404.html +11 -0
  4. package/dist/client/_nuxt/Icon.I3NdYkjC.css +1 -0
  5. package/dist/client/_nuxt/Icon.Y7HhHHAz.js +1 -0
  6. package/dist/client/_nuxt/IconCSS.6oz918NR.css +1 -0
  7. package/dist/client/_nuxt/IconCSS.Q-iLbQkL.js +1 -0
  8. package/dist/client/_nuxt/builds/latest.json +1 -0
  9. package/dist/client/_nuxt/builds/meta/4ef99937-9859-42d8-9d63-62e7809c4b65.json +1 -0
  10. package/dist/client/_nuxt/entry.EEjw95sW.js +15 -0
  11. package/dist/client/_nuxt/entry.UqhvG0ao.css +1 -0
  12. package/dist/client/_nuxt/error-404.DkXpI38i.css +1 -0
  13. package/dist/client/_nuxt/error-404.Loh33F4g.js +1 -0
  14. package/dist/client/_nuxt/error-500.SLhS9LVu.css +1 -0
  15. package/dist/client/_nuxt/error-500.m13OPw8F.js +1 -0
  16. package/dist/client/_nuxt/index.lSDm5iYo.js +1 -0
  17. package/dist/client/index.html +11 -0
  18. package/dist/module.cjs +5 -0
  19. package/dist/module.d.mts +350 -0
  20. package/dist/module.d.ts +350 -0
  21. package/dist/module.json +9 -0
  22. package/dist/module.mjs +994 -0
  23. package/dist/runtime/nitro/composables/asSitemapUrl.d.ts +2 -0
  24. package/dist/runtime/nitro/composables/asSitemapUrl.mjs +3 -0
  25. package/dist/runtime/nitro/composables/defineSitemapEventHandler.d.ts +3 -0
  26. package/dist/runtime/nitro/composables/defineSitemapEventHandler.mjs +2 -0
  27. package/dist/runtime/nitro/composables/getPathRobotConfigPolyfill.d.ts +4 -0
  28. package/dist/runtime/nitro/composables/getPathRobotConfigPolyfill.mjs +3 -0
  29. package/dist/runtime/nitro/kit.d.ts +3 -0
  30. package/dist/runtime/nitro/kit.mjs +23 -0
  31. package/dist/runtime/nitro/middleware/[sitemap]-sitemap.xml.d.ts +2 -0
  32. package/dist/runtime/nitro/middleware/[sitemap]-sitemap.xml.mjs +23 -0
  33. package/dist/runtime/nitro/plugins/compression.d.ts +2 -0
  34. package/dist/runtime/nitro/plugins/compression.mjs +8 -0
  35. package/dist/runtime/nitro/plugins/nuxt-content.d.ts +2 -0
  36. package/dist/runtime/nitro/plugins/nuxt-content.mjs +38 -0
  37. package/dist/runtime/nitro/plugins/warm-up.d.ts +2 -0
  38. package/dist/runtime/nitro/plugins/warm-up.mjs +23 -0
  39. package/dist/runtime/nitro/routes/__sitemap__/debug.d.ts +37 -0
  40. package/dist/runtime/nitro/routes/__sitemap__/debug.mjs +29 -0
  41. package/dist/runtime/nitro/routes/__sitemap__/nuxt-content-urls.d.ts +2 -0
  42. package/dist/runtime/nitro/routes/__sitemap__/nuxt-content-urls.mjs +6 -0
  43. package/dist/runtime/nitro/routes/sitemap.xml.d.ts +2 -0
  44. package/dist/runtime/nitro/routes/sitemap.xml.mjs +13 -0
  45. package/dist/runtime/nitro/routes/sitemap.xsl.d.ts +2 -0
  46. package/dist/runtime/nitro/routes/sitemap.xsl.mjs +229 -0
  47. package/dist/runtime/nitro/routes/sitemap_index.xml.d.ts +2 -0
  48. package/dist/runtime/nitro/routes/sitemap_index.xml.mjs +27 -0
  49. package/dist/runtime/nitro/sitemap/builder/sitemap-index.d.ts +2 -0
  50. package/dist/runtime/nitro/sitemap/builder/sitemap-index.mjs +86 -0
  51. package/dist/runtime/nitro/sitemap/builder/sitemap.d.ts +2 -0
  52. package/dist/runtime/nitro/sitemap/builder/sitemap.mjs +107 -0
  53. package/dist/runtime/nitro/sitemap/builder/xml.d.ts +4 -0
  54. package/dist/runtime/nitro/sitemap/builder/xml.mjs +83 -0
  55. package/dist/runtime/nitro/sitemap/nitro.d.ts +4 -0
  56. package/dist/runtime/nitro/sitemap/nitro.mjs +36 -0
  57. package/dist/runtime/nitro/sitemap/urlset/filter.d.ts +5 -0
  58. package/dist/runtime/nitro/sitemap/urlset/filter.mjs +50 -0
  59. package/dist/runtime/nitro/sitemap/urlset/i18n.d.ts +8 -0
  60. package/dist/runtime/nitro/sitemap/urlset/i18n.mjs +128 -0
  61. package/dist/runtime/nitro/sitemap/urlset/normalise.d.ts +3 -0
  62. package/dist/runtime/nitro/sitemap/urlset/normalise.mjs +77 -0
  63. package/dist/runtime/nitro/sitemap/urlset/sort.d.ts +2 -0
  64. package/dist/runtime/nitro/sitemap/urlset/sort.mjs +19 -0
  65. package/dist/runtime/nitro/sitemap/urlset/sources.d.ts +5 -0
  66. package/dist/runtime/nitro/sitemap/urlset/sources.mjs +82 -0
  67. package/dist/runtime/nitro/tsconfig.json +3 -0
  68. package/dist/runtime/nitro/utils.d.ts +4 -0
  69. package/dist/runtime/nitro/utils.mjs +13 -0
  70. package/dist/runtime/types.d.ts +355 -0
  71. package/dist/runtime/types.mjs +0 -0
  72. package/dist/runtime/utils-pure.d.ts +7 -0
  73. package/dist/runtime/utils-pure.mjs +32 -0
  74. package/dist/types.d.mts +18 -0
  75. package/dist/types.d.ts +18 -0
  76. package/package.json +80 -75
  77. package/CHANGELOG.md +0 -268
  78. package/LICENSE +0 -21
  79. package/lib/builder.js +0 -172
  80. package/lib/cache.js +0 -95
  81. package/lib/generator.js +0 -113
  82. package/lib/logger.js +0 -19
  83. package/lib/middleware.js +0 -195
  84. package/lib/module.js +0 -72
  85. package/lib/options.js +0 -135
  86. package/lib/routes.js +0 -55
@@ -0,0 +1,994 @@
1
+ import { useNuxt, loadNuxtModuleInstance, createResolver, addTemplate, extendPages, defineNuxtModule, useLogger, hasNuxtModule, getNuxtModuleVersion, hasNuxtModuleCompatibility, addServerImports, addServerPlugin, addServerHandler, findPath, addPrerenderRoutes } from '@nuxt/kit';
2
+ import { parseURL, withLeadingSlash, withBase, joinURL, withoutLeadingSlash } from 'ufo';
3
+ import { assertSiteConfig, installNuxtSiteConfig } from 'nuxt-site-config-kit';
4
+ import { defu, createDefu } from 'defu';
5
+ import { readPackageJSON } from 'pkg-types';
6
+ import { statSync, existsSync } from 'node:fs';
7
+ import { extname, relative, dirname } from 'pathe';
8
+ import { provider, env } from 'std-env';
9
+ import { mkdir, writeFile } from 'node:fs/promises';
10
+ import { join } from 'node:path';
11
+ import chalk from 'chalk';
12
+ import { build } from 'nitropack';
13
+ import { withSiteUrl } from 'nuxt-site-config-kit/urls';
14
+ import 'site-config-stack/urls';
15
+
16
+ async function resolveUrls(urls) {
17
+ if (typeof urls === "function")
18
+ urls = urls();
19
+ urls = await urls;
20
+ return urls;
21
+ }
22
+ function deepForEachPage(pages, callback, fullpath = null, depth = 0) {
23
+ pages.forEach((page) => {
24
+ let currentPath;
25
+ if (page.path.startsWith("/"))
26
+ currentPath = page.path;
27
+ else
28
+ currentPath = page.path === "" ? fullpath : `${fullpath.replace(/\/$/, "")}/${page.path}`;
29
+ callback(page, currentPath || "", depth);
30
+ if (page.children)
31
+ deepForEachPage(page.children, callback, currentPath, depth + 1);
32
+ });
33
+ }
34
+ function convertNuxtPagesToSitemapEntries(pages, config) {
35
+ const routesNameSeparator = config.routesNameSeparator || "___";
36
+ let flattenedPages = [];
37
+ deepForEachPage(
38
+ pages,
39
+ (page, loc, depth) => {
40
+ flattenedPages.push({ page, loc, depth });
41
+ }
42
+ );
43
+ flattenedPages = flattenedPages.filter((page) => !page.loc.includes(":")).filter((page, idx, arr) => {
44
+ return !arr.find((p) => {
45
+ return p.loc === page.loc && p.depth > page.depth;
46
+ });
47
+ }).map((p) => {
48
+ delete p.depth;
49
+ return p;
50
+ });
51
+ const pagesWithMeta = flattenedPages.map((p) => {
52
+ if (config.autoLastmod && p.page.file) {
53
+ try {
54
+ const stats = statSync(p.page.file);
55
+ if (stats?.mtime)
56
+ p.lastmod = stats.mtime;
57
+ } catch (e) {
58
+ }
59
+ }
60
+ if (p.page?.meta?.sitemap) {
61
+ p = defu(p.page.meta.sitemap, p);
62
+ }
63
+ return p;
64
+ });
65
+ const localeGroups = {};
66
+ pagesWithMeta.reduce((acc, e) => {
67
+ if (e.page.name?.includes(routesNameSeparator)) {
68
+ const [name, locale] = e.page.name.split(routesNameSeparator);
69
+ if (!acc[name])
70
+ acc[name] = [];
71
+ const { iso, code } = config.normalisedLocales.find((l) => l.code === locale) || { iso: locale, code: locale };
72
+ acc[name].push({ ...e, _sitemap: config.isI18nMapped ? iso || code : void 0, locale });
73
+ } else {
74
+ acc.default = acc.default || [];
75
+ acc.default.push(e);
76
+ }
77
+ return acc;
78
+ }, localeGroups);
79
+ return Object.entries(localeGroups).map(([locale, entries]) => {
80
+ if (locale === "default") {
81
+ return entries.map((e) => {
82
+ const [name] = (e.page?.name || "").split(routesNameSeparator);
83
+ if (localeGroups[name]?.some((a) => a.locale === config.defaultLocale))
84
+ return false;
85
+ const defaultLocale = config.normalisedLocales.find((l) => l.code === config.defaultLocale);
86
+ if (defaultLocale && config.isI18nMapped)
87
+ e._sitemap = defaultLocale.iso || defaultLocale.code;
88
+ delete e.page;
89
+ delete e.locale;
90
+ return { ...e };
91
+ }).filter(Boolean);
92
+ }
93
+ return entries.map((entry) => {
94
+ const alternatives = entries.map((entry2) => {
95
+ const hreflang = config.normalisedLocales.find((l) => l.code === entry2.locale)?.iso || entry2.locale;
96
+ return {
97
+ hreflang,
98
+ href: entry2.loc
99
+ };
100
+ });
101
+ const xDefault = entries.find((a) => a.locale === config.defaultLocale);
102
+ if (xDefault && alternatives.length) {
103
+ alternatives.push({
104
+ hreflang: "x-default",
105
+ href: xDefault.loc
106
+ });
107
+ }
108
+ const e = { ...entry };
109
+ if (config.isI18nMapped) {
110
+ const { iso, code } = config.normalisedLocales.find((l) => l.code === entry.locale) || { iso: locale, code: locale };
111
+ e._sitemap = iso || code;
112
+ }
113
+ delete e.page;
114
+ delete e.locale;
115
+ return {
116
+ ...e,
117
+ alternatives
118
+ };
119
+ });
120
+ }).filter(Boolean).flat();
121
+ }
122
+ function generateExtraRoutesFromNuxtConfig(nuxt = useNuxt()) {
123
+ const routeRules = Object.entries(nuxt.options.routeRules || {}).filter(([k, v]) => {
124
+ if (k.includes("*") || k.includes(".") || k.includes(":"))
125
+ return false;
126
+ if (typeof v.index === "boolean" && !v.index)
127
+ return false;
128
+ return !v.redirect;
129
+ }).map(([k]) => k);
130
+ const prerenderUrls = (nuxt.options.nitro.prerender?.routes || []).filter((p) => p && !extname(p) && !p.startsWith("/api/"));
131
+ return { routeRules, prerenderUrls };
132
+ }
133
+
134
+ async function getNuxtModuleOptions(module, nuxt = useNuxt()) {
135
+ const moduleMeta = (typeof module === "string" ? { name: module } : await module.getMeta?.()) || {};
136
+ const { nuxtModule } = await loadNuxtModuleInstance(module, nuxt);
137
+ let moduleEntry;
138
+ for (const m of nuxt.options.modules) {
139
+ if (Array.isArray(m) && m.length >= 2) {
140
+ const _module = m[0];
141
+ const _moduleEntryName = typeof _module === "string" ? _module : (await _module.getMeta?.())?.name || "";
142
+ if (_moduleEntryName === moduleMeta.name)
143
+ moduleEntry = m;
144
+ }
145
+ }
146
+ let inlineOptions = {};
147
+ if (moduleEntry)
148
+ inlineOptions = moduleEntry[1];
149
+ if (nuxtModule.getOptions)
150
+ return nuxtModule.getOptions(inlineOptions, nuxt);
151
+ return inlineOptions;
152
+ }
153
+ function extendTypes(module, template) {
154
+ const nuxt = useNuxt();
155
+ const { resolve } = createResolver(import.meta.url);
156
+ addTemplate({
157
+ filename: `module/${module}.d.ts`,
158
+ getContents: async () => {
159
+ const typesPath = relative(resolve(nuxt.options.rootDir, nuxt.options.buildDir, "module"), resolve("runtime/types"));
160
+ const s = await template({ typesPath });
161
+ return `// Generated by ${module}
162
+ ${s}
163
+ export {}
164
+ `;
165
+ }
166
+ });
167
+ nuxt.hooks.hook("prepare:types", ({ references }) => {
168
+ references.push({ path: resolve(nuxt.options.buildDir, `module/${module}.d.ts`) });
169
+ });
170
+ }
171
+ function createPagesPromise(nuxt = useNuxt()) {
172
+ return new Promise((resolve) => {
173
+ nuxt.hooks.hook("modules:done", () => {
174
+ extendPages(resolve);
175
+ });
176
+ });
177
+ }
178
+ function createNitroPromise(nuxt = useNuxt()) {
179
+ return new Promise((resolve) => {
180
+ nuxt.hooks.hook("nitro:init", (nitro) => {
181
+ resolve(nitro);
182
+ });
183
+ });
184
+ }
185
+ const autodetectableProviders = {
186
+ azure_static: "azure",
187
+ cloudflare_pages: "cloudflare-pages",
188
+ netlify: "netlify",
189
+ stormkit: "stormkit",
190
+ vercel: "vercel",
191
+ cleavr: "cleavr",
192
+ stackblitz: "stackblitz"
193
+ };
194
+ const autodetectableStaticProviders = {
195
+ netlify: "netlify-static",
196
+ vercel: "vercel-static"
197
+ };
198
+ function detectTarget(options = {}) {
199
+ return options?.static ? autodetectableStaticProviders[provider] : autodetectableProviders[provider];
200
+ }
201
+ function resolveNitroPreset(nitroConfig) {
202
+ if (provider === "stackblitz")
203
+ return "stackblitz";
204
+ let preset;
205
+ if (nitroConfig && nitroConfig?.preset)
206
+ preset = nitroConfig.preset;
207
+ if (!preset)
208
+ preset = env.NITRO_PRESET || detectTarget() || "node-server";
209
+ return preset.replace("_", "-");
210
+ }
211
+
212
+ function extractSitemapMetaFromHtml(html, options) {
213
+ options = options || { images: true, lastmod: true, alternatives: true };
214
+ const payload = {};
215
+ if (options?.images) {
216
+ const images = /* @__PURE__ */ new Set();
217
+ const mainRegex = /<main[^>]*>([\s\S]*?)<\/main>/;
218
+ const mainMatch = mainRegex.exec(html);
219
+ if (mainMatch?.[1] && mainMatch[1].includes("<img")) {
220
+ const imgRegex = /<img[^>]+src="([^">]+)"/g;
221
+ let match;
222
+ while ((match = imgRegex.exec(mainMatch[1])) !== null) {
223
+ if (match.index === imgRegex.lastIndex)
224
+ imgRegex.lastIndex++;
225
+ let url = match[1];
226
+ if (url.startsWith("/"))
227
+ url = withSiteUrl(url);
228
+ images.add(url);
229
+ }
230
+ }
231
+ if (images.size > 0)
232
+ payload.images = [...images].map((i) => ({ loc: i }));
233
+ }
234
+ if (options?.lastmod) {
235
+ const articleModifiedTime = html.match(/<meta[^>]+property="article:modified_time"[^>]+content="([^"]+)"/)?.[1] || html.match(/<meta[^>]+content="([^"]+)"[^>]+property="article:modified_time"/)?.[1];
236
+ if (articleModifiedTime)
237
+ payload.lastmod = articleModifiedTime;
238
+ }
239
+ if (options?.alternatives) {
240
+ const alternatives = (html.match(/<link[^>]+rel="alternate"[^>]+>/g) || []).map((a) => {
241
+ const href = a.match(/href="([^"]+)"/)?.[1];
242
+ const hreflang = a.match(/hreflang="([^"]+)"/)?.[1];
243
+ return { hreflang, href: parseURL(href).pathname };
244
+ }).filter((a) => a.hreflang && a.href);
245
+ if (alternatives?.length && (alternatives.length > 1 || alternatives?.[0].hreflang !== "x-default"))
246
+ payload.alternatives = alternatives;
247
+ }
248
+ return payload;
249
+ }
250
+
251
+ const merger = createDefu((obj, key, value) => {
252
+ if (Array.isArray(obj[key]) && Array.isArray(value))
253
+ obj[key] = Array.from(/* @__PURE__ */ new Set([...obj[key], ...value]));
254
+ return obj[key];
255
+ });
256
+ function mergeOnKey(arr, key) {
257
+ const res = {};
258
+ arr.forEach((item) => {
259
+ const k = item[key];
260
+ res[k] = merger(item, res[k] || {});
261
+ });
262
+ return Object.values(res);
263
+ }
264
+ function splitForLocales(path, locales) {
265
+ const prefix = withLeadingSlash(path).split("/")[1];
266
+ if (locales.includes(prefix))
267
+ return [prefix, path.replace(`/${prefix}`, "")];
268
+ return [null, path];
269
+ }
270
+
271
+ function formatPrerenderRoute(route) {
272
+ let str = ` \u251C\u2500 ${route.route} (${route.generateTimeMS}ms)`;
273
+ if (route.error) {
274
+ const errorColor = chalk[route.error.statusCode === 404 ? "yellow" : "red"];
275
+ const errorLead = "\u2514\u2500\u2500";
276
+ str += `
277
+ \u2502 ${errorLead} ${errorColor(route.error)}`;
278
+ }
279
+ return chalk.gray(str);
280
+ }
281
+ function includesSitemapRoot(sitemapName, routes) {
282
+ return routes.includes(`/sitemap.xml`) || routes.includes(`/${sitemapName}`) || routes.includes("/sitemap_index.xml");
283
+ }
284
+ function isNuxtGenerate(nuxt = useNuxt()) {
285
+ return nuxt.options._generate || nuxt.options.nitro.static || nuxt.options.nitro.preset === "static";
286
+ }
287
+ function setupPrerenderHandler(options, nuxt = useNuxt()) {
288
+ const prerenderedRoutes = nuxt.options.nitro.prerender?.routes || [];
289
+ const prerenderSitemap = isNuxtGenerate() || includesSitemapRoot(options.sitemapName, prerenderedRoutes);
290
+ if (nuxt.options.nitro.prerender?.routes)
291
+ nuxt.options.nitro.prerender.routes = nuxt.options.nitro.prerender.routes.filter((r) => r && !includesSitemapRoot(options.sitemapName, [r]));
292
+ nuxt.hooks.hook("nitro:init", async (nitro) => {
293
+ let prerenderer;
294
+ nitro.hooks.hook("prerender:init", async (_prerenderer) => {
295
+ prerenderer = _prerenderer;
296
+ assertSiteConfig("@nuxtjs/sitemap", {
297
+ url: "Required to generate absolute canonical URLs for your sitemap."
298
+ }, { throwError: false });
299
+ });
300
+ nitro.hooks.hook("prerender:generate", async (route) => {
301
+ const html = route.contents;
302
+ if (!route.fileName?.endsWith(".html") || !html)
303
+ return;
304
+ route._sitemap = defu(route._sitemap, {
305
+ loc: route.route
306
+ });
307
+ if (options.autoI18n && Object.keys(options.sitemaps).length > 1) {
308
+ const path = route.route;
309
+ const match = splitForLocales(path, options.autoI18n.locales.map((l) => l.code));
310
+ const locale = match[0] || options.autoI18n.defaultLocale;
311
+ if (options.isI18nMapped) {
312
+ const { code, iso } = options.autoI18n.locales.find((l) => l.code === locale) || { code: locale, iso: locale };
313
+ route._sitemap._sitemap = iso || code;
314
+ }
315
+ }
316
+ route._sitemap = defu(extractSitemapMetaFromHtml(html, {
317
+ images: options.discoverImages,
318
+ // TODO configurable?
319
+ lastmod: true,
320
+ alternatives: true
321
+ }), route._sitemap);
322
+ });
323
+ nitro.hooks.hook("prerender:done", async () => {
324
+ await build(prerenderer);
325
+ const routes = [];
326
+ if (options.debug)
327
+ routes.push("/__sitemap__/debug.json");
328
+ if (prerenderSitemap) {
329
+ routes.push(
330
+ options.isMultiSitemap ? "/sitemap_index.xml" : `/${Object.keys(options.sitemaps)[0]}`
331
+ );
332
+ }
333
+ for (const route of routes)
334
+ await prerenderRoute(nitro, route);
335
+ });
336
+ });
337
+ }
338
+ async function prerenderRoute(nitro, route) {
339
+ const start = Date.now();
340
+ const _route = { route, fileName: route };
341
+ const encodedRoute = encodeURI(route);
342
+ const res = await globalThis.$fetch.raw(
343
+ withBase(encodedRoute, nitro.options.baseURL),
344
+ {
345
+ headers: { "x-nitro-prerender": encodedRoute },
346
+ retry: nitro.options.prerender.retry,
347
+ retryDelay: nitro.options.prerender.retryDelay
348
+ }
349
+ );
350
+ const header = res.headers.get("x-nitro-prerender") || "";
351
+ const prerenderUrls = [
352
+ ...header.split(",").map((i) => i.trim()).map((i) => decodeURIComponent(i)).filter(Boolean)
353
+ ];
354
+ const filePath = join(nitro.options.output.publicDir, _route.fileName);
355
+ await mkdir(dirname(filePath), { recursive: true });
356
+ const data = res._data;
357
+ if (filePath.endsWith("json") || typeof data === "object")
358
+ await writeFile(filePath, JSON.stringify(data), "utf8");
359
+ else
360
+ await writeFile(filePath, data, "utf8");
361
+ _route.generateTimeMS = Date.now() - start;
362
+ nitro._prerenderedRoutes.push(_route);
363
+ nitro.logger.log(formatPrerenderRoute(_route));
364
+ for (const url of prerenderUrls)
365
+ await prerenderRoute(nitro, url);
366
+ }
367
+
368
+ const DEVTOOLS_UI_ROUTE = "/__sitemap__/devtools";
369
+ const DEVTOOLS_UI_LOCAL_PORT = 3030;
370
+ function setupDevToolsUI(options, resolve, nuxt = useNuxt()) {
371
+ const clientPath = resolve("./client");
372
+ const isProductionBuild = existsSync(clientPath);
373
+ if (isProductionBuild) {
374
+ nuxt.hook("vite:serverCreated", async (server) => {
375
+ const sirv = await import('sirv').then((r) => r.default || r);
376
+ server.middlewares.use(
377
+ DEVTOOLS_UI_ROUTE,
378
+ sirv(clientPath, { dev: true, single: true })
379
+ );
380
+ });
381
+ } else {
382
+ nuxt.hook("vite:extendConfig", (config) => {
383
+ config.server = config.server || {};
384
+ config.server.proxy = config.server.proxy || {};
385
+ config.server.proxy[DEVTOOLS_UI_ROUTE] = {
386
+ target: `http://localhost:${DEVTOOLS_UI_LOCAL_PORT}${DEVTOOLS_UI_ROUTE}`,
387
+ changeOrigin: true,
388
+ followRedirects: true,
389
+ rewrite: (path) => path.replace(DEVTOOLS_UI_ROUTE, "")
390
+ };
391
+ });
392
+ }
393
+ nuxt.hook("devtools:customTabs", (tabs) => {
394
+ tabs.push({
395
+ // unique identifier
396
+ name: "sitemap",
397
+ // title to display in the tab
398
+ title: "Sitemap",
399
+ // any icon from Iconify, or a URL to an image
400
+ icon: "carbon:load-balancer-application",
401
+ // iframe view
402
+ view: {
403
+ type: "iframe",
404
+ src: DEVTOOLS_UI_ROUTE
405
+ }
406
+ });
407
+ });
408
+ }
409
+
410
+ function normaliseDate(d) {
411
+ if (typeof d === "string") {
412
+ d = d.replace("Z", "");
413
+ d = d.replace(/\.\d+$/, "");
414
+ if (d.match(/^\d{4}-\d{2}-\d{2}T\d{2}:\d{2}:\d{2}$/) || d.match(/^\d{4}-\d{2}-\d{2}$/))
415
+ return d;
416
+ d = new Date(d);
417
+ if (Number.isNaN(d.getTime()))
418
+ return false;
419
+ }
420
+ const z = (n) => `0${n}`.slice(-2);
421
+ return `${d.getUTCFullYear()}-${z(d.getUTCMonth() + 1)}-${z(d.getUTCDate())}T${z(d.getUTCHours())}:${z(d.getUTCMinutes())}:${z(d.getUTCSeconds())}+00:00`;
422
+ }
423
+
424
+ function splitPathForI18nLocales(path, autoI18n) {
425
+ const locales = autoI18n.strategy === "prefix_except_default" ? autoI18n.locales.filter((l) => l.code !== autoI18n.defaultLocale) : autoI18n.locales;
426
+ if (typeof path !== "string" || path.startsWith("/api") || path.startsWith("/_nuxt"))
427
+ return path;
428
+ const match = splitForLocales(path, locales.map((l) => l.code));
429
+ const locale = match[0];
430
+ if (locale)
431
+ return path;
432
+ return [
433
+ path,
434
+ ...locales.map((l) => `/${l.code}${path}`)
435
+ ];
436
+ }
437
+ function generatePathForI18nPages({ localeCode, pageLocales, nuxtI18nConfig, forcedStrategy }) {
438
+ switch (forcedStrategy ?? nuxtI18nConfig.strategy) {
439
+ case "prefix_except_default":
440
+ case "prefix_and_default":
441
+ return localeCode === nuxtI18nConfig.defaultLocale ? pageLocales : joinURL(localeCode, pageLocales);
442
+ case "prefix":
443
+ return joinURL(localeCode, pageLocales);
444
+ case "no_prefix":
445
+ default:
446
+ return pageLocales;
447
+ }
448
+ }
449
+
450
+ function isValidFilter(filter) {
451
+ if (typeof filter === "string")
452
+ return true;
453
+ if (filter instanceof RegExp)
454
+ return true;
455
+ if (typeof filter === "object" && typeof filter.regex === "string")
456
+ return true;
457
+ return false;
458
+ }
459
+ function normalizeFilters(filters) {
460
+ return (filters || []).map((filter) => {
461
+ if (!isValidFilter(filter)) {
462
+ console.warn(`[@nuxtjs/sitemap] You have provided an invalid filter: ${filter}, ignoring.`);
463
+ return false;
464
+ }
465
+ return filter instanceof RegExp ? { regex: filter.toString() } : filter;
466
+ }).filter(Boolean);
467
+ }
468
+
469
+ const module = defineNuxtModule({
470
+ meta: {
471
+ name: "@nuxtjs/sitemap",
472
+ compatibility: {
473
+ nuxt: "^3.9.0",
474
+ bridge: false
475
+ },
476
+ configKey: "sitemap"
477
+ },
478
+ defaults: {
479
+ enabled: true,
480
+ credits: true,
481
+ cacheMaxAgeSeconds: 60 * 10,
482
+ // cache for 10 minutes
483
+ debug: false,
484
+ defaultSitemapsChunkSize: 1e3,
485
+ autoLastmod: false,
486
+ discoverImages: true,
487
+ dynamicUrlsApiEndpoint: "/api/_sitemap-urls",
488
+ urls: [],
489
+ sortEntries: true,
490
+ xsl: "/__sitemap__/style.xsl",
491
+ xslTips: true,
492
+ strictNuxtContentPaths: false,
493
+ runtimeCacheStorage: true,
494
+ sitemapName: "sitemap.xml",
495
+ // cacheControlHeader: 'max-age=600, must-revalidate',
496
+ defaults: {},
497
+ // index sitemap options filtering
498
+ include: [],
499
+ exclude: ["/_nuxt/**", "/api/**"],
500
+ // sources
501
+ sources: [],
502
+ excludeAppSources: [],
503
+ inferStaticPagesAsRoutes: true
504
+ },
505
+ async setup(config, nuxt) {
506
+ const { resolve } = createResolver(import.meta.url);
507
+ const { name, version } = await readPackageJSON(resolve("../package.json"));
508
+ const logger = useLogger(name);
509
+ logger.level = config.debug || nuxt.options.debug ? 4 : 3;
510
+ if (config.enabled === false) {
511
+ logger.debug("The module is disabled, skipping setup.");
512
+ return;
513
+ }
514
+ config.xslColumns = config.xslColumns || [
515
+ { label: "URL", width: "50%" },
516
+ { label: "Images", width: "25%", select: "count(image:image)" },
517
+ {
518
+ label: "Last Updated",
519
+ width: "25%",
520
+ select: "concat(substring(sitemap:lastmod,0,11),concat(' ', substring(sitemap:lastmod,12,5)),concat(' ', substring(sitemap:lastmod,20,6)))"
521
+ }
522
+ ];
523
+ if (config.autoLastmod) {
524
+ config.defaults = config.defaults || {};
525
+ config.defaults.lastmod = normaliseDate(/* @__PURE__ */ new Date());
526
+ }
527
+ await installNuxtSiteConfig();
528
+ const userGlobalSources = [
529
+ ...config.sources || []
530
+ ];
531
+ const appGlobalSources = [];
532
+ nuxt.options.nitro.storage = nuxt.options.nitro.storage || {};
533
+ if (config.runtimeCacheStorage && !nuxt.options.dev && typeof config.runtimeCacheStorage === "object")
534
+ nuxt.options.nitro.storage.sitemap = config.runtimeCacheStorage;
535
+ if (!config.sitemapName.endsWith("xml")) {
536
+ const newName = `${config.sitemapName.split(".")[0]}.xml`;
537
+ logger.warn(`You have provided a \`sitemapName\` that does not end with \`.xml\`. This is not supported by search engines, renaming to \`${newName}\`.`);
538
+ config.sitemapName = newName;
539
+ }
540
+ config.sitemapName = withoutLeadingSlash(config.sitemapName);
541
+ let usingMultiSitemaps = !!config.sitemaps;
542
+ let isI18nMapped = false;
543
+ let nuxtI18nConfig = {};
544
+ let resolvedAutoI18n = typeof config.autoI18n === "boolean" ? false : config.autoI18n || false;
545
+ const hasDisabledAutoI18n = typeof config.autoI18n === "boolean" && !config.autoI18n;
546
+ let normalisedLocales = [];
547
+ if (hasNuxtModule("@nuxtjs/i18n")) {
548
+ const i18nVersion = await getNuxtModuleVersion("@nuxtjs/i18n");
549
+ if (!await hasNuxtModuleCompatibility("@nuxtjs/i18n", ">=8"))
550
+ logger.warn(`You are using @nuxtjs/i18n v${i18nVersion}. For the best compatibility, please upgrade to @nuxtjs/i18n v8.0.0 or higher.`);
551
+ nuxtI18nConfig = await getNuxtModuleOptions("@nuxtjs/i18n") || {};
552
+ normalisedLocales = mergeOnKey((nuxtI18nConfig.locales || []).map((locale) => typeof locale === "string" ? { code: locale } : locale), "code");
553
+ const usingI18nPages = Object.keys(nuxtI18nConfig.pages || {}).length;
554
+ if (usingI18nPages && !hasDisabledAutoI18n) {
555
+ const i18nPagesSources = {
556
+ context: {
557
+ name: "@nuxtjs/i18n:pages",
558
+ description: "Generated from your i18n.pages config.",
559
+ tips: [
560
+ "You can disable this with `autoI18n: false`."
561
+ ]
562
+ },
563
+ urls: []
564
+ };
565
+ for (const pageLocales of Object.values(nuxtI18nConfig?.pages)) {
566
+ for (const localeCode in pageLocales) {
567
+ const locale = normalisedLocales.find((l) => l.code === localeCode);
568
+ if (!locale || !pageLocales[localeCode] || pageLocales[localeCode].includes("["))
569
+ continue;
570
+ const alternatives = Object.keys(pageLocales).map((l) => ({
571
+ hreflang: normalisedLocales.find((nl) => nl.code === l)?.iso || l,
572
+ href: generatePathForI18nPages({ localeCode: l, pageLocales: pageLocales[l], nuxtI18nConfig })
573
+ }));
574
+ if (alternatives.length && nuxtI18nConfig.defaultLocale && pageLocales[nuxtI18nConfig.defaultLocale])
575
+ alternatives.push({ hreflang: "x-default", href: generatePathForI18nPages({ localeCode: nuxtI18nConfig.defaultLocale, pageLocales: pageLocales[nuxtI18nConfig.defaultLocale], nuxtI18nConfig }) });
576
+ i18nPagesSources.urls.push({
577
+ _sitemap: locale.iso || locale.code,
578
+ loc: generatePathForI18nPages({ localeCode, pageLocales: pageLocales[localeCode], nuxtI18nConfig }),
579
+ alternatives
580
+ });
581
+ if (nuxtI18nConfig.strategy === "prefix_and_default" && localeCode === nuxtI18nConfig.defaultLocale) {
582
+ i18nPagesSources.urls.push({
583
+ _sitemap: locale.iso || locale.code,
584
+ loc: generatePathForI18nPages({ localeCode, pageLocales: pageLocales[localeCode], nuxtI18nConfig, forcedStrategy: "prefix" }),
585
+ alternatives
586
+ });
587
+ }
588
+ }
589
+ }
590
+ appGlobalSources.push(i18nPagesSources);
591
+ if (Array.isArray(config.excludeAppSources))
592
+ config.excludeAppSources.push("nuxt:pages");
593
+ } else {
594
+ if (!normalisedLocales.length)
595
+ logger.warn(`You are using @nuxtjs/i18n but have not configured any locales, this will cause issues with ${name}. Please configure \`locales\`.`);
596
+ }
597
+ const hasSetAutoI18n = typeof config.autoI18n === "object" && Object.keys(config.autoI18n).length;
598
+ const hasI18nConfigForAlternatives = nuxtI18nConfig.differentDomains || usingI18nPages || nuxtI18nConfig.strategy !== "no_prefix" && nuxtI18nConfig.locales;
599
+ if (!hasSetAutoI18n && !hasDisabledAutoI18n && hasI18nConfigForAlternatives) {
600
+ resolvedAutoI18n = {
601
+ differentDomains: nuxtI18nConfig.differentDomains,
602
+ defaultLocale: nuxtI18nConfig.defaultLocale,
603
+ locales: normalisedLocales,
604
+ strategy: nuxtI18nConfig.strategy
605
+ };
606
+ }
607
+ if (typeof config.sitemaps === "undefined" && !!resolvedAutoI18n && nuxtI18nConfig.strategy !== "no_prefix") {
608
+ config.sitemaps = { index: [] };
609
+ for (const locale of resolvedAutoI18n.locales) {
610
+ config.sitemaps[locale.iso || locale.code] = { includeAppSources: true };
611
+ }
612
+ isI18nMapped = true;
613
+ usingMultiSitemaps = true;
614
+ }
615
+ }
616
+ let needsRobotsPolyfill = true;
617
+ if (hasNuxtModule("nuxt-simple-robots")) {
618
+ const robotsVersion = await getNuxtModuleVersion("nuxt-simple-robots");
619
+ if (!await hasNuxtModuleCompatibility("nuxt-simple-robots", ">=4"))
620
+ logger.warn(`You are using nuxt-simple-robots v${robotsVersion}. For the best compatibility, please upgrade to nuxt-simple-robots v4.0.0 or higher.`);
621
+ else
622
+ needsRobotsPolyfill = false;
623
+ nuxt.hooks.hook("robots:config", (robotsConfig) => {
624
+ robotsConfig.sitemap.push(usingMultiSitemaps ? "/sitemap_index.xml" : `/${config.sitemapName}`);
625
+ });
626
+ }
627
+ if (needsRobotsPolyfill) {
628
+ addServerImports([{
629
+ name: "getPathRobotConfigPolyfill",
630
+ as: "getPathRobotConfig",
631
+ from: resolve("./runtime/nitro/composables/getPathRobotConfigPolyfill")
632
+ }]);
633
+ }
634
+ extendTypes(name, async ({ typesPath }) => {
635
+ return `
636
+ declare module 'nitropack' {
637
+ interface NitroRouteRules {
638
+ index?: boolean
639
+ sitemap?: import('${typesPath}').SitemapItemDefaults
640
+ }
641
+ interface NitroRouteConfig {
642
+ index?: boolean
643
+ sitemap?: import('${typesPath}').SitemapItemDefaults
644
+ }
645
+ interface NitroRuntimeHooks {
646
+ 'sitemap:resolved': (ctx: import('${typesPath}').SitemapRenderCtx) => void | Promise<void>
647
+ 'sitemap:output': (ctx: import('${typesPath}').SitemapOutputHookCtx) => void | Promise<void>
648
+ }
649
+ }
650
+ declare module 'vue-router' {
651
+ interface RouteMeta {
652
+ sitemap?: import('${typesPath}').SitemapItemDefaults
653
+ }
654
+ }
655
+ `;
656
+ });
657
+ const nitroPreset = resolveNitroPreset();
658
+ const prerenderedRoutes = nuxt.options.nitro.prerender?.routes || [];
659
+ const prerenderSitemap = isNuxtGenerate() || includesSitemapRoot(config.sitemapName, prerenderedRoutes);
660
+ const routeRules = {};
661
+ nuxt.options.nitro.routeRules = nuxt.options.nitro.routeRules || {};
662
+ if (prerenderSitemap) {
663
+ routeRules.headers = {
664
+ "Content-Type": "text/xml; charset=UTF-8",
665
+ "Cache-Control": config.cacheMaxAgeSeconds ? `public, max-age=${config.cacheMaxAgeSeconds}, must-revalidate` : "no-cache, no-store",
666
+ "X-Sitemap-Prerendered": (/* @__PURE__ */ new Date()).toISOString()
667
+ };
668
+ }
669
+ if (!nuxt.options.dev && !isNuxtGenerate() && config.cacheMaxAgeSeconds && config.runtimeCacheStorage !== false) {
670
+ routeRules[nitroPreset.includes("vercel") ? "isr" : "swr"] = config.cacheMaxAgeSeconds;
671
+ routeRules.cache = {
672
+ // handle multi-tenancy
673
+ swr: true,
674
+ maxAge: config.cacheMaxAgeSeconds,
675
+ varies: ["X-Forwarded-Host", "X-Forwarded-Proto", "Host"]
676
+ };
677
+ if (typeof config.runtimeCacheStorage === "object")
678
+ routeRules.cache.base = "sitemap";
679
+ }
680
+ nuxt.options.nitro.routeRules["/sitemap.xsl"] = {
681
+ headers: {
682
+ "Content-Type": "application/xslt+xml"
683
+ }
684
+ };
685
+ if (usingMultiSitemaps) {
686
+ nuxt.options.nitro.routeRules["/sitemap.xml"] = { redirect: "/sitemap_index.xml" };
687
+ nuxt.options.nitro.routeRules["/sitemap_index.xml"] = routeRules;
688
+ if (typeof config.sitemaps === "object") {
689
+ for (const k in config.sitemaps)
690
+ nuxt.options.nitro.routeRules[`/${k}-sitemap.xml`] = routeRules;
691
+ } else {
692
+ nuxt.options.nitro.routeRules[`/${config.sitemapName}`] = routeRules;
693
+ }
694
+ } else {
695
+ nuxt.options.nitro.routeRules[`/${config.sitemapName}`] = routeRules;
696
+ }
697
+ if (config.experimentalWarmUp)
698
+ addServerPlugin(resolve("./runtime/nitro/plugins/warm-up"));
699
+ if (config.experimentalCompression)
700
+ addServerPlugin(resolve("./runtime/nitro/plugins/compression"));
701
+ const isNuxtContentDocumentDriven = !!nuxt.options.content?.documentDriven || config.strictNuxtContentPaths;
702
+ if (hasNuxtModule("@nuxt/content")) {
703
+ addServerPlugin(resolve("./runtime/nitro/plugins/nuxt-content"));
704
+ addServerHandler({
705
+ route: "/__sitemap__/nuxt-content-urls.json",
706
+ handler: resolve("./runtime/nitro/routes/__sitemap__/nuxt-content-urls")
707
+ });
708
+ const tips = [];
709
+ if (nuxt.options.content?.documentDriven)
710
+ tips.push("Enabled because you're using `@nuxt/content` with `documentDriven: true`.");
711
+ else if (config.strictNuxtContentPaths)
712
+ tips.push("Enabled because you've set `config.strictNuxtContentPaths: true`.");
713
+ else
714
+ tips.push("You can provide a `sitemap` key in your markdown frontmatter to configure specific URLs. Make sure you include a `loc`.");
715
+ appGlobalSources.push({
716
+ context: {
717
+ name: "@nuxt/content:urls",
718
+ description: "Generated from your markdown files.",
719
+ tips
720
+ },
721
+ fetch: "/__sitemap__/nuxt-content-urls.json"
722
+ });
723
+ }
724
+ const hasLegacyDefaultApiSource = !!await findPath(resolve(nuxt.options.serverDir, "api/_sitemap-urls"));
725
+ if (
726
+ // make sure they didn't manually add it as a source
727
+ !config.sources?.includes("/api/_sitemap-urls") && (hasLegacyDefaultApiSource || config.dynamicUrlsApiEndpoint !== "/api/_sitemap-urls")
728
+ ) {
729
+ userGlobalSources.push({
730
+ context: {
731
+ name: "dynamicUrlsApiEndpoint",
732
+ description: "Generated from your dynamicUrlsApiEndpoint config.",
733
+ tips: [
734
+ "The `dynamicUrlsApiEndpoint` config is deprecated.",
735
+ hasLegacyDefaultApiSource ? "Consider renaming the `api/_sitemap-urls` file and add it the `sitemap.sources` config instead. This provides more explicit sitemap generation." : "Consider switching to using the `sitemap.sources` config which also supports fetch options."
736
+ ]
737
+ },
738
+ fetch: hasLegacyDefaultApiSource ? "/api/_sitemap-urls" : config.dynamicUrlsApiEndpoint
739
+ });
740
+ } else {
741
+ config.dynamicUrlsApiEndpoint = false;
742
+ }
743
+ const sitemaps = {};
744
+ if (usingMultiSitemaps) {
745
+ addServerHandler({
746
+ route: "/sitemap_index.xml",
747
+ handler: resolve("./runtime/nitro/routes/sitemap_index.xml")
748
+ });
749
+ sitemaps.index = {
750
+ sitemapName: "index",
751
+ _route: withBase("sitemap_index.xml", nuxt.options.app.baseURL || "/"),
752
+ // TODO better index support
753
+ // @ts-expect-error untyped
754
+ sitemaps: config.sitemaps.index || []
755
+ };
756
+ if (typeof config.sitemaps === "object") {
757
+ for (const sitemapName in config.sitemaps) {
758
+ if (sitemapName === "index")
759
+ continue;
760
+ addServerHandler({
761
+ route: `/${sitemapName}-sitemap.xml`,
762
+ handler: resolve("./runtime/nitro/middleware/[sitemap]-sitemap.xml")
763
+ });
764
+ const definition = config.sitemaps[sitemapName];
765
+ sitemaps[sitemapName] = defu(
766
+ {
767
+ sitemapName,
768
+ _route: withBase(`${sitemapName}-sitemap.xml`, nuxt.options.app.baseURL || "/"),
769
+ _hasSourceChunk: typeof definition.urls !== "undefined" || definition.sources?.length || !!definition.dynamicUrlsApiEndpoint
770
+ },
771
+ { ...definition, urls: void 0, sources: void 0 },
772
+ { include: config.include, exclude: config.exclude }
773
+ );
774
+ }
775
+ } else {
776
+ addServerHandler({
777
+ handler: resolve("./runtime/nitro/middleware/[sitemap]-sitemap.xml")
778
+ });
779
+ sitemaps.chunks = {
780
+ sitemapName: "chunks",
781
+ defaults: config.defaults,
782
+ include: config.include,
783
+ exclude: config.exclude,
784
+ includeAppSources: true
785
+ };
786
+ }
787
+ } else {
788
+ sitemaps[config.sitemapName] = {
789
+ sitemapName: config.sitemapName,
790
+ route: withBase(config.sitemapName, nuxt.options.app.baseURL || "/"),
791
+ // will contain the xml
792
+ defaults: config.defaults,
793
+ include: config.include,
794
+ exclude: config.exclude,
795
+ includeAppSources: true
796
+ };
797
+ }
798
+ if (resolvedAutoI18n && resolvedAutoI18n.locales && resolvedAutoI18n.strategy !== "no_prefix") {
799
+ const i18n = resolvedAutoI18n;
800
+ for (const sitemapName in sitemaps) {
801
+ if (["index", "chunks"].includes(sitemapName))
802
+ continue;
803
+ const sitemap = sitemaps[sitemapName];
804
+ sitemap.include = (sitemap.include || []).map((path) => splitPathForI18nLocales(path, i18n)).flat();
805
+ sitemap.exclude = (sitemap.exclude || []).map((path) => splitPathForI18nLocales(path, i18n)).flat();
806
+ }
807
+ }
808
+ for (const sitemapName in sitemaps) {
809
+ const sitemap = sitemaps[sitemapName];
810
+ sitemap.include = normalizeFilters(sitemap.include);
811
+ sitemap.exclude = normalizeFilters(sitemap.exclude);
812
+ }
813
+ const runtimeConfig = {
814
+ isI18nMapped,
815
+ sitemapName: config.sitemapName,
816
+ isMultiSitemap: usingMultiSitemaps,
817
+ excludeAppSources: config.excludeAppSources,
818
+ cacheMaxAgeSeconds: nuxt.options.dev ? 0 : config.cacheMaxAgeSeconds,
819
+ autoLastmod: config.autoLastmod,
820
+ defaultSitemapsChunkSize: config.defaultSitemapsChunkSize,
821
+ sortEntries: config.sortEntries,
822
+ debug: config.debug,
823
+ // needed for nuxt/content integration and prerendering
824
+ discoverImages: config.discoverImages,
825
+ /* @nuxt/content */
826
+ isNuxtContentDocumentDriven,
827
+ /* xsl styling */
828
+ xsl: config.xsl,
829
+ xslTips: config.xslTips,
830
+ xslColumns: config.xslColumns,
831
+ credits: config.credits,
832
+ version,
833
+ sitemaps
834
+ };
835
+ if (resolvedAutoI18n)
836
+ runtimeConfig.autoI18n = resolvedAutoI18n;
837
+ nuxt.options.runtimeConfig.sitemap = runtimeConfig;
838
+ if (config.debug || nuxt.options.dev) {
839
+ addServerHandler({
840
+ route: "/__sitemap__/debug.json",
841
+ handler: resolve("./runtime/nitro/routes/__sitemap__/debug")
842
+ });
843
+ setupDevToolsUI(config, resolve);
844
+ }
845
+ if (!config.inferStaticPagesAsRoutes)
846
+ config.excludeAppSources = true;
847
+ const imports = [
848
+ {
849
+ from: resolve("./runtime/nitro/composables/defineSitemapEventHandler"),
850
+ name: "defineSitemapEventHandler"
851
+ },
852
+ {
853
+ from: resolve("./runtime/nitro/composables/asSitemapUrl"),
854
+ name: "asSitemapUrl"
855
+ }
856
+ ];
857
+ addServerImports(imports);
858
+ const pagesPromise = createPagesPromise();
859
+ const nitroPromise = createNitroPromise();
860
+ let resolvedConfigUrls = false;
861
+ nuxt.hooks.hook("nitro:config", (nitroConfig) => {
862
+ nitroConfig.virtual["#sitemap/global-sources.mjs"] = async () => {
863
+ const { prerenderUrls, routeRules: routeRules2 } = generateExtraRoutesFromNuxtConfig();
864
+ const prerenderUrlsFinal = [
865
+ ...prerenderUrls,
866
+ ...((await nitroPromise)._prerenderedRoutes || []).filter((r) => (!r.fileName || r.fileName.endsWith(".html")) && !r.route.endsWith(".html") && !r.route.startsWith("/api/")).map((r) => r._sitemap)
867
+ ];
868
+ const pageSource = convertNuxtPagesToSitemapEntries(await pagesPromise, {
869
+ isI18nMapped,
870
+ autoLastmod: config.autoLastmod,
871
+ defaultLocale: nuxtI18nConfig.defaultLocale || "en",
872
+ strategy: nuxtI18nConfig.strategy || "no_prefix",
873
+ routesNameSeparator: nuxtI18nConfig.routesNameSeparator,
874
+ normalisedLocales
875
+ });
876
+ if (!resolvedConfigUrls) {
877
+ config.urls && userGlobalSources.push({
878
+ context: {
879
+ name: "sitemap:urls",
880
+ description: "Set with the `sitemap.urls` config."
881
+ },
882
+ urls: await resolveUrls(config.urls)
883
+ });
884
+ resolvedConfigUrls = true;
885
+ }
886
+ const globalSources = [
887
+ ...userGlobalSources.map((s) => {
888
+ if (typeof s === "string") {
889
+ return {
890
+ sourceType: "user",
891
+ fetch: s
892
+ };
893
+ }
894
+ s.sourceType = "user";
895
+ return s;
896
+ }),
897
+ ...(config.excludeAppSources === true ? [] : [
898
+ ...appGlobalSources,
899
+ {
900
+ context: {
901
+ name: "nuxt:pages",
902
+ description: "Generated from your static page files.",
903
+ tips: [
904
+ "Can be disabled with `{ excludeAppSources: ['nuxt:pages'] }`."
905
+ ]
906
+ },
907
+ urls: pageSource
908
+ },
909
+ {
910
+ context: {
911
+ name: "nuxt:route-rules",
912
+ description: "Generated from your route rules config.",
913
+ tips: [
914
+ "Can be disabled with `{ excludeAppSources: ['nuxt:route-rules'] }`."
915
+ ]
916
+ },
917
+ urls: routeRules2
918
+ },
919
+ {
920
+ context: {
921
+ name: "nuxt:prerender",
922
+ description: "Generated at build time when prerendering.",
923
+ tips: [
924
+ "Can be disabled with `{ excludeAppSources: ['nuxt:prerender'] }`."
925
+ ]
926
+ },
927
+ urls: prerenderUrlsFinal
928
+ }
929
+ ]).filter((s) => !config.excludeAppSources.includes(s.context.name) && (!!s.urls?.length || !!s.fetch)).map((s) => {
930
+ s.sourceType = "app";
931
+ return s;
932
+ })
933
+ ];
934
+ return `export const sources = ${JSON.stringify(globalSources, null, 4)}`;
935
+ };
936
+ const extraSitemapModules = typeof config.sitemaps == "object" ? Object.keys(config.sitemaps).filter((n) => n !== "index") : [];
937
+ const sitemapSources = {};
938
+ nitroConfig.virtual[`#sitemap/child-sources.mjs`] = async () => {
939
+ for (const sitemapName of extraSitemapModules) {
940
+ sitemapSources[sitemapName] = sitemapSources[sitemapName] || [];
941
+ const definition = config.sitemaps[sitemapName];
942
+ if (!sitemapSources[sitemapName].length) {
943
+ definition.urls && sitemapSources[sitemapName].push({
944
+ context: {
945
+ name: `sitemaps:${sitemapName}:urls`,
946
+ description: "Set with the `sitemap.urls` config."
947
+ },
948
+ urls: await resolveUrls(definition.urls)
949
+ });
950
+ definition.dynamicUrlsApiEndpoint && sitemapSources[sitemapName].push({
951
+ context: {
952
+ name: `${sitemapName}:dynamicUrlsApiEndpoint`,
953
+ description: `Generated from your ${sitemapName}:dynamicUrlsApiEndpoint config.`,
954
+ tips: [
955
+ `You should switch to using the \`sitemaps.${sitemapName}.sources\` config which also supports fetch options.`
956
+ ]
957
+ },
958
+ fetch: definition.dynamicUrlsApiEndpoint
959
+ });
960
+ sitemapSources[sitemapName].push(
961
+ ...(definition.sources || []).map((s) => {
962
+ if (typeof s === "string") {
963
+ return {
964
+ sourceType: "user",
965
+ fetch: s
966
+ };
967
+ }
968
+ s.sourceType = "user";
969
+ return s;
970
+ })
971
+ );
972
+ }
973
+ }
974
+ return `export const sources = ${JSON.stringify(sitemapSources, null, 4)}`;
975
+ };
976
+ });
977
+ if (config.xsl === "/__sitemap__/style.xsl") {
978
+ addServerHandler({
979
+ route: config.xsl,
980
+ handler: resolve("./runtime/nitro/routes/sitemap.xsl")
981
+ });
982
+ config.xsl = withBase(config.xsl, nuxt.options.app.baseURL);
983
+ if (prerenderSitemap)
984
+ addPrerenderRoutes(config.xsl);
985
+ }
986
+ addServerHandler({
987
+ route: `/${config.sitemapName}`,
988
+ handler: resolve("./runtime/nitro/routes/sitemap.xml")
989
+ });
990
+ setupPrerenderHandler(runtimeConfig);
991
+ }
992
+ });
993
+
994
+ export { module as default };