From ca502d80b131ad8450e9a020bc34f8857adb1c99 Mon Sep 17 00:00:00 2001 From: hiyuki <674883329@qq.com> Date: Thu, 7 Dec 2023 16:57:35 +0800 Subject: [PATCH 1/4] support web async subpackages --- packages/webpack-plugin/lib/index.js | 78 +++++++++++-------- .../lib/json-compiler/helper.js | 13 ++-- .../webpack-plugin/lib/json-compiler/index.js | 4 +- .../webpack-plugin/lib/web/processJSON.js | 7 +- 4 files changed, 60 insertions(+), 42 deletions(-) diff --git a/packages/webpack-plugin/lib/index.js b/packages/webpack-plugin/lib/index.js index 226f77fbe8..252395b3d8 100644 --- a/packages/webpack-plugin/lib/index.js +++ b/packages/webpack-plugin/lib/index.js @@ -15,6 +15,8 @@ const EntryPlugin = require('webpack/lib/EntryPlugin') const JavascriptModulesPlugin = require('webpack/lib/javascript/JavascriptModulesPlugin') const FlagEntryExportAsUsedPlugin = require('webpack/lib/FlagEntryExportAsUsedPlugin') const FileSystemInfo = require('webpack/lib/FileSystemInfo') +const ImportDependency = require('webpack/lib/dependencies/ImportDependency') +const AsyncDependenciesBlock = require('webpack/lib/AsyncDependenciesBlock') const normalize = require('./utils/normalize') const toPosix = require('./utils/to-posix') const addQuery = require('./utils/add-query') @@ -328,33 +330,31 @@ class MpxWebpackPlugin { let splitChunksPlugin let splitChunksOptions - if (this.options.mode !== 'web') { - const optimization = compiler.options.optimization - optimization.runtimeChunk = { - name: (entrypoint) => { - for (const packageName in mpx.independentSubpackagesMap) { - if (hasOwn(mpx.independentSubpackagesMap, packageName) && isChunkInPackage(entrypoint.name, packageName)) { - return `${packageName}/bundle` - } + const optimization = compiler.options.optimization + optimization.runtimeChunk = { + name: (entrypoint) => { + for (const packageName in mpx.independentSubpackagesMap) { + if (hasOwn(mpx.independentSubpackagesMap, packageName) && isChunkInPackage(entrypoint.name, packageName)) { + return `${packageName}/bundle` } - return 'bundle' } + return 'bundle' } - splitChunksOptions = Object.assign({ - defaultSizeTypes: ['javascript', 'unknown'], - chunks: 'all', - usedExports: optimization.usedExports === true, - minChunks: 1, - minSize: 1000, - enforceSizeThreshold: Infinity, - maxAsyncRequests: 30, - maxInitialRequests: 30, - automaticNameDelimiter: '-' - }, optimization.splitChunks) - delete optimization.splitChunks - splitChunksPlugin = new SplitChunksPlugin(splitChunksOptions) - splitChunksPlugin.apply(compiler) } + splitChunksOptions = Object.assign({ + defaultSizeTypes: ['javascript', 'unknown'], + chunks: 'all', + usedExports: optimization.usedExports === true, + minChunks: 1, + minSize: 1000, + enforceSizeThreshold: Infinity, + maxAsyncRequests: 30, + maxInitialRequests: 30, + automaticNameDelimiter: '-' + }, optimization.splitChunks) + delete optimization.splitChunks + splitChunksPlugin = new SplitChunksPlugin(splitChunksOptions) + splitChunksPlugin.apply(compiler) // 代理writeFile if (this.options.writeMode === 'changed') { @@ -635,7 +635,7 @@ class MpxWebpackPlugin { useRelativePath: this.options.useRelativePath, removedChunks: [], forceProxyEventRules: this.options.forceProxyEventRules, - enableRequireAsync: this.options.mode === 'wx' || (this.options.mode === 'ali' && this.options.enableAliRequireAsync), + supportRequireAsync: this.options.mode === 'wx' || this.options.mode === 'web' || (this.options.mode === 'ali' && this.options.enableAliRequireAsync), partialCompile: this.options.partialCompile, collectDynamicEntryInfo: ({ resource, packageName, filename, entryType }) => { const curInfo = mpx.dynamicEntryInfo[packageName] = mpx.dynamicEntryInfo[packageName] || { @@ -1093,15 +1093,29 @@ class MpxWebpackPlugin { // 删除root query if (queryObj.root) request = addQuery(request, {}, false, ['root']) // 目前仅wx和ali支持require.async,ali需要开启enableAliRequireAsync,其余平台使用CommonJsAsyncDependency进行模拟抹平 - if (mpx.enableRequireAsync) { - const dep = new DynamicEntryDependency(request, 'export', '', tarRoot, '', context, range, { - isRequireAsync: true, - retryRequireAsync: !!this.options.retryRequireAsync - }) + if (mpx.supportRequireAsync) { + if (mpx.mode === 'web') { + const depBlock = new AsyncDependenciesBlock( + { + name: tarRoot + }, + expr.loc, + request + ) + const dep = new ImportDependency(request, expr.range) + dep.loc = expr.loc + depBlock.addDependency(dep) + parser.state.current.addBlock(depBlock) + } else { + const dep = new DynamicEntryDependency(request, 'export', '', tarRoot, '', context, range, { + isRequireAsync: true, + retryRequireAsync: !!this.options.retryRequireAsync + }) - parser.state.current.addPresentationalDependency(dep) - // 包含require.async的模块不能被concatenate,避免DynamicEntryDependency中无法获取模块chunk以计算相对路径 - parser.state.module.buildInfo.moduleConcatenationBailout = 'require async' + parser.state.current.addPresentationalDependency(dep) + // 包含require.async的模块不能被concatenate,避免DynamicEntryDependency中无法获取模块chunk以计算相对路径 + parser.state.module.buildInfo.moduleConcatenationBailout = 'require async' + } } else { const range = expr.range const dep = new CommonJsAsyncDependency(request, range) diff --git a/packages/webpack-plugin/lib/json-compiler/helper.js b/packages/webpack-plugin/lib/json-compiler/helper.js index 33cc2754f9..94ae2fd177 100644 --- a/packages/webpack-plugin/lib/json-compiler/helper.js +++ b/packages/webpack-plugin/lib/json-compiler/helper.js @@ -17,7 +17,7 @@ module.exports = function createJSONHelper ({ loaderContext, emitWarning, custom const pathHash = mpx.pathHash const getOutputPath = mpx.getOutputPath const mode = mpx.mode - const enableRequireAsync = mpx.enableRequireAsync + const supportRequireAsync = mpx.supportRequireAsync const asyncSubpackageRules = mpx.asyncSubpackageRules const isUrlRequest = r => isUrlRequestRaw(r, root, externals) @@ -51,15 +51,15 @@ module.exports = function createJSONHelper ({ loaderContext, emitWarning, custom resolve(context, component, loaderContext, (err, resource, info) => { if (err) return callback(err) const { resourcePath, queryObj } = parseRequest(resource) - let placeholder = null + let placeholder = '' if (queryObj.root) { // 删除root query resource = addQuery(resource, {}, false, ['root']) // 目前只有微信支持分包异步化 - if (enableRequireAsync) { + if (supportRequireAsync) { tarRoot = queryObj.root } - } else if (!queryObj.root && asyncSubpackageRules && enableRequireAsync) { + } else if (!queryObj.root && asyncSubpackageRules && supportRequireAsync) { for (const item of asyncSubpackageRules) { if (matchCondition(resourcePath, item)) { tarRoot = item.root @@ -97,7 +97,10 @@ module.exports = function createJSONHelper ({ loaderContext, emitWarning, custom } const entry = getDynamicEntry(resource, 'component', outputPath, tarRoot, relativePath) - callback(null, entry, tarRoot, placeholder) + callback(null, entry, { + tarRoot, + placeholder + }) }) } diff --git a/packages/webpack-plugin/lib/json-compiler/index.js b/packages/webpack-plugin/lib/json-compiler/index.js index 470fa96375..785a83535c 100644 --- a/packages/webpack-plugin/lib/json-compiler/index.js +++ b/packages/webpack-plugin/lib/json-compiler/index.js @@ -211,14 +211,14 @@ module.exports = function (content) { const processComponents = (components, context, callback) => { if (components) { async.eachOf(components, (component, name, callback) => { - processComponent(component, context, { relativePath }, (err, entry, root, placeholder) => { + processComponent(component, context, { relativePath }, (err, entry, { tarRoot, placeholder }) => { if (err === RESOLVE_IGNORED_ERR) { delete components[name] return callback() } if (err) return callback(err) components[name] = entry - if (root) { + if (tarRoot) { if (placeholder) { placeholder = normalizePlaceholder(placeholder) if (placeholder.resource) { diff --git a/packages/webpack-plugin/lib/web/processJSON.js b/packages/webpack-plugin/lib/web/processJSON.js index eaeedd99f8..e85f0dc5c2 100644 --- a/packages/webpack-plugin/lib/web/processJSON.js +++ b/packages/webpack-plugin/lib/web/processJSON.js @@ -61,7 +61,8 @@ module.exports = function (json, { customGetDynamicEntry (resource, type, outputPath, packageRoot) { return { resource, - outputPath: toPosix(path.join(packageRoot, outputPath)), + // 输出web时组件outputPath不需要拼接packageRoot + outputPath: type === 'page' ? toPosix(path.join(packageRoot, outputPath)) : outputPath, packageRoot } } @@ -297,7 +298,7 @@ module.exports = function (json, { const processComponents = (components, context, callback) => { if (components) { async.eachOf(components, (component, name, callback) => { - processComponent(component, context, {}, (err, { resource, outputPath } = {}) => { + processComponent(component, context, {}, (err, { resource, outputPath } = {}, { tarRoot } = {}) => { if (err) return callback(err === RESOLVE_IGNORED_ERR ? null : err) const { resourcePath, queryObj } = parseRequest(resource) componentsMap[resourcePath] = outputPath @@ -307,7 +308,7 @@ module.exports = function (json, { isComponent: true, outputPath }), - async: queryObj.async + async: queryObj.async || tarRoot } callback() }) From 5a674a9305467277137181112c6522fe831e7c4b Mon Sep 17 00:00:00 2001 From: hiyuki <674883329@qq.com> Date: Thu, 7 Dec 2023 17:00:05 +0800 Subject: [PATCH 2/4] fix lint --- packages/webpack-plugin/lib/index.js | 7 ++----- 1 file changed, 2 insertions(+), 5 deletions(-) diff --git a/packages/webpack-plugin/lib/index.js b/packages/webpack-plugin/lib/index.js index 252395b3d8..5328df02ab 100644 --- a/packages/webpack-plugin/lib/index.js +++ b/packages/webpack-plugin/lib/index.js @@ -327,9 +327,6 @@ class MpxWebpackPlugin { compiler.options.resolve.plugins.push(packageEntryPlugin) compiler.options.resolve.plugins.push(new FixDescriptionInfoPlugin()) - let splitChunksPlugin - let splitChunksOptions - const optimization = compiler.options.optimization optimization.runtimeChunk = { name: (entrypoint) => { @@ -341,7 +338,7 @@ class MpxWebpackPlugin { return 'bundle' } } - splitChunksOptions = Object.assign({ + const splitChunksOptions = Object.assign({ defaultSizeTypes: ['javascript', 'unknown'], chunks: 'all', usedExports: optimization.usedExports === true, @@ -353,7 +350,7 @@ class MpxWebpackPlugin { automaticNameDelimiter: '-' }, optimization.splitChunks) delete optimization.splitChunks - splitChunksPlugin = new SplitChunksPlugin(splitChunksOptions) + const splitChunksPlugin = new SplitChunksPlugin(splitChunksOptions) splitChunksPlugin.apply(compiler) // 代理writeFile From 0c6800cb1e8fcaf6bebf94d678ccb0480f2bcb64 Mon Sep 17 00:00:00 2001 From: hiyuki <674883329@qq.com> Date: Thu, 7 Dec 2023 17:00:13 +0800 Subject: [PATCH 3/4] v2.9.8 --- lerna.json | 2 +- packages/webpack-plugin/package.json | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/lerna.json b/lerna.json index eaaa6aff15..d511221f77 100644 --- a/lerna.json +++ b/lerna.json @@ -2,5 +2,5 @@ "packages": [ "packages/*" ], - "version": "2.9.7" + "version": "2.9.8" } diff --git a/packages/webpack-plugin/package.json b/packages/webpack-plugin/package.json index 7850dbd072..75e00d88f0 100644 --- a/packages/webpack-plugin/package.json +++ b/packages/webpack-plugin/package.json @@ -1,6 +1,6 @@ { "name": "@mpxjs/webpack-plugin", - "version": "2.9.7", + "version": "2.9.8", "description": "mpx compile core", "keywords": [ "mpx" From 4c788de69ead7dc6f94379cc16aeb6dfec3b273d Mon Sep 17 00:00:00 2001 From: hiyuki <674883329@qq.com> Date: Thu, 7 Dec 2023 17:33:19 +0800 Subject: [PATCH 4/4] fix unit --- packages/webpack-plugin/lib/json-compiler/index.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/webpack-plugin/lib/json-compiler/index.js b/packages/webpack-plugin/lib/json-compiler/index.js index 785a83535c..f28b76f9a2 100644 --- a/packages/webpack-plugin/lib/json-compiler/index.js +++ b/packages/webpack-plugin/lib/json-compiler/index.js @@ -211,7 +211,7 @@ module.exports = function (content) { const processComponents = (components, context, callback) => { if (components) { async.eachOf(components, (component, name, callback) => { - processComponent(component, context, { relativePath }, (err, entry, { tarRoot, placeholder }) => { + processComponent(component, context, { relativePath }, (err, entry, { tarRoot, placeholder } = {}) => { if (err === RESOLVE_IGNORED_ERR) { delete components[name] return callback()