@serwist/next 9.5.7 → 9.5.9

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 (87) hide show
  1. package/dist/chunks/schema-BhRhcBIb.js +22 -0
  2. package/dist/chunks/schema-BhRhcBIb.js.map +1 -0
  3. package/dist/index.config.d.mts +50 -0
  4. package/dist/index.config.d.mts.map +1 -0
  5. package/dist/index.config.mjs +89 -0
  6. package/dist/index.config.mjs.map +1 -0
  7. package/dist/index.d.mts +111 -0
  8. package/dist/index.d.mts.map +1 -0
  9. package/dist/index.mjs +242 -0
  10. package/dist/index.mjs.map +1 -0
  11. package/dist/index.react.d.mts +41 -0
  12. package/dist/index.react.d.mts.map +1 -0
  13. package/dist/index.react.mjs +138 -0
  14. package/dist/index.react.mjs.map +1 -0
  15. package/dist/index.schema.d.mts +94 -0
  16. package/dist/index.schema.d.mts.map +1 -0
  17. package/dist/index.schema.mjs +2 -0
  18. package/dist/index.worker.d.mts +18 -0
  19. package/dist/index.worker.d.mts.map +1 -0
  20. package/dist/index.worker.mjs +227 -0
  21. package/dist/index.worker.mjs.map +1 -0
  22. package/dist/sw-entry-worker.d.mts +11 -0
  23. package/dist/sw-entry-worker.d.mts.map +1 -0
  24. package/dist/sw-entry-worker.mjs +25 -0
  25. package/dist/sw-entry-worker.mjs.map +1 -0
  26. package/dist/sw-entry.d.mts +9 -0
  27. package/dist/sw-entry.d.mts.map +1 -0
  28. package/dist/sw-entry.mjs +37 -0
  29. package/dist/sw-entry.mjs.map +1 -0
  30. package/package.json +40 -38
  31. package/src/index.react.tsx +2 -2
  32. package/src/index.ts +2 -2
  33. package/src/lib/config/utils.ts +3 -2
  34. package/dist/chunks/schema.js +0 -24
  35. package/dist/index.config.d.ts +0 -36
  36. package/dist/index.config.d.ts.map +0 -1
  37. package/dist/index.config.js +0 -118
  38. package/dist/index.d.ts +0 -13
  39. package/dist/index.d.ts.map +0 -1
  40. package/dist/index.js +0 -285
  41. package/dist/index.react.d.ts +0 -25
  42. package/dist/index.react.d.ts.map +0 -1
  43. package/dist/index.react.js +0 -88
  44. package/dist/index.schema.d.ts +0 -3
  45. package/dist/index.schema.d.ts.map +0 -1
  46. package/dist/index.schema.js +0 -4
  47. package/dist/index.worker.d.ts +0 -14
  48. package/dist/index.worker.d.ts.map +0 -1
  49. package/dist/index.worker.js +0 -261
  50. package/dist/internal-types.d.ts +0 -15
  51. package/dist/internal-types.d.ts.map +0 -1
  52. package/dist/lib/config/constants.d.ts +0 -2
  53. package/dist/lib/config/constants.d.ts.map +0 -1
  54. package/dist/lib/config/types.d.ts +0 -11
  55. package/dist/lib/config/types.d.ts.map +0 -1
  56. package/dist/lib/config/utils.d.ts +0 -3
  57. package/dist/lib/config/utils.d.ts.map +0 -1
  58. package/dist/lib/context.d.ts +0 -7
  59. package/dist/lib/context.d.ts.map +0 -1
  60. package/dist/lib/find-first-truthy.d.ts +0 -8
  61. package/dist/lib/find-first-truthy.d.ts.map +0 -1
  62. package/dist/lib/get-content-hash.d.ts +0 -3
  63. package/dist/lib/get-content-hash.d.ts.map +0 -1
  64. package/dist/lib/get-file-hash.d.ts +0 -3
  65. package/dist/lib/get-file-hash.d.ts.map +0 -1
  66. package/dist/lib/get-package-version.d.ts +0 -7
  67. package/dist/lib/get-package-version.d.ts.map +0 -1
  68. package/dist/lib/index.d.ts +0 -7
  69. package/dist/lib/index.d.ts.map +0 -1
  70. package/dist/lib/load-tsconfig.d.ts +0 -3
  71. package/dist/lib/load-tsconfig.d.ts.map +0 -1
  72. package/dist/lib/logger.d.ts +0 -7
  73. package/dist/lib/logger.d.ts.map +0 -1
  74. package/dist/lib/schema.d.ts +0 -90
  75. package/dist/lib/schema.d.ts.map +0 -1
  76. package/dist/lib/types.d.ts +0 -95
  77. package/dist/lib/types.d.ts.map +0 -1
  78. package/dist/lib/validator.d.ts +0 -3
  79. package/dist/lib/validator.d.ts.map +0 -1
  80. package/dist/sw-entry-worker.d.ts +0 -8
  81. package/dist/sw-entry-worker.d.ts.map +0 -1
  82. package/dist/sw-entry-worker.js +0 -33
  83. package/dist/sw-entry.d.ts +0 -7
  84. package/dist/sw-entry.d.ts.map +0 -1
  85. package/dist/sw-entry.js +0 -43
  86. package/dist/utils.d.ts +0 -4
  87. package/dist/utils.d.ts.map +0 -1
@@ -0,0 +1,22 @@
1
+ import { requiredSwDestPartial } from "@serwist/build/schema";
2
+ import { z } from "zod";
3
+ import { injectManifestOptions } from "@serwist/webpack-plugin/schema";
4
+ //#region src/lib/schema.ts
5
+ const injectPartial = z.strictObject({
6
+ cacheOnNavigation: z.boolean().default(false),
7
+ disable: z.boolean().default(false),
8
+ register: z.boolean().default(true),
9
+ reloadOnOnline: z.boolean().default(true),
10
+ scope: z.string().optional(),
11
+ swUrl: z.string().default("/sw.js"),
12
+ globPublicPatterns: z.array(z.string()).default(["**/*"])
13
+ });
14
+ const injectManifestOptions$1 = z.strictObject({
15
+ ...injectManifestOptions.shape,
16
+ ...requiredSwDestPartial.shape,
17
+ ...injectPartial.shape
18
+ }).omit({ disablePrecacheManifest: true });
19
+ //#endregion
20
+ export { injectPartial as n, injectManifestOptions$1 as t };
21
+
22
+ //# sourceMappingURL=schema-BhRhcBIb.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"schema-BhRhcBIb.js","names":["injectManifestOptions","webpackInjectManifestOptions"],"sources":["../../src/lib/schema.ts"],"sourcesContent":["import { requiredSwDestPartial } from \"@serwist/build/schema\";\nimport { injectManifestOptions as webpackInjectManifestOptions } from \"@serwist/webpack-plugin/schema\";\nimport { z } from \"zod\";\n\nexport const injectPartial = z.strictObject({\n cacheOnNavigation: z.boolean().default(false),\n disable: z.boolean().default(false),\n register: z.boolean().default(true),\n reloadOnOnline: z.boolean().default(true),\n scope: z.string().optional(),\n swUrl: z.string().default(\"/sw.js\"),\n globPublicPatterns: z.array(z.string()).default([\"**/*\"]),\n});\n\nexport const injectManifestOptions = z\n .strictObject({\n ...webpackInjectManifestOptions.shape,\n ...requiredSwDestPartial.shape,\n ...injectPartial.shape,\n })\n .omit({ disablePrecacheManifest: true });\n"],"mappings":";;;;AAIA,MAAa,gBAAgB,EAAE,aAAa;CAC1C,mBAAmB,EAAE,SAAS,CAAC,QAAQ,MAAM;CAC7C,SAAS,EAAE,SAAS,CAAC,QAAQ,MAAM;CACnC,UAAU,EAAE,SAAS,CAAC,QAAQ,KAAK;CACnC,gBAAgB,EAAE,SAAS,CAAC,QAAQ,KAAK;CACzC,OAAO,EAAE,QAAQ,CAAC,UAAU;CAC5B,OAAO,EAAE,QAAQ,CAAC,QAAQ,SAAS;CACnC,oBAAoB,EAAE,MAAM,EAAE,QAAQ,CAAC,CAAC,QAAQ,CAAC,OAAO,CAAC;CAC1D,CAAC;AAEF,MAAaA,0BAAwB,EAClC,aAAa;CACZ,GAAGC,sBAA6B;CAChC,GAAG,sBAAsB;CACzB,GAAG,cAAc;CAClB,CAAC,CACD,KAAK,EAAE,yBAAyB,MAAM,CAAC"}
@@ -0,0 +1,50 @@
1
+ import { Optional } from "@serwist/utils";
2
+ import { BuildOptions } from "@serwist/cli";
3
+ import { NextConfigComplete } from "next/dist/server/config-shared.js";
4
+
5
+ //#region src/lib/config/types.d.ts
6
+ interface SerwistOptions extends Optional<BuildOptions, "globDirectory"> {
7
+ /**
8
+ * Whether Serwist should precache prerendered routes.
9
+ *
10
+ * @default true
11
+ */
12
+ precachePrerendered?: boolean;
13
+ }
14
+ //#endregion
15
+ //#region src/lib/config/utils.d.ts
16
+ declare const generateGlobPatterns: (distDir: string) => string[];
17
+ //#endregion
18
+ //#region src/index.config.d.ts
19
+ /**
20
+ * Additional build context.
21
+ */
22
+ interface SerwistContext {
23
+ /**
24
+ * The current working directory.
25
+ */
26
+ cwd?: string;
27
+ /**
28
+ * Whether Serwist is in development mode. This option determines how Next.js configuration
29
+ * is resolved. Note that it doesn't change how the service worker is built.
30
+ */
31
+ isDev?: boolean;
32
+ }
33
+ interface Serwist {
34
+ /**
35
+ * Integrates Serwist into your Next.js app.
36
+ * @param options
37
+ * @returns
38
+ */
39
+ (options: SerwistOptions, nextConfig?: NextConfigComplete, context?: SerwistContext): Promise<BuildOptions>;
40
+ /**
41
+ * Integrates Serwist into your Next.js app. Allows reading fully resolved Next.js configuration.
42
+ * @param optionsFunction
43
+ * @returns
44
+ */
45
+ withNextConfig: (optionsFunction: (nextConfig: NextConfigComplete) => Promise<SerwistOptions> | SerwistOptions, context?: SerwistContext) => Promise<BuildOptions>;
46
+ }
47
+ declare const serwist: Serwist;
48
+ //#endregion
49
+ export { Serwist, SerwistContext, type SerwistOptions, generateGlobPatterns, serwist };
50
+ //# sourceMappingURL=index.config.d.mts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.config.d.mts","names":[],"sources":["../src/lib/config/types.ts","../src/lib/config/utils.ts","../src/index.config.ts"],"mappings":";;;;;UAGiB,cAAA,SAAuB,QAAA,CAAS,YAAA;;;AAAjD;;;EAME,mBAAA;AAAA;;;cCGW,oBAAA,GAAwB,OAAA;;;;ADTrC;;UEciB,cAAA;EFd+B;;;EEkB9C,GAAA;EFZmB;;;;EEiBnB,KAAA;AAAA;AAAA,UAGe,OAAA;;;;;;GAMd,OAAA,EAAS,cAAA,EAAgB,UAAA,GAAa,kBAAA,EAAoB,OAAA,GAAU,cAAA,GAAiB,OAAA,CAAQ,YAAA;EAlB/E;;;;;EAwBf,cAAA,GACE,eAAA,GAAkB,UAAA,EAAY,kBAAA,KAAuB,OAAA,CAAQ,cAAA,IAAkB,cAAA,EAC/E,OAAA,GAAU,cAAA,KACP,OAAA,CAAQ,YAAA;AAAA;AAAA,cAGF,OAAA,EAAS,OAAA"}
@@ -0,0 +1,89 @@
1
+ import { createRequire } from "node:module";
2
+ import fs from "node:fs";
3
+ import path from "node:path";
4
+ import { rebasePath } from "@serwist/build";
5
+ import { browserslistToEsbuild } from "@serwist/utils";
6
+ import browserslist from "browserslist";
7
+ import { MODERN_BROWSERSLIST_TARGET, PHASE_DEVELOPMENT_SERVER, PHASE_PRODUCTION_BUILD } from "next/constants.js";
8
+ //#endregion
9
+ //#region src/lib/config/utils.ts
10
+ const nextConfig = (/* @__PURE__ */ createRequire(import.meta.url))("next/dist/server/config.js");
11
+ const loadNextConfig = (cwd, isDev) => {
12
+ const nextPhase = isDev ? PHASE_DEVELOPMENT_SERVER : PHASE_PRODUCTION_BUILD;
13
+ return nextConfig.default(nextPhase, cwd, { silent: false });
14
+ };
15
+ const generateGlobPatterns = (distDir) => [`${distDir}static/**/*.{js,css,html,ico,apng,png,avif,jpg,jpeg,jfif,pjpeg,pjp,gif,svg,webp,json,webmanifest}`, "public/**/*"];
16
+ //#endregion
17
+ //#region src/index.config.ts
18
+ const _cwd = process.cwd();
19
+ const _isDev = process.env.NODE_ENV === "development";
20
+ const serwist = async (options, nextConfig, { cwd = _cwd, isDev = _isDev } = {}) => {
21
+ if (!nextConfig) nextConfig = await loadNextConfig(cwd, isDev);
22
+ const basePath = nextConfig.basePath || "/";
23
+ let distDir = nextConfig.distDir;
24
+ if (distDir[0] === "/") distDir = distDir.slice(1);
25
+ if (distDir[distDir.length - 1] !== "/") distDir += "/";
26
+ const distServerDir = `${distDir}server/`;
27
+ const distAppDir = `${distServerDir}app/`;
28
+ const distPagesDir = `${distServerDir}pages/`;
29
+ const { precachePrerendered = true, globDirectory = cwd, ...cliOptions } = options;
30
+ for (const file of [cliOptions.swDest, `${cliOptions.swDest}.map`]) fs.rmSync(file, { force: true });
31
+ return {
32
+ dontCacheBustURLsMatching: new RegExp(`^${distDir}static/`),
33
+ disablePrecacheManifest: isDev,
34
+ ...cliOptions,
35
+ globDirectory,
36
+ globPatterns: [...cliOptions.globPatterns ?? generateGlobPatterns(distDir), ...precachePrerendered ? [`${distServerDir}{app,pages}/**/*.html`] : []],
37
+ globIgnores: [
38
+ `${distAppDir}**/_not-found.html`,
39
+ `${distAppDir}_global-error*`,
40
+ `${distPagesDir}404.html`,
41
+ `${distPagesDir}500.html`,
42
+ ...cliOptions.globIgnores ?? [],
43
+ rebasePath({
44
+ baseDirectory: globDirectory,
45
+ file: cliOptions.swSrc
46
+ }),
47
+ rebasePath({
48
+ baseDirectory: globDirectory,
49
+ file: cliOptions.swDest
50
+ }),
51
+ rebasePath({
52
+ baseDirectory: globDirectory,
53
+ file: `${cliOptions.swDest}.map`
54
+ })
55
+ ],
56
+ manifestTransforms: [...cliOptions.manifestTransforms ?? [], (manifestEntries) => {
57
+ return {
58
+ manifest: manifestEntries.map((m) => {
59
+ if (m.url.startsWith(distAppDir)) m.url = m.url.slice(distAppDir.length - 1);
60
+ if (m.url.startsWith(distPagesDir)) m.url = m.url.slice(distPagesDir.length - 1);
61
+ if (m.url.endsWith(".html")) {
62
+ if (m.url.endsWith("/index.html")) m.url = m.url.slice(0, m.url.lastIndexOf("/") + 1);
63
+ else m.url = m.url.substring(0, m.url.lastIndexOf("."));
64
+ m.url = path.posix.join(basePath, m.url);
65
+ }
66
+ if (m.url.startsWith(distDir)) m.url = `${nextConfig.assetPrefix ?? ""}/_next/${m.url.slice(distDir.length)}`;
67
+ if (m.url.startsWith("public/")) m.url = path.posix.join(basePath, m.url.slice(7));
68
+ return m;
69
+ }),
70
+ warnings: []
71
+ };
72
+ }],
73
+ esbuildOptions: {
74
+ ...cliOptions.esbuildOptions,
75
+ target: cliOptions.esbuildOptions?.target ?? browserslistToEsbuild(browserslist, cwd, MODERN_BROWSERSLIST_TARGET)
76
+ }
77
+ };
78
+ };
79
+ serwist.withNextConfig = async (optionsFunction, { cwd = _cwd, isDev = _isDev } = {}) => {
80
+ const nextConfig = await loadNextConfig(cwd, isDev);
81
+ return serwist(await optionsFunction(nextConfig), nextConfig, {
82
+ cwd,
83
+ isDev
84
+ });
85
+ };
86
+ //#endregion
87
+ export { generateGlobPatterns, serwist };
88
+
89
+ //# sourceMappingURL=index.config.mjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.config.mjs","names":["PHASE_DEVELOPMENT_SERVER","PHASE_PRODUCTION_BUILD","NextConfigComplete","nextConfig","loadNextConfig","cwd","isDev","Promise","nextPhase","default","silent","generateGlobPatterns","distDir","fs","path","rebasePath","BuildOptions","browserslistToEsbuild","browserslist","MODERN_BROWSERSLIST_TARGET","NextConfigComplete","SerwistOptions","generateGlobPatterns","loadNextConfig","_cwd","process","cwd","_isDev","env","NODE_ENV","SerwistContext","isDev","Serwist","options","nextConfig","context","Promise","withNextConfig","optionsFunction","serwist","basePath","distDir","slice","length","distServerDir","distAppDir","distPagesDir","precachePrerendered","globDirectory","cliOptions","file","swDest","rmSync","force","dontCacheBustURLsMatching","RegExp","disablePrecacheManifest","globPatterns","globIgnores","baseDirectory","swSrc","manifestTransforms","manifestEntries","manifest","map","m","url","startsWith","endsWith","lastIndexOf","substring","posix","join","assetPrefix","warnings","esbuildOptions","target"],"sources":["../src/lib/config/utils.ts","../src/index.config.ts"],"sourcesContent":["import { PHASE_DEVELOPMENT_SERVER, PHASE_PRODUCTION_BUILD } from \"next/constants.js\";\nimport type { NextConfigComplete } from \"next/dist/server/config-shared.js\";\n\nimport nextConfig = require(\"next/dist/server/config.js\");\n\nexport const loadNextConfig = (cwd: string, isDev: boolean): Promise<NextConfigComplete> => {\n const nextPhase = isDev ? PHASE_DEVELOPMENT_SERVER : PHASE_PRODUCTION_BUILD;\n return nextConfig.default(nextPhase, cwd, {\n silent: false,\n });\n};\n\nexport const generateGlobPatterns = (distDir: string): string[] => [\n `${distDir}static/**/*.{js,css,html,ico,apng,png,avif,jpg,jpeg,jfif,pjpeg,pjp,gif,svg,webp,json,webmanifest}`,\n \"public/**/*\",\n];\n","import fs from \"node:fs\";\nimport path from \"node:path\";\nimport { rebasePath } from \"@serwist/build\";\nimport type { BuildOptions } from \"@serwist/cli\";\nimport { browserslistToEsbuild } from \"@serwist/utils\";\nimport browserslist from \"browserslist\";\nimport { MODERN_BROWSERSLIST_TARGET } from \"next/constants.js\";\nimport type { NextConfigComplete } from \"next/dist/server/config-shared.js\";\nimport type { SerwistOptions } from \"./lib/config/types.js\";\nimport { generateGlobPatterns, loadNextConfig } from \"./lib/config/utils.js\";\n\nconst _cwd = process.cwd();\nconst _isDev = process.env.NODE_ENV === \"development\";\n\n/**\n * Additional build context.\n */\nexport interface SerwistContext {\n /**\n * The current working directory.\n */\n cwd?: string;\n /**\n * Whether Serwist is in development mode. This option determines how Next.js configuration\n * is resolved. Note that it doesn't change how the service worker is built.\n */\n isDev?: boolean;\n}\n\nexport interface Serwist {\n /**\n * Integrates Serwist into your Next.js app.\n * @param options\n * @returns\n */\n (options: SerwistOptions, nextConfig?: NextConfigComplete, context?: SerwistContext): Promise<BuildOptions>;\n /**\n * Integrates Serwist into your Next.js app. Allows reading fully resolved Next.js configuration.\n * @param optionsFunction\n * @returns\n */\n withNextConfig: (\n optionsFunction: (nextConfig: NextConfigComplete) => Promise<SerwistOptions> | SerwistOptions,\n context?: SerwistContext,\n ) => Promise<BuildOptions>;\n}\n\nexport const serwist: Serwist = async (options, nextConfig, { cwd = _cwd, isDev = _isDev } = {}) => {\n if (!nextConfig) nextConfig = await loadNextConfig(cwd, isDev);\n const basePath = nextConfig.basePath || \"/\";\n let distDir = nextConfig.distDir;\n if (distDir[0] === \"/\") distDir = distDir.slice(1);\n if (distDir[distDir.length - 1] !== \"/\") distDir += \"/\";\n const distServerDir = `${distDir}server/`;\n const distAppDir = `${distServerDir}app/`;\n const distPagesDir = `${distServerDir}pages/`;\n const { precachePrerendered = true, globDirectory = cwd, ...cliOptions } = options;\n for (const file of [cliOptions.swDest, `${cliOptions.swDest}.map`]) {\n fs.rmSync(file, { force: true });\n }\n return {\n dontCacheBustURLsMatching: new RegExp(`^${distDir}static/`),\n disablePrecacheManifest: isDev,\n ...cliOptions,\n globDirectory,\n globPatterns: [\n ...(cliOptions.globPatterns ?? generateGlobPatterns(distDir)),\n ...(precachePrerendered ? [`${distServerDir}{app,pages}/**/*.html`] : []),\n ],\n globIgnores: [\n `${distAppDir}**/_not-found.html`,\n `${distAppDir}_global-error*`,\n `${distPagesDir}404.html`,\n `${distPagesDir}500.html`,\n ...(cliOptions.globIgnores ?? []),\n rebasePath({ baseDirectory: globDirectory, file: cliOptions.swSrc }),\n rebasePath({ baseDirectory: globDirectory, file: cliOptions.swDest }),\n rebasePath({ baseDirectory: globDirectory, file: `${cliOptions.swDest}.map` }),\n ],\n manifestTransforms: [\n ...(cliOptions.manifestTransforms ?? []),\n (manifestEntries) => {\n const manifest = manifestEntries.map((m) => {\n if (m.url.startsWith(distAppDir)) {\n // Keep the prefixing slash.\n m.url = m.url.slice(distAppDir.length - 1);\n }\n if (m.url.startsWith(distPagesDir)) {\n // Keep the prefixing slash.\n m.url = m.url.slice(distPagesDir.length - 1);\n }\n if (m.url.endsWith(\".html\")) {\n // trailingSlash: true && output: 'export'\n // or root index.html.\n // https://nextjs.org/docs/app/api-reference/config/next-config-js/trailingSlash\n // \"/abc/index.html\" -> \"/abc/\"\n // \"/index.html\" -> \"/\"\n if (m.url.endsWith(\"/index.html\")) {\n m.url = m.url.slice(0, m.url.lastIndexOf(\"/\") + 1);\n }\n // \"/xxx.html\" -> \"/xxx\"\n else {\n m.url = m.url.substring(0, m.url.lastIndexOf(\".\"));\n }\n m.url = path.posix.join(basePath, m.url);\n }\n // Replace all references to \"$(distDir)\" with \"$(assetPrefix)/_next/\".\n if (m.url.startsWith(distDir)) {\n m.url = `${nextConfig.assetPrefix ?? \"\"}/_next/${m.url.slice(distDir.length)}`;\n }\n // Replace all references to public/ with \"$(basePath)/\".\n if (m.url.startsWith(\"public/\")) {\n m.url = path.posix.join(basePath, m.url.slice(7));\n }\n return m;\n });\n return { manifest, warnings: [] };\n },\n ],\n esbuildOptions: {\n ...cliOptions.esbuildOptions,\n target: cliOptions.esbuildOptions?.target ?? browserslistToEsbuild(browserslist, cwd, MODERN_BROWSERSLIST_TARGET),\n },\n };\n};\n\nserwist.withNextConfig = async (optionsFunction, { cwd = _cwd, isDev = _isDev } = {}) => {\n const nextConfig = await loadNextConfig(cwd, isDev);\n return serwist(await optionsFunction(nextConfig), nextConfig, { cwd, isDev });\n};\n\nexport { generateGlobPatterns };\n\nexport type { SerwistOptions };\n"],"mappings":"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"}
@@ -0,0 +1,111 @@
1
+ import { InjectManifestOptions as InjectManifestOptions$1, InjectManifestOptionsComplete as InjectManifestOptionsComplete$1 } from "@serwist/webpack-plugin";
2
+ import { RequiredSwDestPartial, RequiredSwDestResolved } from "@serwist/build";
3
+ import { Require } from "@serwist/utils";
4
+ import { NextConfig } from "next";
5
+
6
+ //#region src/lib/types.d.ts
7
+ interface InjectPartial {
8
+ /**
9
+ * Enables additional route caching when users navigate through pages with
10
+ * `next/link`. This improves the user experience in some cases but it
11
+ * also adds a bit of overhead due to additional network calls.
12
+ * @default false
13
+ */
14
+ cacheOnNavigation?: boolean;
15
+ /**
16
+ * Whether Serwist should be disabled.
17
+ * @default false
18
+ */
19
+ disable?: boolean;
20
+ /**
21
+ * Whether `@serwist/next` should automatically register the service worker for you. If
22
+ * you want to register the service worker yourself, set this to `false` and run
23
+ * `window.serwist.register()` in `componentDidMount` or `useEffect`.
24
+ * @example
25
+ * ```tsx
26
+ * // app/register-pwa.tsx
27
+ * "use client";
28
+ * import { useEffect } from "react";
29
+ * import type { Serwist } from "@serwist/window";
30
+ *
31
+ * declare global {
32
+ * interface Window {
33
+ * serwist: Serwist;
34
+ * }
35
+ * }
36
+ *
37
+ * export default function RegisterPWA() {
38
+ * useEffect(() => {
39
+ * if ("serviceWorker" in navigator && window.serwist !== undefined) {
40
+ * window.serwist.register();
41
+ * }
42
+ * }, []);
43
+ * return <></>;
44
+ * }
45
+ *
46
+ * // app/layout.tsx
47
+ * import RegisterPWA from "./register-pwa";
48
+ *
49
+ * export default function RootLayout({
50
+ * children,
51
+ * }: {
52
+ * children: React.ReactNode;
53
+ * }) {
54
+ * return (
55
+ * <html lang="en">
56
+ * <head />
57
+ * <body>
58
+ * <RegisterPWA />
59
+ * {children}
60
+ * </body>
61
+ * </html>
62
+ * );
63
+ * }
64
+ * ```
65
+ * @default true
66
+ */
67
+ register?: boolean;
68
+ /**
69
+ * Whether Serwist should reload the app when it goes online.
70
+ * @default true
71
+ */
72
+ reloadOnOnline?: boolean;
73
+ /**
74
+ * The service worker's URL scope. Set to `/foo/` so that paths under `/foo/` are under the service
75
+ * worker's control while others are not.
76
+ * @default nextConfig.basePath
77
+ */
78
+ scope?: string;
79
+ /**
80
+ * The URL to the service worker.
81
+ * @default "/sw.js"
82
+ */
83
+ swUrl?: string;
84
+ /**
85
+ * Files in the public directory matching any of these patterns
86
+ * will be included in the precache manifest. For more information,
87
+ * see [`node-glob`'s Glob Primer](https://github.com/isaacs/node-glob#glob-primer).
88
+ * @default
89
+ * ```
90
+ * ["**\/*"]
91
+ * ```
92
+ */
93
+ globPublicPatterns?: string[];
94
+ }
95
+ type InjectResolved = Require<InjectPartial, "cacheOnNavigation" | "disable" | "register" | "reloadOnOnline" | "swUrl" | "globPublicPatterns">;
96
+ type InjectManifestOptions = Omit<InjectManifestOptions$1 & RequiredSwDestPartial & InjectPartial, "disablePrecacheManifest">;
97
+ type InjectManifestOptionsComplete = Omit<InjectManifestOptionsComplete$1 & RequiredSwDestResolved & InjectResolved, "disablePrecacheManifest">;
98
+ //#endregion
99
+ //#region src/lib/validator.d.ts
100
+ declare const validateInjectManifestOptions: (input: unknown) => InjectManifestOptionsComplete;
101
+ //#endregion
102
+ //#region src/index.d.ts
103
+ /**
104
+ * Integrates Serwist into your Next.js app.
105
+ * @param userOptions
106
+ * @returns
107
+ */
108
+ declare const withSerwistInit: (userOptions: InjectManifestOptions) => ((nextConfig?: NextConfig) => NextConfig);
109
+ //#endregion
110
+ export { type InjectManifestOptions as PluginOptions, type InjectManifestOptionsComplete as PluginOptionsComplete, withSerwistInit as default, validateInjectManifestOptions };
111
+ //# sourceMappingURL=index.d.mts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.mts","names":[],"sources":["../src/lib/types.ts","../src/lib/validator.ts","../src/index.ts"],"mappings":";;;;;;UAOiB,aAAA;;;AAAjB;;;;EAOE,iBAAA;EAKA;;;;EAAA,OAAA;EA0EA;;;AAGF;;;;;AAEA;;;;;;;;;;;;;;;AAEA;;;;;;;;;;;;;;;;;;AC/FA;;;;;;ED8DE,QAAA;;AExDiE;;;EF6DjE,cAAA;EEpD2E;;;;;EF0D3E,KAAA;EE1D2E;;;;EF+D3E,KAAA;;;;;;;;;;EAUA,kBAAA;AAAA;AAAA,KAGU,cAAA,GAAiB,OAAA,CAAQ,aAAA;AAAA,KAEzB,qBAAA,GAAwB,IAAA,CAAK,uBAAA,GAA+B,qBAAA,GAAwB,aAAA;AAAA,KAEpF,6BAAA,GAAgC,IAAA,CAC1C,+BAAA,GAAuC,sBAAA,GAAyB,cAAA;;;cChGrD,6BAAA,GAAiC,KAAA,cAAiB,6BAAA;;;;;;ADE/D;;cEaM,eAAA,GAAmB,WAAA,EAAa,qBAAA,OAA0B,UAAA,GAAa,UAAA,KAAe,UAAA"}
package/dist/index.mjs ADDED
@@ -0,0 +1,242 @@
1
+ import { t as injectManifestOptions } from "./chunks/schema-BhRhcBIb.js";
2
+ import { createRequire } from "node:module";
3
+ import fs from "node:fs";
4
+ import path from "node:path";
5
+ import { fileURLToPath } from "node:url";
6
+ import { InjectManifest } from "@serwist/webpack-plugin";
7
+ import { ChildCompilationPlugin, relativeToOutputPath } from "@serwist/webpack-plugin/internal";
8
+ import { globSync } from "glob";
9
+ import crypto from "node:crypto";
10
+ import { bold, green, red, white, yellow } from "kolorist";
11
+ import semver from "semver";
12
+ import { SerwistConfigError, validationErrorMap } from "@serwist/build/schema";
13
+ import { z } from "zod";
14
+ //#region src/lib/find-first-truthy.ts
15
+ /**
16
+ * Find the first truthy value in an array.
17
+ * @param arr
18
+ * @param fn
19
+ * @returns
20
+ */
21
+ const findFirstTruthy = (arr, fn) => {
22
+ for (const i of arr) {
23
+ const resolved = fn(i);
24
+ if (resolved) return resolved;
25
+ }
26
+ };
27
+ //#endregion
28
+ //#region src/lib/get-file-hash.ts
29
+ const getFileHash = (file) => crypto.createHash("md5").update(fs.readFileSync(file)).digest("hex");
30
+ //#endregion
31
+ //#region src/lib/get-content-hash.ts
32
+ const getContentHash = (file, isDev) => {
33
+ if (isDev) return "development";
34
+ return getFileHash(file).slice(0, 16);
35
+ };
36
+ createRequire(import.meta.url);
37
+ //#endregion
38
+ //#region src/lib/load-tsconfig.ts
39
+ const loadTSConfig = (baseDir, relativeTSConfigPath) => {
40
+ try {
41
+ const tsConfigPath = findFirstTruthy([relativeTSConfigPath ?? "tsconfig.json", "jsconfig.json"], (filePath) => {
42
+ const resolvedPath = path.join(baseDir, filePath);
43
+ return fs.existsSync(resolvedPath) ? resolvedPath : void 0;
44
+ });
45
+ if (!tsConfigPath) return;
46
+ return JSON.parse(fs.readFileSync(tsConfigPath, "utf-8"));
47
+ } catch {
48
+ return;
49
+ }
50
+ };
51
+ //#endregion
52
+ //#region src/lib/logger.ts
53
+ const require = createRequire(import.meta.url);
54
+ const LOGGING_SPACE_PREFIX = semver.gte(require("next/package.json").version, "16.0.0") ? "" : " ";
55
+ const prefixedLog = (prefixType, ...message) => {
56
+ let prefix;
57
+ let consoleMethod;
58
+ switch (prefixType) {
59
+ case "wait":
60
+ prefix = `${white(bold("○"))} (serwist)`;
61
+ consoleMethod = "log";
62
+ break;
63
+ case "error":
64
+ prefix = `${red(bold("X"))} (serwist)`;
65
+ consoleMethod = "error";
66
+ break;
67
+ case "warn":
68
+ prefix = `${yellow(bold("⚠"))} (serwist)`;
69
+ consoleMethod = "warn";
70
+ break;
71
+ case "info":
72
+ prefix = `${white(bold("○"))} (serwist)`;
73
+ consoleMethod = "log";
74
+ break;
75
+ case "event":
76
+ prefix = `${green(bold("✓"))} (serwist)`;
77
+ consoleMethod = "log";
78
+ break;
79
+ }
80
+ if ((message[0] === "" || message[0] === void 0) && message.length === 1) message.shift();
81
+ if (message.length === 0) console[consoleMethod]("");
82
+ else console[consoleMethod](`${LOGGING_SPACE_PREFIX}${prefix}`, ...message);
83
+ };
84
+ const info = (...message) => prefixedLog("info", ...message);
85
+ const event = (...message) => prefixedLog("event", ...message);
86
+ //#endregion
87
+ //#region src/lib/validator.ts
88
+ const validateInjectManifestOptions = (input) => {
89
+ const result = injectManifestOptions.safeParse(input, { error: validationErrorMap });
90
+ if (!result.success) throw new SerwistConfigError({
91
+ moduleName: "@serwist/next",
92
+ message: z.prettifyError(result.error)
93
+ });
94
+ return result.data;
95
+ };
96
+ //#endregion
97
+ //#region src/index.ts
98
+ const dirname = "__dirname" in globalThis ? __dirname : fileURLToPath(new URL(".", import.meta.url));
99
+ /**
100
+ * Integrates Serwist into your Next.js app.
101
+ * @param userOptions
102
+ * @returns
103
+ */
104
+ const withSerwistInit = (userOptions) => {
105
+ if (!process.env.SERWIST_SUPPRESS_TURBOPACK_WARNING && process.env.TURBOPACK && !userOptions.disable) {
106
+ process.env.SERWIST_SUPPRESS_TURBOPACK_WARNING = "1";
107
+ console.warn(`[@serwist/next] WARNING: You are using '@serwist/next' with \`next dev --turbopack\`, but it doesn't support Turbopack. Do one of the following:
108
+
109
+ - Set \`disable\` to \`process.env.NODE_ENV !== "production"\`.
110
+
111
+ - Use webpack by running \`next dev --webpack\` instead of \`next dev --turbopack\`.
112
+
113
+ - Migrate to '@serwist/turbopack' which has experimental support for Turbopack. See https://serwist.pages.dev/docs/next/turbo for more information.
114
+
115
+ - Migrate to configurator mode which has support for Turbopack. See https://serwist.pages.dev/docs/next/config for more information.
116
+
117
+ Follow https://github.com/serwist/serwist/issues/54 for progress on Serwist + Turbopack. You can also suppress this warning by setting SERWIST_SUPPRESS_TURBOPACK_WARNING=1.\n`);
118
+ }
119
+ return (nextConfig = {}) => ({
120
+ ...nextConfig,
121
+ webpack(config, options) {
122
+ const webpack = options.webpack;
123
+ const { dev } = options;
124
+ const basePath = options.config.basePath || "/";
125
+ const tsConfigJson = loadTSConfig(options.dir, nextConfig?.typescript?.tsconfigPath);
126
+ const { cacheOnNavigation, disable, scope = basePath, swUrl, register, reloadOnOnline, globPublicPatterns, ...buildOptions } = validateInjectManifestOptions(userOptions);
127
+ if (typeof nextConfig.webpack === "function") config = nextConfig.webpack(config, options);
128
+ if (disable) {
129
+ options.isServer && info("Serwist is disabled.");
130
+ return config;
131
+ }
132
+ if (!config.plugins) config.plugins = [];
133
+ const _sw = path.posix.join(basePath, swUrl);
134
+ const _scope = path.posix.join(scope, "/");
135
+ config.plugins.push(new webpack.DefinePlugin({
136
+ "self.__SERWIST_SW_ENTRY.sw": `'${_sw}'`,
137
+ "self.__SERWIST_SW_ENTRY.scope": `'${_scope}'`,
138
+ "self.__SERWIST_SW_ENTRY.cacheOnNavigation": `${cacheOnNavigation}`,
139
+ "self.__SERWIST_SW_ENTRY.register": `${register}`,
140
+ "self.__SERWIST_SW_ENTRY.reloadOnOnline": `${reloadOnOnline}`
141
+ }));
142
+ const swEntryJs = path.join(dirname, "sw-entry.mjs");
143
+ const entry = config.entry;
144
+ config.entry = async () => {
145
+ const entries = await entry();
146
+ if (entries["main.js"] && !entries["main.js"].includes(swEntryJs)) {
147
+ if (Array.isArray(entries["main.js"])) entries["main.js"].unshift(swEntryJs);
148
+ else if (typeof entries["main.js"] === "string") entries["main.js"] = [swEntryJs, entries["main.js"]];
149
+ }
150
+ if (entries["main-app"] && !entries["main-app"].includes(swEntryJs)) {
151
+ if (Array.isArray(entries["main-app"])) entries["main-app"].unshift(swEntryJs);
152
+ else if (typeof entries["main-app"] === "string") entries["main-app"] = [swEntryJs, entries["main-app"]];
153
+ }
154
+ return entries;
155
+ };
156
+ if (!options.isServer) {
157
+ if (!register) {
158
+ info("The service worker will not be automatically registered, please call 'window.serwist.register()' in 'componentDidMount' or 'useEffect'.");
159
+ if (!tsConfigJson?.compilerOptions?.types?.includes("@serwist/next/typings")) info("You may also want to add '@serwist/next/typings' to your TypeScript/JavaScript configuration file at 'compilerOptions.types'.");
160
+ }
161
+ const { swSrc: userSwSrc, swDest: userSwDest, additionalPrecacheEntries, exclude, manifestTransforms = [], ...otherBuildOptions } = buildOptions;
162
+ let swSrc = userSwSrc;
163
+ let swDest = userSwDest;
164
+ if (!path.isAbsolute(swSrc)) swSrc = path.join(options.dir, swSrc);
165
+ if (!path.isAbsolute(swDest)) swDest = path.join(options.dir, swDest);
166
+ const publicDir = path.resolve(options.dir, "public");
167
+ const { dir: destDir, base: destBase } = path.parse(swDest);
168
+ const cleanUpList = globSync([
169
+ "swe-worker-*.js",
170
+ "swe-worker-*.js.map",
171
+ destBase,
172
+ `${destBase}.map`
173
+ ], {
174
+ absolute: true,
175
+ nodir: true,
176
+ follow: true,
177
+ cwd: destDir
178
+ });
179
+ for (const file of cleanUpList) fs.rmSync(file, { force: true });
180
+ const shouldBuildSWEntryWorker = cacheOnNavigation;
181
+ let swEntryPublicPath;
182
+ let swEntryWorkerDest;
183
+ if (shouldBuildSWEntryWorker) {
184
+ const swEntryWorkerSrc = path.join(dirname, "sw-entry-worker.mjs");
185
+ const swEntryName = `swe-worker-${getContentHash(swEntryWorkerSrc, dev)}.js`;
186
+ swEntryPublicPath = path.posix.join(basePath, swEntryName);
187
+ swEntryWorkerDest = path.join(destDir, swEntryName);
188
+ config.plugins.push(new ChildCompilationPlugin({
189
+ src: swEntryWorkerSrc,
190
+ dest: swEntryWorkerDest
191
+ }));
192
+ }
193
+ config.plugins.push(new webpack.DefinePlugin({ "self.__SERWIST_SW_ENTRY.swEntryWorker": swEntryPublicPath && `'${swEntryPublicPath}'` }));
194
+ event(`Bundling the service worker script with the URL '${_sw}' and the scope '${_scope}'...`);
195
+ let resolvedManifestEntries = additionalPrecacheEntries;
196
+ if (!resolvedManifestEntries) resolvedManifestEntries = globSync(globPublicPatterns, {
197
+ nodir: true,
198
+ follow: true,
199
+ cwd: publicDir,
200
+ ignore: [
201
+ "swe-worker-*.js",
202
+ destBase,
203
+ `${destBase}.map`
204
+ ]
205
+ }).map((f) => ({
206
+ url: path.posix.join(basePath, f),
207
+ revision: getFileHash(path.join(publicDir, f))
208
+ }));
209
+ const publicPath = config.output?.publicPath;
210
+ config.plugins.push(new InjectManifest({
211
+ swSrc,
212
+ swDest,
213
+ disablePrecacheManifest: dev,
214
+ additionalPrecacheEntries: dev ? [] : resolvedManifestEntries,
215
+ exclude: [...exclude, ({ asset, compilation }) => {
216
+ const swDestRelativeOutput = relativeToOutputPath(compilation, swDest);
217
+ const swAsset = compilation.getAsset(swDestRelativeOutput);
218
+ return asset.name === swAsset?.name || asset.name.startsWith("server/") || /^[^/]*\.json$/.test(asset.name) || dev && !asset.name.startsWith("static/runtime/");
219
+ }],
220
+ manifestTransforms: [...manifestTransforms, async (manifestEntries, compilation) => {
221
+ const publicFilesPrefix = `${publicPath}${relativeToOutputPath(compilation, publicDir)}`;
222
+ return {
223
+ manifest: manifestEntries.map((m) => {
224
+ m.url = m.url.replace("/_next//static/image", "/_next/static/image").replace("/_next//static/media", "/_next/static/media");
225
+ if (m.url.startsWith(publicFilesPrefix)) m.url = path.posix.join(basePath, m.url.replace(publicFilesPrefix, ""));
226
+ m.url = m.url.replace(/\[/g, "%5B").replace(/\]/g, "%5D").replace(/@/g, "%40");
227
+ return m;
228
+ }),
229
+ warnings: []
230
+ };
231
+ }],
232
+ ...otherBuildOptions
233
+ }));
234
+ }
235
+ return config;
236
+ }
237
+ });
238
+ };
239
+ //#endregion
240
+ export { withSerwistInit as default, validateInjectManifestOptions };
241
+
242
+ //# sourceMappingURL=index.mjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.mjs","names":["findFirstTruthy","arr","T","fn","elm","U","i","resolved","undefined","crypto","fs","getFileHash","file","PathOrFileDescriptor","createHash","update","readFileSync","digest","fs","getFileHash","getContentHash","file","PathOrFileDescriptor","isDev","slice","createRequire","require","import","meta","url","getPackageVersion","packageName","version","undefined","fs","path","TsConfigJson","TSConfigJSON","findFirstTruthy","loadTSConfig","baseDir","relativeTSConfigPath","tsConfigPath","filePath","resolvedPath","join","existsSync","undefined","JSON","parse","readFileSync","createRequire","bold","green","red","white","yellow","semver","require","import","meta","url","LOGGING_SPACE_PREFIX","gte","version","LoggingMethods","prefixedLog","prefixType","message","prefix","consoleMethod","Console","undefined","length","shift","console","wait","error","warn","info","event","SerwistConfigError","validationErrorMap","z","injectManifestOptions","InjectManifestOptionsComplete","validateInjectManifestOptions","input","result","safeParse","error","success","moduleName","message","prettifyError","data","fs","path","fileURLToPath","InjectManifest","ChildCompilationPlugin","relativeToOutputPath","globSync","NextConfig","Compilation","Configuration","default","Webpack","ExcludeParams","SerwistNextOptions","SerwistNextOptionsKey","getContentHash","getFileHash","loadTSConfig","logger","InjectManifestOptions","InjectManifestOptionsComplete","validateInjectManifestOptions","dirname","globalThis","__dirname","URL","import","meta","url","withSerwistInit","userOptions","nextConfig","process","env","SERWIST_SUPPRESS_TURBOPACK_WARNING","TURBOPACK","disable","console","warn","webpack","config","options","dev","basePath","tsConfigJson","dir","typescript","tsconfigPath","cacheOnNavigation","scope","swUrl","register","reloadOnOnline","globPublicPatterns","buildOptions","isServer","info","plugins","_sw","posix","join","_scope","push","DefinePlugin","Record","Exclude","swEntryJs","entry","Promise","entries","includes","Array","isArray","unshift","compilerOptions","types","swSrc","userSwSrc","swDest","userSwDest","additionalPrecacheEntries","exclude","manifestTransforms","otherBuildOptions","isAbsolute","publicDir","resolve","destDir","base","destBase","parse","cleanUpList","absolute","nodir","follow","cwd","file","rmSync","force","shouldBuildSWEntryWorker","swEntryPublicPath","swEntryWorkerDest","swEntryWorkerSrc","swEntryName","src","dest","Extract","event","resolvedManifestEntries","publicScan","ignore","map","f","revision","publicPath","output","disablePrecacheManifest","asset","compilation","swDestRelativeOutput","swAsset","getAsset","name","startsWith","test","manifestEntries","publicDirRelativeOutput","publicFilesPrefix","manifest","m","replace","warnings","PluginOptions","PluginOptionsComplete"],"sources":["../src/lib/find-first-truthy.ts","../src/lib/get-file-hash.ts","../src/lib/get-content-hash.ts","../src/lib/get-package-version.ts","../src/lib/load-tsconfig.ts","../src/lib/logger.ts","../src/lib/validator.ts","../src/index.ts"],"sourcesContent":["/**\n * Find the first truthy value in an array.\n * @param arr\n * @param fn\n * @returns\n */\nexport const findFirstTruthy = <T, U>(arr: T[], fn: (elm: T) => U) => {\n for (const i of arr) {\n const resolved = fn(i);\n if (resolved) {\n return resolved;\n }\n }\n return undefined;\n};\n","import crypto from \"node:crypto\";\nimport fs from \"node:fs\";\n\nexport const getFileHash = (file: fs.PathOrFileDescriptor) => crypto.createHash(\"md5\").update(fs.readFileSync(file)).digest(\"hex\");\n","import type fs from \"node:fs\";\n\nimport { getFileHash } from \"./get-file-hash.js\";\n\nexport const getContentHash = (file: fs.PathOrFileDescriptor, isDev: boolean) => {\n if (isDev) {\n return \"development\";\n }\n return getFileHash(file).slice(0, 16);\n};\n","import { createRequire } from \"node:module\";\n\nconst require = createRequire(import.meta.url);\n\n/**\n * Get a package's version\n * @param packageName\n * @returns\n */\nexport const getPackageVersion = (packageName: string): string | undefined => {\n try {\n return require(`${packageName}/package.json`).version;\n } catch {\n return undefined;\n }\n};\n","import fs from \"node:fs\";\nimport path from \"node:path\";\n\nimport type { TsConfigJson as TSConfigJSON } from \"type-fest\";\n\nimport { findFirstTruthy } from \"./find-first-truthy.js\";\n\nexport const loadTSConfig = (baseDir: string, relativeTSConfigPath: string | undefined): TSConfigJSON | undefined => {\n try {\n // Find tsconfig.json file\n const tsConfigPath = findFirstTruthy([relativeTSConfigPath ?? \"tsconfig.json\", \"jsconfig.json\"], (filePath) => {\n const resolvedPath = path.join(baseDir, filePath);\n return fs.existsSync(resolvedPath) ? resolvedPath : undefined;\n });\n if (!tsConfigPath) {\n return undefined;\n }\n // Read tsconfig.json file\n return JSON.parse(fs.readFileSync(tsConfigPath, \"utf-8\"));\n } catch {\n return undefined;\n }\n};\n","import { createRequire } from \"node:module\";\nimport { bold, green, red, white, yellow } from \"kolorist\";\nimport semver from \"semver\";\n\nconst require = createRequire(import.meta.url);\n\nconst LOGGING_SPACE_PREFIX = semver.gte(require(\"next/package.json\").version, \"16.0.0\") ? \"\" : \" \";\n\nexport type LoggingMethods = \"wait\" | \"error\" | \"warn\" | \"info\" | \"event\";\n\nconst prefixedLog = (prefixType: LoggingMethods, ...message: any[]) => {\n let prefix: string;\n let consoleMethod: keyof Console;\n\n switch (prefixType) {\n case \"wait\":\n prefix = `${white(bold(\"○\"))} (serwist)`;\n consoleMethod = \"log\";\n break;\n case \"error\":\n prefix = `${red(bold(\"X\"))} (serwist)`;\n consoleMethod = \"error\";\n break;\n case \"warn\":\n prefix = `${yellow(bold(\"⚠\"))} (serwist)`;\n consoleMethod = \"warn\";\n break;\n case \"info\":\n prefix = `${white(bold(\"○\"))} (serwist)`;\n consoleMethod = \"log\";\n break;\n case \"event\":\n prefix = `${green(bold(\"✓\"))} (serwist)`;\n consoleMethod = \"log\";\n break;\n }\n\n if ((message[0] === \"\" || message[0] === undefined) && message.length === 1) {\n message.shift();\n }\n\n // If there's no message, don't print the prefix but a new line\n if (message.length === 0) {\n console[consoleMethod](\"\");\n } else {\n console[consoleMethod](`${LOGGING_SPACE_PREFIX}${prefix}`, ...message);\n }\n};\n\nexport const wait = (...message: any[]) => prefixedLog(\"wait\", ...message);\n\nexport const error = (...message: any[]) => prefixedLog(\"error\", ...message);\n\nexport const warn = (...message: any[]) => prefixedLog(\"warn\", ...message);\n\nexport const info = (...message: any[]) => prefixedLog(\"info\", ...message);\n\nexport const event = (...message: any[]) => prefixedLog(\"event\", ...message);\n","import { SerwistConfigError, validationErrorMap } from \"@serwist/build/schema\";\nimport { z } from \"zod\";\nimport { injectManifestOptions } from \"./schema.js\";\nimport type { InjectManifestOptionsComplete } from \"./types.js\";\n\nexport const validateInjectManifestOptions = (input: unknown): InjectManifestOptionsComplete => {\n const result = injectManifestOptions.safeParse(input, {\n error: validationErrorMap,\n });\n if (!result.success) {\n throw new SerwistConfigError({ moduleName: \"@serwist/next\", message: z.prettifyError(result.error) });\n }\n return result.data;\n};\n","import fs from \"node:fs\";\nimport path from \"node:path\";\nimport { fileURLToPath } from \"node:url\";\nimport { InjectManifest } from \"@serwist/webpack-plugin\";\nimport { ChildCompilationPlugin, relativeToOutputPath } from \"@serwist/webpack-plugin/internal\";\nimport { globSync } from \"glob\";\nimport type { NextConfig } from \"next\";\nimport type { Compilation, Configuration, default as Webpack } from \"webpack\";\nimport type { ExcludeParams, SerwistNextOptions, SerwistNextOptionsKey } from \"./internal-types.js\";\nimport { getContentHash, getFileHash, loadTSConfig, logger } from \"./lib/index.js\";\nimport type { InjectManifestOptions, InjectManifestOptionsComplete } from \"./lib/types.js\";\nimport { validateInjectManifestOptions } from \"./lib/validator.js\";\n\nconst dirname = \"__dirname\" in globalThis ? __dirname : fileURLToPath(new URL(\".\", import.meta.url));\n\n/**\n * Integrates Serwist into your Next.js app.\n * @param userOptions\n * @returns\n */\nconst withSerwistInit = (userOptions: InjectManifestOptions): ((nextConfig?: NextConfig) => NextConfig) => {\n if (!process.env.SERWIST_SUPPRESS_TURBOPACK_WARNING && process.env.TURBOPACK && !userOptions.disable) {\n process.env.SERWIST_SUPPRESS_TURBOPACK_WARNING = \"1\";\n console.warn(\n `[@serwist/next] WARNING: You are using '@serwist/next' with \\`next dev --turbopack\\`, but it doesn't support Turbopack. Do one of the following:\n\n- Set \\`disable\\` to \\`process.env.NODE_ENV !== \"production\"\\`.\n\n- Use webpack by running \\`next dev --webpack\\` instead of \\`next dev --turbopack\\`.\n\n- Migrate to '@serwist/turbopack' which has experimental support for Turbopack. See https://serwist.pages.dev/docs/next/turbo for more information.\n\n- Migrate to configurator mode which has support for Turbopack. See https://serwist.pages.dev/docs/next/config for more information. \n\nFollow https://github.com/serwist/serwist/issues/54 for progress on Serwist + Turbopack. You can also suppress this warning by setting SERWIST_SUPPRESS_TURBOPACK_WARNING=1.\\n`,\n );\n }\n return (nextConfig = {}) => ({\n ...nextConfig,\n webpack(config: Configuration, options) {\n const webpack: typeof Webpack = options.webpack;\n const { dev } = options;\n\n const basePath = options.config.basePath || \"/\";\n\n const tsConfigJson = loadTSConfig(options.dir, nextConfig?.typescript?.tsconfigPath);\n\n const {\n cacheOnNavigation,\n disable,\n scope = basePath,\n swUrl,\n register,\n reloadOnOnline,\n globPublicPatterns,\n ...buildOptions\n } = validateInjectManifestOptions(userOptions);\n\n if (typeof nextConfig.webpack === \"function\") {\n config = nextConfig.webpack(config, options);\n }\n\n if (disable) {\n options.isServer && logger.info(\"Serwist is disabled.\");\n return config;\n }\n\n if (!config.plugins) {\n config.plugins = [];\n }\n\n const _sw = path.posix.join(basePath, swUrl);\n const _scope = path.posix.join(scope, \"/\");\n\n config.plugins.push(\n new webpack.DefinePlugin({\n \"self.__SERWIST_SW_ENTRY.sw\": `'${_sw}'`,\n \"self.__SERWIST_SW_ENTRY.scope\": `'${_scope}'`,\n \"self.__SERWIST_SW_ENTRY.cacheOnNavigation\": `${cacheOnNavigation}`,\n \"self.__SERWIST_SW_ENTRY.register\": `${register}`,\n \"self.__SERWIST_SW_ENTRY.reloadOnOnline\": `${reloadOnOnline}`,\n } satisfies Record<`${SerwistNextOptionsKey}.${Exclude<keyof SerwistNextOptions, \"swEntryWorker\">}`, string | undefined>),\n );\n\n const swEntryJs = path.join(dirname, \"sw-entry.mjs\");\n const entry = config.entry as () => Promise<Record<string, string[] | string>>;\n config.entry = async () => {\n const entries = await entry();\n if (entries[\"main.js\"] && !entries[\"main.js\"].includes(swEntryJs)) {\n if (Array.isArray(entries[\"main.js\"])) {\n entries[\"main.js\"].unshift(swEntryJs);\n } else if (typeof entries[\"main.js\"] === \"string\") {\n entries[\"main.js\"] = [swEntryJs, entries[\"main.js\"]];\n }\n }\n if (entries[\"main-app\"] && !entries[\"main-app\"].includes(swEntryJs)) {\n if (Array.isArray(entries[\"main-app\"])) {\n entries[\"main-app\"].unshift(swEntryJs);\n } else if (typeof entries[\"main-app\"] === \"string\") {\n entries[\"main-app\"] = [swEntryJs, entries[\"main-app\"]];\n }\n }\n return entries;\n };\n\n if (!options.isServer) {\n if (!register) {\n logger.info(\n \"The service worker will not be automatically registered, please call 'window.serwist.register()' in 'componentDidMount' or 'useEffect'.\",\n );\n\n if (!tsConfigJson?.compilerOptions?.types?.includes(\"@serwist/next/typings\")) {\n logger.info(\n \"You may also want to add '@serwist/next/typings' to your TypeScript/JavaScript configuration file at 'compilerOptions.types'.\",\n );\n }\n }\n\n const {\n swSrc: userSwSrc,\n swDest: userSwDest,\n additionalPrecacheEntries,\n exclude,\n manifestTransforms = [],\n ...otherBuildOptions\n } = buildOptions;\n\n let swSrc = userSwSrc;\n let swDest = userSwDest;\n\n // If these two paths are not absolute, they will be resolved from `compilation.options.output.path`,\n // which is `${options.dir}/${nextConfig.destDir}` for Next.js apps, rather than `${options.dir}`\n // as an user would expect.\n if (!path.isAbsolute(swSrc)) {\n swSrc = path.join(options.dir, swSrc);\n }\n if (!path.isAbsolute(swDest)) {\n swDest = path.join(options.dir, swDest);\n }\n\n const publicDir = path.resolve(options.dir, \"public\");\n const { dir: destDir, base: destBase } = path.parse(swDest);\n\n const cleanUpList = globSync([\"swe-worker-*.js\", \"swe-worker-*.js.map\", destBase, `${destBase}.map`], {\n absolute: true,\n nodir: true,\n follow: true,\n cwd: destDir,\n });\n\n for (const file of cleanUpList) {\n fs.rmSync(file, { force: true });\n }\n\n const shouldBuildSWEntryWorker = cacheOnNavigation;\n let swEntryPublicPath: string | undefined;\n let swEntryWorkerDest: string | undefined;\n\n if (shouldBuildSWEntryWorker) {\n const swEntryWorkerSrc = path.join(dirname, \"sw-entry-worker.mjs\");\n const swEntryName = `swe-worker-${getContentHash(swEntryWorkerSrc, dev)}.js`;\n swEntryPublicPath = path.posix.join(basePath, swEntryName);\n swEntryWorkerDest = path.join(destDir, swEntryName);\n config.plugins.push(\n new ChildCompilationPlugin({\n src: swEntryWorkerSrc,\n dest: swEntryWorkerDest,\n }),\n );\n }\n config.plugins.push(\n new webpack.DefinePlugin({\n \"self.__SERWIST_SW_ENTRY.swEntryWorker\": swEntryPublicPath && `'${swEntryPublicPath}'`,\n } satisfies Record<`${SerwistNextOptionsKey}.${Extract<keyof SerwistNextOptions, \"swEntryWorker\">}`, string | undefined>),\n );\n\n logger.event(`Bundling the service worker script with the URL '${_sw}' and the scope '${_scope}'...`);\n\n // Precache files in public folder\n let resolvedManifestEntries = additionalPrecacheEntries;\n\n if (!resolvedManifestEntries) {\n const publicScan = globSync(globPublicPatterns, {\n nodir: true,\n follow: true,\n cwd: publicDir,\n ignore: [\"swe-worker-*.js\", destBase, `${destBase}.map`],\n });\n resolvedManifestEntries = publicScan.map((f) => ({\n url: path.posix.join(basePath, f),\n revision: getFileHash(path.join(publicDir, f)),\n }));\n }\n\n const publicPath = config.output?.publicPath;\n\n config.plugins.push(\n new InjectManifest({\n swSrc,\n swDest,\n disablePrecacheManifest: dev,\n additionalPrecacheEntries: dev ? [] : resolvedManifestEntries,\n exclude: [\n ...exclude,\n ({ asset, compilation }: ExcludeParams) => {\n // Same as how `@serwist/webpack-plugin` does it. It is always\n // `relativeToOutputPath(compilation, originalSwDest)`.\n const swDestRelativeOutput = relativeToOutputPath(compilation, swDest);\n const swAsset = compilation.getAsset(swDestRelativeOutput);\n return (\n // We don't need the service worker to be cached.\n asset.name === swAsset?.name ||\n asset.name.startsWith(\"server/\") ||\n // This excludes all JSON files in the compilation directory by filtering\n // out paths that have slashes or don't end with `.json`. Only said files\n // match this criterion.\n /^[^/]*\\.json$/.test(asset.name) ||\n (dev && !asset.name.startsWith(\"static/runtime/\"))\n );\n },\n ],\n manifestTransforms: [\n ...manifestTransforms,\n async (manifestEntries, compilation) => {\n // This path always uses forward slashes, so it is safe to use it in the following string replace.\n const publicDirRelativeOutput = relativeToOutputPath(compilation as Compilation, publicDir);\n // `publicPath` is always `${assetPrefix}/_next/` for Next.js apps.\n const publicFilesPrefix = `${publicPath}${publicDirRelativeOutput}`;\n const manifest = manifestEntries.map((m) => {\n m.url = m.url.replace(\"/_next//static/image\", \"/_next/static/image\").replace(\"/_next//static/media\", \"/_next/static/media\");\n // We remove `${publicPath}/${publicDirRelativeOutput}` because `assetPrefix`\n // is not intended for files that are in the public directory and we also want\n // to remove `/_next/${publicDirRelativeOutput}` from the URL, since that is not how\n // we resolve files in the public directory.\n if (m.url.startsWith(publicFilesPrefix)) {\n m.url = path.posix.join(basePath, m.url.replace(publicFilesPrefix, \"\"));\n }\n m.url = m.url.replace(/\\[/g, \"%5B\").replace(/\\]/g, \"%5D\").replace(/@/g, \"%40\");\n return m;\n });\n return { manifest, warnings: [] };\n },\n ],\n ...otherBuildOptions,\n }),\n );\n }\n\n return config;\n },\n });\n};\n\nexport default withSerwistInit;\nexport { validateInjectManifestOptions };\nexport type { InjectManifestOptions as PluginOptions, InjectManifestOptionsComplete as PluginOptionsComplete };\n"],"mappings":"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"}