From 5607c5210f591b525cdf1a2547594fd3bb6e0814 Mon Sep 17 00:00:00 2001 From: rixo Date: Tue, 6 Oct 2020 00:04:48 +0200 Subject: [PATCH 1/6] adding svelte-hmr --- plugins/plugin-svelte/package.json | 3 ++- plugins/plugin-svelte/plugin.js | 41 +++++++++++++++++++++++++----- yarn.lock | 5 ++++ 3 files changed, 41 insertions(+), 8 deletions(-) diff --git a/plugins/plugin-svelte/package.json b/plugins/plugin-svelte/package.json index fec976c870..af321024b8 100644 --- a/plugins/plugin-svelte/package.json +++ b/plugins/plugin-svelte/package.json @@ -13,7 +13,8 @@ "access": "public" }, "peerDependencies": { - "svelte": "^3.21.0" + "svelte": "^3.21.0", + "svelte-hmr": "^0.11.1" }, "gitHead": "a01616bb0787d56cd782f94cecf2daa12c7594e4", "dependencies": { diff --git a/plugins/plugin-svelte/plugin.js b/plugins/plugin-svelte/plugin.js index 8d7314f5d2..4dd98fba5b 100644 --- a/plugins/plugin-svelte/plugin.js +++ b/plugins/plugin-svelte/plugin.js @@ -2,8 +2,11 @@ const svelte = require('svelte/compiler'); const svelteRollupPlugin = require('rollup-plugin-svelte'); const fs = require('fs'); const path = require('path'); +const {createMakeHot} = require('svelte-hmr'); -module.exports = function plugin(snowpackConfig, pluginOptions = {}) { +const makeHot = createMakeHot({walk: svelte.walk}); + +module.exports = function plugin(snowpackConfig, {hot: hotOptions, ...sveltePluginOptions} = {}) { const isDev = process.env.NODE_ENV !== 'production'; // Support importing Svelte files when you install dependencies. @@ -25,7 +28,7 @@ module.exports = function plugin(snowpackConfig, pluginOptions = {}) { dev: isDev, css: false, ...svelteOptions, - ...pluginOptions, + ...sveltePluginOptions, }; return { @@ -34,9 +37,13 @@ module.exports = function plugin(snowpackConfig, pluginOptions = {}) { input: ['.svelte'], output: ['.js', '.css'], }, - knownEntrypoints: ['svelte/internal'], - async load({filePath, isSSR}) { - let codeToCompile = fs.readFileSync(filePath, 'utf-8'); + knownEntrypoints: [ + 'svelte/internal', + 'svelte-hmr/runtime/hot-api-esm.js', + 'svelte-hmr/runtime/proxy-adapter-dom.js', + ], + async load({filePath, isHmrEnabled, isSSR}) { + let codeToCompile = await fs.promises.readFile(filePath, 'utf-8'); // PRE-PROCESS if (preprocessOptions) { codeToCompile = ( @@ -53,12 +60,16 @@ module.exports = function plugin(snowpackConfig, pluginOptions = {}) { ssrOptions.css = true; } - const {js, css} = svelte.compile(codeToCompile, { + const compileOptions = { ...svelteOptions, ...ssrOptions, outputFilename: filePath, filename: filePath, - }); + }; + + const compiled = svelte.compile(codeToCompile, compileOptions); + + const {js, css} = compiled; const {sourceMaps} = snowpackConfig.buildOptions; const output = { @@ -67,6 +78,22 @@ module.exports = function plugin(snowpackConfig, pluginOptions = {}) { map: sourceMaps ? js.map : undefined, }, }; + + if (isHmrEnabled && !isSSR) { + output['.js'].code = makeHot({ + id: filePath, + compiledCode: compiled.js.code, + hotOptions: { + ...hotOptions, + absoluteImports: false, + injectCss: false, + }, + compiled, + originalCode: codeToCompile, + compileOptions, + }); + } + if (!svelteOptions.css && css && css.code) { output['.css'] = { code: css.code, diff --git a/yarn.lock b/yarn.lock index 9f552bd395..48fe35e8c9 100644 --- a/yarn.lock +++ b/yarn.lock @@ -13076,6 +13076,11 @@ svelte-check@^1.0.0: vscode-languageserver-types "3.15.1" vscode-uri "2.1.2" +svelte-hmr@^0.11.1: + version "0.11.1" + resolved "https://registry.yarnpkg.com/svelte-hmr/-/svelte-hmr-0.11.1.tgz#8789db456a068e49d7813bf8a59beed49971f7c6" + integrity sha512-ecW9G/Pp7+RXXFvoWcF1WQsdajgigtdFH6qe25kMggmidvqTrzThkfELfR8cgnWng6eNVV4Y70vvb4MI/3N7OQ== + svelte-language-server@*: version "0.10.133" resolved "https://registry.yarnpkg.com/svelte-language-server/-/svelte-language-server-0.10.133.tgz#e5d121a1a27090076e6c6c046b1aeeb45b5d0b93" From 6f2af1d59bdfd2667f341efc8e9e15231ba9eb8a Mon Sep 17 00:00:00 2001 From: rixo Date: Tue, 6 Oct 2020 00:45:27 +0200 Subject: [PATCH 2/6] make svelte-hmr a normal dep of the plugin, & lazy load svelte-hmr --- plugins/plugin-svelte/package.json | 6 +++--- plugins/plugin-svelte/plugin.js | 5 ++++- 2 files changed, 7 insertions(+), 4 deletions(-) diff --git a/plugins/plugin-svelte/package.json b/plugins/plugin-svelte/package.json index af321024b8..54e19c5e17 100644 --- a/plugins/plugin-svelte/package.json +++ b/plugins/plugin-svelte/package.json @@ -13,11 +13,11 @@ "access": "public" }, "peerDependencies": { - "svelte": "^3.21.0", - "svelte-hmr": "^0.11.1" + "svelte": "^3.21.0" }, "gitHead": "a01616bb0787d56cd782f94cecf2daa12c7594e4", "dependencies": { - "rollup-plugin-svelte": "^5.2.3" + "rollup-plugin-svelte": "^5.2.3", + "svelte-hmr": "^0.11.1" } } diff --git a/plugins/plugin-svelte/plugin.js b/plugins/plugin-svelte/plugin.js index 4dd98fba5b..83b2ac18e5 100644 --- a/plugins/plugin-svelte/plugin.js +++ b/plugins/plugin-svelte/plugin.js @@ -4,7 +4,10 @@ const fs = require('fs'); const path = require('path'); const {createMakeHot} = require('svelte-hmr'); -const makeHot = createMakeHot({walk: svelte.walk}); +let makeHot = (...args) => { + makeHot = createMakeHot({walk: svelte.walk}); + return makeHot(...args) +} module.exports = function plugin(snowpackConfig, {hot: hotOptions, ...sveltePluginOptions} = {}) { const isDev = process.env.NODE_ENV !== 'production'; From 9456bebde7e7edfbdaf3ed443c62fa0648bd6240 Mon Sep 17 00:00:00 2001 From: rixo Date: Tue, 6 Oct 2020 23:19:27 +0200 Subject: [PATCH 3/6] plugin svelte: document HMR options --- plugins/plugin-svelte/README.md | 27 ++++++++++++++++++++++++++- 1 file changed, 26 insertions(+), 1 deletion(-) diff --git a/plugins/plugin-svelte/README.md b/plugins/plugin-svelte/README.md index 8488f0f0d3..d55cedaf6f 100644 --- a/plugins/plugin-svelte/README.md +++ b/plugins/plugin-svelte/README.md @@ -15,6 +15,31 @@ npm install --save-dev @snowpack/plugin-svelte } ``` -#### Plugin Options +## Plugin Options This plugin also supports all Svelte compiler options. See [here](https://svelte.dev/docs#svelte_compile) for a list of supported options. + +### HMR Options + +You can pass Svelte HMR specific options through the `hot` option of the plugin. Here are the available options and their defaults: + +```js +{ + "plugins": [ + ["@snowpack/plugin-svelte", { + hot: { + // don't preserve local state + noPreserveState: false, + // escape hatch from preserve local state -- if this string appears anywhere + // in the component's code, then state won't be preserved for this update + noPreserveStateKey: '@!hmr', + // don't reload on fatal error + noReload: false, + // try to recover after runtime errors during component init + optimistic: false, + }, + }] + ] +} +``` + From e07758ec3b1690368416d4cd3a446f8538f53385 Mon Sep 17 00:00:00 2001 From: "Fred K. Schott" Date: Tue, 6 Oct 2020 14:50:31 -0700 Subject: [PATCH 4/6] add bubbled esm-hmr property --- snowpack/assets/hmr-client.js | 6 +++--- snowpack/src/commands/dev.ts | 5 +++-- snowpack/src/hmr-server-engine.ts | 2 +- 3 files changed, 7 insertions(+), 6 deletions(-) diff --git a/snowpack/assets/hmr-client.js b/snowpack/assets/hmr-client.js index ab137dac37..e2e1918a0c 100644 --- a/snowpack/assets/hmr-client.js +++ b/snowpack/assets/hmr-client.js @@ -110,7 +110,7 @@ export function createHotContext(fullUrl) { } /** Called when a new module is loaded, to pass the updated module to the "active" module */ -async function runModuleAccept(id) { +async function runModuleAccept({url: id, bubbled}) { const state = REGISTERED_MODULES[id]; if (!state) { return false; @@ -125,7 +125,7 @@ async function runModuleAccept(id) { import(id + `?mtime=${updateID}`), ...deps.map((d) => import(d + `?mtime=${updateID}`)), ]); - acceptCallback({module, deps: depModules}); + acceptCallback({module, bubbled, deps: depModules}); } return true; } @@ -165,7 +165,7 @@ socket.addEventListener('message', ({data: _data}) => { } if (data.type === 'update') { log('message: update', data); - runModuleAccept(data.url) + runModuleAccept(data) .then((ok) => { if (ok) { clearErrorOverlay(); diff --git a/snowpack/src/commands/dev.ts b/snowpack/src/commands/dev.ts index 1142141f7d..50ad8c886e 100644 --- a/snowpack/src/commands/dev.ts +++ b/snowpack/src/commands/dev.ts @@ -970,11 +970,12 @@ export async function startServer(commandOptions: CommandOptions) { if (visited.has(url)) { return; } - visited.add(url); const node = hmrEngine.getEntry(url); + const isBubbled = visited.size > 0; if (node && node.isHmrEnabled) { - hmrEngine.broadcastMessage({type: 'update', url}); + hmrEngine.broadcastMessage({type: 'update', url, bubbled: isBubbled}); } + visited.add(url); if (node && node.isHmrAccepted) { // Found a boundary, no bubbling needed } else if (node && node.dependents.size > 0) { diff --git a/snowpack/src/hmr-server-engine.ts b/snowpack/src/hmr-server-engine.ts index e6beec9bf0..e236649782 100644 --- a/snowpack/src/hmr-server-engine.ts +++ b/snowpack/src/hmr-server-engine.ts @@ -14,7 +14,7 @@ interface Dependency { type HMRMessage = | {type: 'reload'} - | {type: 'update'; url: string} + | {type: 'update'; url: string; bubbled: boolean;} | { type: 'error'; title: string; From d009e593f96c2567ac07e52a9994902e03bb950e Mon Sep 17 00:00:00 2001 From: rixo Date: Wed, 7 Oct 2020 00:55:28 +0200 Subject: [PATCH 5/6] svelte plugin: upgrade svelte-hmr, & enable CSS only updates --- plugins/plugin-svelte/package.json | 2 +- plugins/plugin-svelte/plugin.js | 2 +- yarn.lock | 8 ++++---- 3 files changed, 6 insertions(+), 6 deletions(-) diff --git a/plugins/plugin-svelte/package.json b/plugins/plugin-svelte/package.json index 67d9ffb1b0..247f5052fd 100644 --- a/plugins/plugin-svelte/package.json +++ b/plugins/plugin-svelte/package.json @@ -18,6 +18,6 @@ "gitHead": "a01616bb0787d56cd782f94cecf2daa12c7594e4", "dependencies": { "rollup-plugin-svelte": "^5.2.3", - "svelte-hmr": "^0.11.1" + "svelte-hmr": "^0.11.2-1" } } diff --git a/plugins/plugin-svelte/plugin.js b/plugins/plugin-svelte/plugin.js index 7bb0b413cd..ecd49b6a58 100644 --- a/plugins/plugin-svelte/plugin.js +++ b/plugins/plugin-svelte/plugin.js @@ -82,7 +82,7 @@ module.exports = function plugin(snowpackConfig, {hot: hotOptions, ...sveltePlug hotOptions: { ...hotOptions, absoluteImports: false, - injectCss: false, + injectCss: true, }, compiled, originalCode: codeToCompile, diff --git a/yarn.lock b/yarn.lock index 1456122ae8..020a1b3f90 100644 --- a/yarn.lock +++ b/yarn.lock @@ -12907,10 +12907,10 @@ svelte-check@^1.0.0: vscode-languageserver-types "3.15.1" vscode-uri "2.1.2" -svelte-hmr@^0.11.1: - version "0.11.1" - resolved "https://registry.yarnpkg.com/svelte-hmr/-/svelte-hmr-0.11.1.tgz#8789db456a068e49d7813bf8a59beed49971f7c6" - integrity sha512-ecW9G/Pp7+RXXFvoWcF1WQsdajgigtdFH6qe25kMggmidvqTrzThkfELfR8cgnWng6eNVV4Y70vvb4MI/3N7OQ== +svelte-hmr@^0.11.2-1: + version "0.11.2-1" + resolved "https://registry.yarnpkg.com/svelte-hmr/-/svelte-hmr-0.11.2-1.tgz#ce1b481a2489697ccf7aa405bccae1421ce80011" + integrity sha512-VanuFg1OiMvLjs44jo8+qnZnKfQGfflNRf8hETUhOs28J5V4xsCgU2NJHy+3iTVgEX1+a41zIEIBgquh02o9bQ== svelte-language-server@*: version "0.10.133" From b8386b248c4a493afcb646ae5d696955bda9aa76 Mon Sep 17 00:00:00 2001 From: "Fred K. Schott" Date: Wed, 7 Oct 2020 18:04:46 -0700 Subject: [PATCH 6/6] Update plugin.js --- plugins/plugin-svelte/plugin.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/plugins/plugin-svelte/plugin.js b/plugins/plugin-svelte/plugin.js index a4b003375b..fbcb532584 100644 --- a/plugins/plugin-svelte/plugin.js +++ b/plugins/plugin-svelte/plugin.js @@ -21,7 +21,7 @@ module.exports = function plugin(snowpackConfig, {hot: hotOptions, ...sveltePlug let preprocessOptions; // Note(drew): __config is for internal testing use; maybe we should make this public at some point? const userSvelteConfigLoc = - pluginOptions.__config || path.join(process.cwd(), 'svelte.config.js'); + sveltePluginOptions.__config || path.join(process.cwd(), 'svelte.config.js'); if (fs.existsSync(userSvelteConfigLoc)) { const userSvelteConfig = require(userSvelteConfigLoc); const {preprocess, ..._svelteOptions} = userSvelteConfig;