refactor: move mini-css-extract-plugin to client

This commit is contained in:
Clark Du 2018-03-21 19:34:16 +08:00 committed by Pooya Parsa
parent d828cbd04c
commit ade0d940c3
4 changed files with 89 additions and 83 deletions

View File

@ -1,6 +1,5 @@
import path from 'path' import path from 'path'
import MiniCssExtractPlugin from 'mini-css-extract-plugin'
import FriendlyErrorsWebpackPlugin from '@nuxtjs/friendly-errors-webpack-plugin' import FriendlyErrorsWebpackPlugin from '@nuxtjs/friendly-errors-webpack-plugin'
import TimeFixPlugin from 'time-fix-plugin' import TimeFixPlugin from 'time-fix-plugin'
import webpack from 'webpack' import webpack from 'webpack'
@ -11,7 +10,7 @@ import { isUrl, urlJoin } from '../../common/utils'
import WarnFixPlugin from './plugins/warnfix' import WarnFixPlugin from './plugins/warnfix'
import ProgressPlugin from './plugins/progress' import ProgressPlugin from './plugins/progress'
import vueLoader from './vue-loader' import vueLoader from './vue-loader'
import styleLoader from './style-loader' import styleLoaderWrapper from './style-loader'
/* /*
|-------------------------------------------------------------------------- |--------------------------------------------------------------------------
@ -26,6 +25,7 @@ export default function webpackBaseConfig({ name, isServer }) {
const webpackModulesDir = ['node_modules'].concat(this.options.modulesDir) const webpackModulesDir = ['node_modules'].concat(this.options.modulesDir)
const configAlias = {} const configAlias = {}
const styleLoader = styleLoaderWrapper({ isServer })
// Used by vue-loader so we can use in templates // Used by vue-loader so we can use in templates
// with <img src="~/assets/nuxt.png"/> // with <img src="~/assets/nuxt.png"/>
@ -161,14 +161,6 @@ export default function webpackBaseConfig({ name, isServer }) {
}) })
) )
// CSS extraction
const extractCSS = this.options.build.extractCSS
if (extractCSS && !this.options.dev) {
config.plugins.push(new MiniCssExtractPlugin(Object.assign({
filename: this.getFileName('css')
}, typeof extractCSS === 'object' ? extractCSS : {})))
}
// Clone deep avoid leaking config between Client and Server // Clone deep avoid leaking config between Client and Server
return _.cloneDeep(config) return _.cloneDeep(config)
} }

View File

@ -6,6 +6,7 @@ import webpack from 'webpack'
import HTMLPlugin from 'html-webpack-plugin' import HTMLPlugin from 'html-webpack-plugin'
import StylishPlugin from 'webpack-stylish' import StylishPlugin from 'webpack-stylish'
import BundleAnalyzer from 'webpack-bundle-analyzer' import BundleAnalyzer from 'webpack-bundle-analyzer'
import MiniCssExtractPlugin from 'mini-css-extract-plugin'
import Debug from 'debug' import Debug from 'debug'
import base from './base.config' import base from './base.config'
@ -154,5 +155,13 @@ export default function webpackClientConfig() {
} }
} }
// CSS extraction
const extractCSS = this.options.build.extractCSS
if (extractCSS) {
config.plugins.push(new MiniCssExtractPlugin(Object.assign({
filename: this.getFileName('css')
}, typeof extractCSS === 'object' ? extractCSS : {})))
}
return config return config
} }

View File

@ -4,85 +4,87 @@ import MiniCssExtractPlugin from 'mini-css-extract-plugin'
import postcssConfig from './postcss' import postcssConfig from './postcss'
export default function styleLoader(ext, loaders = [], isVueLoader = false) { export default ({isVueLoader = false, isServer}) => {
const sourceMap = Boolean(this.options.build.cssSourceMap) return function styleLoader(ext, loaders = []) {
const sourceMap = Boolean(this.options.build.cssSourceMap)
// Normalize loaders // Normalize loaders
loaders = (Array.isArray(loaders) ? loaders : [loaders]).map(loader => loaders = (Array.isArray(loaders) ? loaders : [loaders]).map(loader =>
Object.assign( Object.assign(
{ options: { sourceMap } }, { options: { sourceMap } },
typeof loader === 'string' ? { loader } : loader typeof loader === 'string' ? { loader } : loader
) )
)
// -- Configure additional loaders --
// style-resources-loader
// https://github.com/yenshih/style-resources-loader
if (this.options.build.styleResources[ext]) {
const patterns = Array.isArray(this.options.build.styleResources[ext])
? this.options.build.styleResources[ext]
: [this.options.build.styleResources[ext]]
const options = Object.assign(
{},
this.options.build.styleResources.options || {},
{ patterns }
) )
loaders.push({ // -- Configure additional loaders --
loader: 'style-resources-loader',
options
})
}
// postcss-loader // style-resources-loader
// vue-loader already provides it's own // https://github.com/yenshih/style-resources-loader
// https://github.com/postcss/postcss-loader if (this.options.build.styleResources[ext]) {
if (!isVueLoader) { const patterns = Array.isArray(this.options.build.styleResources[ext])
const _postcssConfig = postcssConfig.call(this) ? this.options.build.styleResources[ext]
: [this.options.build.styleResources[ext]]
const options = Object.assign(
{},
this.options.build.styleResources.options || {},
{ patterns }
)
if (_postcssConfig) { loaders.push({
loaders.unshift({ loader: 'style-resources-loader',
loader: 'postcss-loader', options
options: Object.assign({ sourceMap }, _postcssConfig)
}) })
} }
}
// css-loader // postcss-loader
// https://github.com/webpack-contrib/css-loader // vue-loader already provides it's own
const cssLoaderAlias = {} // https://github.com/postcss/postcss-loader
cssLoaderAlias[`/${this.options.dir.assets}`] = path.join(this.options.srcDir, this.options.dir.assets) if (!isVueLoader) {
cssLoaderAlias[`/${this.options.dir.static}`] = path.join(this.options.srcDir, this.options.dir.static) const _postcssConfig = postcssConfig.call(this)
loaders.unshift({ if (_postcssConfig) {
loader: 'css-loader', loaders.unshift({
options: { loader: 'postcss-loader',
sourceMap, options: Object.assign({ sourceMap }, _postcssConfig)
minimize: !this.options.dev, })
importLoaders: loaders.length, // Important! }
alias: cssLoaderAlias
} }
})
// -- With extractCSS -- // css-loader
if (this.options.build.extractCSS) { // https://github.com/webpack-contrib/css-loader
loaders.unshift(MiniCssExtractPlugin.loader) const cssLoaderAlias = {}
if (this.options.dev) { cssLoaderAlias[`/${this.options.dir.assets}`] = path.join(this.options.srcDir, this.options.dir.assets)
// css-hot-loader cssLoaderAlias[`/${this.options.dir.static}`] = path.join(this.options.srcDir, this.options.dir.static)
// https://github.com/shepherdwind/css-hot-loader
loaders.unshift({
loader: 'css-loader',
options: {
sourceMap,
minimize: !this.options.dev,
importLoaders: loaders.length, // Important!
alias: cssLoaderAlias
}
})
// -- With extractCSS --
if (!isServer && this.options.build.extractCSS) {
loaders.unshift(MiniCssExtractPlugin.loader)
if (this.options.dev) {
// css-hot-loader
// https://github.com/shepherdwind/css-hot-loader
loaders.unshift({
loader: 'css-hot-loader',
options: { sourceMap }
})
}
} else {
// Prepare vue-style-loader
// https://github.com/vuejs/vue-style-loader
loaders.unshift({ loaders.unshift({
loader: 'css-hot-loader', loader: 'vue-style-loader',
options: { sourceMap } options: { sourceMap }
}) })
} }
} else { return loaders
// Prepare vue-style-loader
// https://github.com/vuejs/vue-style-loader
loaders.unshift({
loader: 'vue-style-loader',
options: { sourceMap }
})
} }
return loaders
} }

View File

@ -1,8 +1,12 @@
import postcssConfig from './postcss' import postcssConfig from './postcss'
import styleLoader from './style-loader' import styleLoaderWrapper from './style-loader'
export default function vueLoader({ isServer }) { export default function vueLoader({ isServer }) {
// https://vue-loader.vuejs.org/en // https://vue-loader.vuejs.org/en
const styleLoader = styleLoaderWrapper({
isServer,
isVueLoader: true
})
const config = { const config = {
postcss: postcssConfig.call(this), postcss: postcssConfig.call(this),
cssSourceMap: this.options.build.cssSourceMap, cssSourceMap: this.options.build.cssSourceMap,
@ -13,17 +17,16 @@ export default function vueLoader({ isServer }) {
options: this.getBabelOptions({ isServer }) options: this.getBabelOptions({ isServer })
}, },
// Note: do not nest the `postcss` option under `loaders` // Note: do not nest the `postcss` option under `loaders`
css: styleLoader.call(this, 'css', [], true), css: styleLoader.call(this, 'css', []),
less: styleLoader.call(this, 'less', 'less-loader', true), less: styleLoader.call(this, 'less', 'less-loader'),
scss: styleLoader.call(this, 'scss', 'sass-loader', true), scss: styleLoader.call(this, 'scss', 'sass-loader'),
sass: styleLoader.call( sass: styleLoader.call(
this, this,
'sass', 'sass',
{ loader: 'sass-loader', options: { indentedSyntax: true } }, { loader: 'sass-loader', options: { indentedSyntax: true } }
true
), ),
stylus: styleLoader.call(this, 'stylus', 'stylus-loader', true), stylus: styleLoader.call(this, 'stylus', 'stylus-loader'),
styl: styleLoader.call(this, 'stylus', 'stylus-loader', true) styl: styleLoader.call(this, 'stylus', 'stylus-loader')
}, },
template: { template: {
doctype: 'html' // For pug, see https://github.com/vuejs/vue-loader/issues/55 doctype: 'html' // For pug, see https://github.com/vuejs/vue-loader/issues/55