提交 e3800009 编写于 作者: Q qiang

feat(vue-cli-plugin-uni): support webpack5

上级 05275209
const path = require('path')
const webpack = require('webpack')
const {
runByHBuilderX,
......@@ -98,14 +99,18 @@ function getWebpackConfig (api, args, options) {
if (args.minimize && process.env.NODE_ENV !== 'production') {
modifyConfig(webpackConfig, config => {
config.optimization.minimize = true
if (webpack.version[0] <= 4) {
config.optimization.namedModules = false
}
})
} else {
modifyConfig(webpackConfig, config => {
if (!config.optimization) {
config.optimization = {}
}
if (webpack.version[0] <= 4) {
config.optimization.namedModules = false
}
})
}
return webpackConfig
......@@ -131,7 +136,6 @@ function getWebpackConfigs (api, args, options) {
async function build (args, api, options) {
const fs = require('fs-extra')
const chalk = require('chalk')
const webpack = require('webpack')
const {
log,
......
......@@ -37,7 +37,7 @@ module.exports = (api, options) => {
const url = require('url')
const path = require('path')
const chalk = require('chalk')
const { chalk } = require('@vue/cli-shared-utils')
const webpack = require('webpack')
const WebpackDevServer = require('webpack-dev-server')
const portfinder = require('portfinder')
......@@ -139,7 +139,56 @@ module.exports = (api, options) => {
const compiler = webpack(webpackConfig)
// create server
const server = new WebpackDevServer(compiler, Object.assign({
let server
if (webpack.version[0] > 4) {
server = new WebpackDevServer(Object.assign({
historyApiFallback: {
disableDotRule: true,
rewrites: [{
from: /./,
to: path.posix.join(options.publicPath, 'index.html')
}]
},
hot: !isProduction,
compress: isProduction,
static: {
directory: api.resolve('public'),
publicPath: options.publicPath,
watch: !isProduction,
...projectDevServerOptions.static
},
client: {
logging: 'none',
overlay: isProduction // TODO disable this
? false
: { warnings: false, errors: true },
progress: !process.env.VUE_CLI_TEST,
...projectDevServerOptions.client
}
}, projectDevServerOptions, {
https: useHttps,
proxy: proxySettings,
setupMiddlewares (middlewares, devServer) {
// launch editor support.
// this works with vue-devtools & @vue/cli-overlay
devServer.app.use('/__open-in-editor', launchEditorMiddleware(() => console.log(
`To specify an editor, specify the EDITOR env variable or ` +
`add "editor" field to your Vue project config.\n`
)))
// allow other plugins to register middlewares, e.g. PWA
// todo: migrate to the new API interface
api.service.devServerConfigFns.forEach(fn => fn(devServer.app, devServer))
if (projectDevServerOptions.setupMiddlewares) {
return projectDevServerOptions.setupMiddlewares(middlewares, devServer)
}
return middlewares
}
}), compiler)
} else {
server = new WebpackDevServer(compiler, Object.assign({
clientLogLevel: 'none',
historyApiFallback: {
disableDotRule: true,
......@@ -176,11 +225,12 @@ module.exports = (api, options) => {
server)
}
}))
}
;
['SIGINT', 'SIGTERM'].forEach(signal => {
process.on(signal, () => {
server.close(() => {
server[webpack.version[0] > 4 ? 'stopCallback' : 'close'](() => {
process.exit(0)
})
})
......@@ -192,7 +242,7 @@ module.exports = (api, options) => {
process.stdin.on('data', data => {
if (data.toString() === 'close') {
console.log('got close signal!')
server.close(() => {
server[webpack.version[0] > 4 ? 'stopCallback' : 'close'](() => {
process.exit(0)
})
}
......@@ -303,11 +353,15 @@ module.exports = (api, options) => {
server.showStatus = function () {}
}
if (webpack.version[0] > 4) {
server.start().catch(err => reject(err))
} else {
server.listen(port, host, err => {
if (err) {
reject(err)
}
})
}
})
})
}
......
......@@ -70,7 +70,11 @@ const v3 = {
webpackConfig.optimization = {}
}
// disable noEmitOnErrors
webpackConfig.optimization.noEmitOnErrors = false
if (webpack.version[0] > 4) {
webpackConfig.optimization.emitOnErrors = true
} else {
webpackConfig.optimization.noEmitOnErrors = false
}
if (isAppService) {
webpackConfig.optimization.runtimeChunk = {
......@@ -134,7 +138,8 @@ const v3 = {
output: {
filename: '[name].js',
chunkFilename: '[id].js',
globalObject: 'this'
// webpack5 use strict
globalObject: webpack.version[0] > 4 ? `(new Function("return this")())` : 'this'
},
performance: {
hints: false
......@@ -158,7 +163,7 @@ const v3 = {
compiler: vueLoader.compiler,
before: [
beforeCode + require('../util').getAutomatorCode() + statCode + pushCode + uniCloudCode +
getGlobalUsingComponentsCode()
getGlobalUsingComponentsCode()
]
}
}]
......
const path = require('path')
const webpack = require('webpack')
const {
sassLoaderVersion
......@@ -23,11 +24,22 @@ module.exports = function chainWebpack (platformOptions, vueOptions, api) {
const urlLoader = require('@dcloudio/uni-cli-shared/lib/url-loader')
const staticTypes = ['images', 'media', 'fonts']
staticTypes.forEach(staticType => {
webpackConfig.module
.rule(staticType)
.use('url-loader')
.loader(urlLoader.loader)
.tap(options => Object.assign(options, urlLoader.options()))
const newOptions = urlLoader.options()
if (webpack.version[0] > 4) {
if ('limit' in newOptions) {
webpackConfig.module.rule(staticType).parser({
dataUrlCondition: {
maxSize: newOptions.limit
}
})
}
} else {
webpackConfig.module
.rule(staticType)
.use('url-loader')
.loader(urlLoader.loader)
.tap(options => Object.assign(options, newOptions))
}
})
// 条件编译 vue 文件统一直接过滤html,js,css三种类型,单独资源文件引用各自过滤
......
const fs = require('fs')
const path = require('path')
const webpack = require('webpack')
const RuleSet = require('webpack/lib/RuleSet')
const CopyWebpackPlugin = require('copy-webpack-plugin')
const merge = require('webpack-merge')
......@@ -39,6 +38,37 @@ module.exports = function configureWebpack (platformOptions, manifestPlatformOpt
return (rule, i) => {
const clone = Object.assign({}, rule)
delete clone.include
if (webpack.version[0] > 4) {
const BasicEffectRulePlugin = require('webpack/lib/rules/BasicEffectRulePlugin')
const BasicMatcherRulePlugin = require('webpack/lib/rules/BasicMatcherRulePlugin')
const RuleSetCompiler = require('webpack/lib/rules/RuleSetCompiler')
const UseEffectRulePlugin = require('webpack/lib/rules/UseEffectRulePlugin')
const ruleSetCompiler = new RuleSetCompiler([
new BasicMatcherRulePlugin('test', 'resource'),
new BasicMatcherRulePlugin('include', 'resource'),
new BasicMatcherRulePlugin('exclude', 'resource', true),
new BasicMatcherRulePlugin('resource'),
new BasicMatcherRulePlugin('conditions'),
new BasicMatcherRulePlugin('resourceQuery'),
new BasicMatcherRulePlugin('realResource'),
new BasicMatcherRulePlugin('issuer'),
new BasicMatcherRulePlugin('compiler'),
new BasicEffectRulePlugin('type'),
new BasicEffectRulePlugin('sideEffects'),
new BasicEffectRulePlugin('parser'),
new BasicEffectRulePlugin('resolve'),
new BasicEffectRulePlugin('generator'),
new UseEffectRulePlugin()
])
const ruleSet = ruleSetCompiler.compile([{
rules: [clone]
}])
const rules = ruleSet.exec({
resource: fakeFile
})
return rules.length > 0 && rule.use
} else {
const RuleSet = require('webpack/lib/RuleSet')
const normalized = RuleSet.normalizeRule(clone, {}, '')
return (
!rule.enforce &&
......@@ -47,6 +77,7 @@ module.exports = function configureWebpack (platformOptions, manifestPlatformOpt
)
}
}
}
function updateJsLoader (rawRules, fakeFile, checkLoaderRegex, loader) {
const matchRule = rawRules.find(createMatcher(fakeFile))
......@@ -152,6 +183,7 @@ module.exports = function configureWebpack (platformOptions, manifestPlatformOpt
if (Array.isArray(uses)) {
if (uses.find(use => babelLoaderRe.test(use.loader))) {
const index = uses.findIndex(use => cacheLoaderRe.test(use.loader))
if (index >= 0) {
if (process.env.UNI_USING_CACHE) {
Object.assign(uses[index].options, api.genCacheConfig(
'babel-loader/' + process.env.UNI_PLATFORM,
......@@ -163,6 +195,7 @@ module.exports = function configureWebpack (platformOptions, manifestPlatformOpt
}
}
}
}
// js preprocess
updateJsLoader(rawRules, 'foo.js', babelLoaderRe, {
......
const {
getPlatformCssnano
} = require('@dcloudio/uni-cli-shared')
const webpack = require('webpack')
module.exports = function initCssnanoOptions (webpackConfig) {
const module = webpackConfig.module
// TODO 临时 hack calc:false 看看 vue cli 后续是否开放 cssnano 的配置
const cssnanoOptions = {
sourceMap: false,
plugins: [require('cssnano')({
sourceMap: false
}
const plugins = [require('cssnano')({
preset: ['default', getPlatformCssnano()]
})]
// TODO postcss-loader version > 4
if (webpack.version[0] > 4) {
cssnanoOptions.postcssOptions = { plugins }
} else {
cssnanoOptions.plugins = plugins
}
module.rule('css').oneOf('vue-modules').use('cssnano').loader('postcss-loader').options(cssnanoOptions)
......
......@@ -160,9 +160,13 @@ module.exports = {
},
plugins,
optimization: {
moduleIds: 'hashed'
moduleIds: webpack.version[0] > 4 ? 'deterministic' : 'hashed'
},
devServer: {
devServer: webpack.version[0] > 4 ? {
watchFiles: {
options: require('../util').getWatchOptions()
}
} : {
watchOptions: require('../util').getWatchOptions()
}
}
......
......@@ -157,7 +157,11 @@ module.exports = {
webpackConfig.optimization = {}
}
// disable noEmitOnErrors
webpackConfig.optimization.noEmitOnErrors = false
if (webpack.version[0] > 4) {
webpackConfig.optimization.emitOnErrors = true
} else {
webpackConfig.optimization.noEmitOnErrors = false
}
webpackConfig.optimization.runtimeChunk = {
name: 'common/runtime'
......
const fs = require('fs')
const path = require('path')
const webpack = require('webpack')
const isWin = /^win/.test(process.platform)
......@@ -23,11 +24,11 @@ module.exports = function initOptions (options) {
options.transpileDependencies.push(genTranspileDepRegex(path.resolve(process.env.UNI_INPUT_DIR, 'node_modules')))
options.transpileDependencies.push('@dcloudio/uni-' + process.env.UNI_PLATFORM)
options.transpileDependencies.push('@dcloudio/uni-i18n')
options.transpileDependencies.push('@dcloudio/uni-stat')
options.transpileDependencies.push('@dcloudio/uni-stat')
options.transpileDependencies.push('@dcloudio/uni-push')
options.transpileDependencies.push('@dcloudio/vue-cli-plugin-uni/packages/uni-app')
options.transpileDependencies.push('@dcloudio/vue-cli-plugin-uni/packages/uni-cloud')
options.transpileDependencies.push('@dcloudio/vue-cli-plugin-uni/packages/uni-stat')
options.transpileDependencies.push('@dcloudio/vue-cli-plugin-uni/packages/uni-stat')
options.transpileDependencies.push('@dcloudio/vue-cli-plugin-uni/packages/uni-push')
if (process.env.UNI_PLATFORM !== 'mp-weixin') { // mp runtime
......@@ -59,8 +60,14 @@ module.exports = function initOptions (options) {
options.css.loaderOptions.sass = {}
}
if (!options.css.loaderOptions.postcss.config) {
options.css.loaderOptions.postcss.config = {}
if (webpack.version[0] > 4) {
if (!options.css.loaderOptions.postcss.postcssOptions) {
options.css.loaderOptions.postcss.postcssOptions = {}
}
} else {
if (!options.css.loaderOptions.postcss.config) {
options.css.loaderOptions.postcss.config = {}
}
}
// sass 全局变量
......@@ -85,9 +92,10 @@ module.exports = function initOptions (options) {
}
options.css.loaderOptions.sass.prependData = sassData
const userPostcssConfigPath = path.resolve(process.env.UNI_INPUT_DIR, 'postcss.config.js')
if (fs.existsSync(userPostcssConfigPath)) {
options.css.loaderOptions.postcss.config.path = userPostcssConfigPath
const configPath = fs.existsSync(userPostcssConfigPath) ? userPostcssConfigPath : path.resolve(process.env.UNI_CLI_CONTEXT, 'postcss.config.js')
if (webpack.version[0] > 4) {
options.css.loaderOptions.postcss.postcssOptions.config = configPath
} else {
options.css.loaderOptions.postcss.config.path = path.resolve(process.env.UNI_CLI_CONTEXT, 'postcss.config.js')
options.css.loaderOptions.postcss.config.path = configPath
}
}
}
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册