1 | "use strict";
|
2 | var __importDefault = (this && this.__importDefault) || function (mod) {
|
3 | return (mod && mod.__esModule) ? mod : { "default": mod };
|
4 | };
|
5 | Object.defineProperty(exports, "__esModule", { value: true });
|
6 | exports.generateEnvModule = exports.wrapImportProxy = exports.wrapHtmlResponse = exports.wrapImportMeta = exports.getMetaUrlPath = void 0;
|
7 | const path_1 = __importDefault(require("path"));
|
8 | const postcss_1 = __importDefault(require("postcss"));
|
9 | const postcss_modules_1 = __importDefault(require("postcss-modules"));
|
10 | const logger_1 = require("../logger");
|
11 | const util_1 = require("../util");
|
12 | const import_sri_1 = require("./import-sri");
|
13 | const SRI_CLIENT_HMR_SNOWPACK = import_sri_1.generateSRI(Buffer.from(util_1.HMR_CLIENT_CODE));
|
14 | const SRI_ERROR_HMR_SNOWPACK = import_sri_1.generateSRI(Buffer.from(util_1.HMR_OVERLAY_CODE));
|
15 | const importMetaRegex = /import\s*\.\s*meta/;
|
16 | function getMetaUrlPath(urlPath, config) {
|
17 | return path_1.default.posix.normalize(path_1.default.posix.join('/', config.buildOptions.metaUrlPath, urlPath));
|
18 | }
|
19 | exports.getMetaUrlPath = getMetaUrlPath;
|
20 | function wrapImportMeta({ code, hmr, env, config, }) {
|
21 |
|
22 | const importMetaHotRegex = /import\s*\.\s*meta\s*\.\s*hot/g;
|
23 | const importMetaEnvRegex = /import\s*\.\s*meta\s*\.\s*env/g;
|
24 |
|
25 |
|
26 | if (!hmr) {
|
27 | code = code.replace(importMetaHotRegex, 'undefined /* [snowpack] import.meta.hot */ ');
|
28 | }
|
29 | if (!importMetaRegex.test(code)) {
|
30 | return code;
|
31 | }
|
32 | let hmrSnippet = ``;
|
33 | if (hmr) {
|
34 | hmrSnippet = `import * as __SNOWPACK_HMR__ from '${getMetaUrlPath('hmr-client.js', config)}';\nimport.meta.hot = __SNOWPACK_HMR__.createHotContext(import.meta.url);\n`;
|
35 | }
|
36 | let envSnippet = ``;
|
37 | if (env) {
|
38 | envSnippet = `import * as __SNOWPACK_ENV__ from '${getMetaUrlPath('env.js', config)}';\n`;
|
39 |
|
40 | code = code.replace(importMetaEnvRegex, '__SNOWPACK_ENV__');
|
41 |
|
42 | if (importMetaRegex.test(code)) {
|
43 | envSnippet += `import.meta.env = __SNOWPACK_ENV__;\n`;
|
44 | }
|
45 | }
|
46 | return hmrSnippet + envSnippet + '\n' + code;
|
47 | }
|
48 | exports.wrapImportMeta = wrapImportMeta;
|
49 | function wrapHtmlResponse({ code, hmr, hmrPort, isDev, config, mode, }) {
|
50 |
|
51 | code = code.replace(/\/?%PUBLIC_URL%\/?/g, isDev ? '/' : config.buildOptions.baseUrl);
|
52 |
|
53 | code = code.replace(/%MODE%/g, mode);
|
54 | const snowpackPublicEnv = getSnowpackPublicEnvVariables();
|
55 | code = code.replace(/%SNOWPACK_PUBLIC_.+?%/gi, (match) => {
|
56 | const envVariableName = match.slice(1, -1);
|
57 | if (envVariableName in snowpackPublicEnv) {
|
58 | return snowpackPublicEnv[envVariableName] || '';
|
59 | }
|
60 | logger_1.logger.warn(`Environment variable "${envVariableName}" is not set`);
|
61 | return match;
|
62 | });
|
63 |
|
64 |
|
65 | const isFullPage = code.trim().toLowerCase().startsWith('<!doctype html>');
|
66 | if (hmr && !isFullPage && !config.buildOptions.htmlFragments) {
|
67 | throw new Error(`HTML fragment found!
|
68 | HTML fragments (files not starting with "<!doctype html>") are not transformed like full HTML pages.
|
69 | Add the missing doctype, or set buildOptions.htmlFragments=true if HTML fragments are expected.`);
|
70 | }
|
71 | if (hmr && isFullPage) {
|
72 | let hmrScript = ``;
|
73 | if (hmrPort) {
|
74 | hmrScript += `<script type="text/javascript">window.HMR_WEBSOCKET_PORT=${hmrPort}</script>\n`;
|
75 | }
|
76 | hmrScript += `<script type="module" integrity="${SRI_CLIENT_HMR_SNOWPACK}" src="${getMetaUrlPath('hmr-client.js', config)}"></script>`;
|
77 | if (config.devOptions.hmrErrorOverlay) {
|
78 | hmrScript += `<script type="module" integrity="${SRI_ERROR_HMR_SNOWPACK}" src="${getMetaUrlPath('hmr-error-overlay.js', config)}"></script>`;
|
79 | }
|
80 | code = util_1.appendHtmlToHead(code, hmrScript);
|
81 | }
|
82 | return code;
|
83 | }
|
84 | exports.wrapHtmlResponse = wrapHtmlResponse;
|
85 | function generateJsonImportProxy({ code, hmr, config, }) {
|
86 | const jsonImportProxyCode = `let json = ${JSON.stringify(JSON.parse(code))};
|
87 | export default json;`;
|
88 | return wrapImportMeta({ code: jsonImportProxyCode, hmr, env: false, config });
|
89 | }
|
90 | function generateCssImportProxy({ code, hmr, config, }) {
|
91 | const cssImportProxyCode = `// [snowpack] add styles to the page (skip if no document exists)
|
92 | if (typeof document !== 'undefined') {${hmr
|
93 | ? `
|
94 | import.meta.hot.accept();
|
95 | import.meta.hot.dispose(() => {
|
96 | document.head.removeChild(styleEl);
|
97 | });\n`
|
98 | : ''}
|
99 | const code = ${JSON.stringify(code)};
|
100 |
|
101 | const styleEl = document.createElement("style");
|
102 | const codeEl = document.createTextNode(code);
|
103 | styleEl.type = 'text/css';
|
104 | styleEl.appendChild(codeEl);
|
105 | document.head.appendChild(styleEl);
|
106 | }`;
|
107 | return wrapImportMeta({ code: cssImportProxyCode, hmr, env: false, config });
|
108 | }
|
109 | async function generateCssModuleImportProxy({ url, code, hmr, config, }) {
|
110 | let moduleJson;
|
111 | const processor = postcss_1.default([
|
112 | postcss_modules_1.default({
|
113 | getJSON: (_, json) => {
|
114 | moduleJson = json;
|
115 | },
|
116 | }),
|
117 | ]);
|
118 | const result = await processor.process(code, {
|
119 | from: url,
|
120 | to: url + '.proxy.js',
|
121 | });
|
122 |
|
123 | result
|
124 | .warnings()
|
125 | .forEach((element) => logger_1.logger.warn(`${url} - ${element.text}`, { name: 'snowpack:cssmodules' }));
|
126 |
|
127 | return `
|
128 | export let code = ${JSON.stringify(result.css)};
|
129 | let json = ${JSON.stringify(moduleJson)};
|
130 | export default json;
|
131 | ${hmr
|
132 | ? `
|
133 | import * as __SNOWPACK_HMR_API__ from '${getMetaUrlPath('hmr-client.js', config)}';
|
134 | import.meta.hot = __SNOWPACK_HMR_API__.createHotContext(import.meta.url);\n`
|
135 | : ``}
|
136 | // [snowpack] add styles to the page (skip if no document exists)
|
137 | if (typeof document !== 'undefined') {${hmr
|
138 | ? `
|
139 | import.meta.hot.dispose(() => {
|
140 | document && document.head.removeChild(styleEl);
|
141 | });\n`
|
142 | : ``}
|
143 | const styleEl = document.createElement("style");
|
144 | const codeEl = document.createTextNode(code);
|
145 | styleEl.type = 'text/css';
|
146 |
|
147 | styleEl.appendChild(codeEl);
|
148 | document.head.appendChild(styleEl);
|
149 | }`;
|
150 | }
|
151 | function generateDefaultImportProxy(url) {
|
152 | return `export default ${JSON.stringify(url)};`;
|
153 | }
|
154 | async function wrapImportProxy({ url, code, hmr, config, }) {
|
155 | if (typeof code === 'string') {
|
156 | if (util_1.hasExtension(url, '.json')) {
|
157 | return generateJsonImportProxy({ code, hmr, config });
|
158 | }
|
159 | if (util_1.hasExtension(url, '.css')) {
|
160 |
|
161 | const sanitized = code.replace(/\/\*#\s*sourceMappingURL=[^/]+\//gm, '');
|
162 | return util_1.hasExtension(url, '.module.css')
|
163 | ? generateCssModuleImportProxy({ url, code: sanitized, hmr, config })
|
164 | : generateCssImportProxy({ code: sanitized, hmr, config });
|
165 | }
|
166 | }
|
167 | return generateDefaultImportProxy(url);
|
168 | }
|
169 | exports.wrapImportProxy = wrapImportProxy;
|
170 | function generateEnvModule({ mode, isSSR, }) {
|
171 | const envObject = getSnowpackPublicEnvVariables();
|
172 | envObject.MODE = mode;
|
173 | envObject.NODE_ENV = mode;
|
174 | envObject.SSR = isSSR;
|
175 | return Object.entries(envObject)
|
176 | .map(([key, val]) => {
|
177 | return `export const ${key} = ${JSON.stringify(val)};`;
|
178 | })
|
179 | .join('\n');
|
180 | }
|
181 | exports.generateEnvModule = generateEnvModule;
|
182 | const PUBLIC_ENV_REGEX = /^SNOWPACK_PUBLIC_.+/;
|
183 | function getSnowpackPublicEnvVariables() {
|
184 | const envObject = { ...process.env };
|
185 | for (const env of Object.keys(envObject)) {
|
186 | if (!PUBLIC_ENV_REGEX.test(env)) {
|
187 | delete envObject[env];
|
188 | }
|
189 | }
|
190 | return envObject;
|
191 | }
|