diff --git a/packages/toolkit/config/webpack.config.js b/packages/toolkit/config/webpack.config.js index 17251ce8..32a2c6cb 100644 --- a/packages/toolkit/config/webpack.config.js +++ b/packages/toolkit/config/webpack.config.js @@ -49,13 +49,10 @@ const config = { defaultTargets, }; -module.exports = { +const baseConfig = { devtool: !isProduction || projectConfig.sourcemap ? 'source-map' : false, mode, devServer: getDevServer(config), - // using a function here in order to re-evaluate - // the entrypoints whenever something changes - entry: () => getEntryPoints(config), output: getOutput(config), target: getTarget(config), resolve: getResolve(config), @@ -69,3 +66,33 @@ module.exports = { outputModule: packageConfig.packageType === 'module', }, }; + +const scriptsConfig = { + ...baseConfig, + entry: () => getEntryPoints({ ...config, buildType: 'script' }), +}; + +const moduleConfig = { + ...baseConfig, + + entry: () => getEntryPoints({ ...config, buildType: 'module' }), + plugins: getPlugins({ ...config, isModule: true }), + + experiments: { + ...baseConfig.experiments, + outputModule: true, + }, + + output: { + clean: false, + module: true, + chunkFormat: 'module', + library: { + ...baseConfig.output.library, + type: 'module', + }, + filename: 'blocks/[name].js', + }, +}; + +module.exports = [scriptsConfig, moduleConfig]; diff --git a/packages/toolkit/config/webpack/entry.js b/packages/toolkit/config/webpack/entry.js index f94877f9..5f66b3af 100644 --- a/packages/toolkit/config/webpack/entry.js +++ b/packages/toolkit/config/webpack/entry.js @@ -7,6 +7,7 @@ const removeDistFolder = (file) => { }; module.exports = ({ + buildType = 'script', isPackage, projectConfig: { devServer, paths, useBlockAssets, filenames }, packageConfig: { packageType, source, main, umd, libraryName }, @@ -36,12 +37,31 @@ module.exports = ({ // at which point they are completely empty and therefore not valid JSON try { // get all assets from the block.json file - const { editorScript, script, viewScript, style, editorStyle } = JSON.parse( - readFileSync(blockMetadataFile), - ); + const { + editorScript, + script, + viewScript, + scriptModule, + viewScriptModule, + style, + editorStyle, + viewStyle, + } = JSON.parse(readFileSync(blockMetadataFile)); + + const assets = []; + + if (buildType === 'script') { + assets.push( + ...[editorScript, script, viewScript, style, editorStyle, viewStyle].filter( + Boolean, + ), + ); + } else if (buildType === 'module') { + assets.push(...[scriptModule, viewScriptModule].filter(Boolean)); + } // generate a new entrypoint for each of the assets - [editorScript, script, viewScript, style, editorStyle] + assets .flat() .filter((rawFilepath) => rawFilepath && rawFilepath.startsWith('file:')) // assets can be files or handles. we only want files .forEach((rawFilepath) => { @@ -84,6 +104,10 @@ module.exports = ({ }, {}); } + if (buildType === 'module') { + return additionalEntrypoints; + } + // merge the new entrypoints with the existing ones Object.assign(buildFiles, additionalEntrypoints); diff --git a/packages/toolkit/config/webpack/output.js b/packages/toolkit/config/webpack/output.js index e0e86ae4..cc463779 100644 --- a/packages/toolkit/config/webpack/output.js +++ b/packages/toolkit/config/webpack/output.js @@ -23,7 +23,7 @@ module.exports = ({ return { // when in hot reload mode we should not clear dist folder between builds - clean: !hot, + clean: false, path: path.resolve(process.cwd(), 'dist'), chunkFilename: filenames.jsChunk, publicPath, diff --git a/packages/toolkit/config/webpack/plugins.js b/packages/toolkit/config/webpack/plugins.js index 3567ac11..eaf0a0b6 100644 --- a/packages/toolkit/config/webpack/plugins.js +++ b/packages/toolkit/config/webpack/plugins.js @@ -34,6 +34,7 @@ const webpackbarArguments = module.exports = ({ isPackage, + isModule = false, isProduction, projectConfig: { devServer, @@ -202,6 +203,10 @@ module.exports = ({ injectPolyfill: false, requestToHandle: (request) => { if (request.includes('react-refresh/runtime')) { + if (isModule) { + return undefined; + } + return 'tenup-toolkit-react-refresh-runtime'; } diff --git a/projects/10up-theme/includes/blocks/example/block.json b/projects/10up-theme/includes/blocks/example/block.json index a8bd8bca..15e0b060 100644 --- a/projects/10up-theme/includes/blocks/example/block.json +++ b/projects/10up-theme/includes/blocks/example/block.json @@ -36,11 +36,13 @@ "reusable": false, "spacing": { "padding": false - } + }, + "interactivity": true }, "editorScript": "file:./index.js", "editorStyle": "file:./editor.css", "style": "file:./style.css", "viewScript": "file:./view.js", + "viewScriptModule": "file:./view-module.js", "script": "file:./script.js" } diff --git a/projects/10up-theme/includes/blocks/example/markup.php b/projects/10up-theme/includes/blocks/example/markup.php index 62760819..978578f0 100644 --- a/projects/10up-theme/includes/blocks/example/markup.php +++ b/projects/10up-theme/includes/blocks/example/markup.php @@ -11,8 +11,9 @@ */ ?> -
> +
'example']); // phpcs:ignore ?>>

+
diff --git a/projects/10up-theme/includes/blocks/example/view-module.js b/projects/10up-theme/includes/blocks/example/view-module.js new file mode 100644 index 00000000..0e8f3649 --- /dev/null +++ b/projects/10up-theme/includes/blocks/example/view-module.js @@ -0,0 +1,11 @@ +import { store } from '@wordpress/interactivity'; + +store('example', { + actions: { + toggle: () => { + console.log('Hello, world!'); + }, + }, +}); + +console.log('Loaded');