Skip to content

Commit 5de194e

Browse files
committed
Completing vue-loader support
1 parent 3e7dffa commit 5de194e

21 files changed

+561
-58
lines changed

fixtures/vuejs/App.vue

Lines changed: 50 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,50 @@
1+
<template>
2+
<div id="app">
3+
<img src="./assets/logo.png">
4+
<hello></hello>
5+
</div>
6+
</template>
7+
8+
<script>
9+
import Hello from './components/Hello'
10+
11+
class TestClassSyntax {
12+
13+
}
14+
15+
export default {
16+
name: 'app',
17+
components: {
18+
Hello
19+
}
20+
}
21+
</script>
22+
23+
<style>
24+
#app {
25+
font-family: 'Avenir', Helvetica, Arial, sans-serif;
26+
-webkit-font-smoothing: antialiased;
27+
-moz-osx-font-smoothing: grayscale;
28+
text-align: center;
29+
color: #2c3e50;
30+
margin-top: 60px;
31+
}
32+
</style>
33+
34+
<style lang="scss">
35+
#app {
36+
display: flex;
37+
color: #2c3e90;
38+
}
39+
</style>
40+
41+
<style lang="sass">
42+
#app
43+
color: #2c3e90
44+
</style>
45+
46+
<style lang="less">
47+
#app {
48+
margin-top: 40px;
49+
}
50+
</style>

fixtures/vuejs/assets/logo.png

6.69 KB
Loading

fixtures/vuejs/components/Hello.vue

Lines changed: 53 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,53 @@
1+
<template>
2+
<div class="hello">
3+
<h1>{{ msg }}</h1>
4+
<h2>Essential Links</h2>
5+
<ul>
6+
<li><a href="https://vuejs.org" target="_blank">Core Docs</a></li>
7+
<li><a href="https://forum.vuejs.org" target="_blank">Forum</a></li>
8+
<li><a href="https://gitter.im/vuejs/vue" target="_blank">Gitter Chat</a></li>
9+
<li><a href="https://twitter.com/vuejs" target="_blank">Twitter</a></li>
10+
<br>
11+
<li><a href="http://vuejs-templates.github.io/webpack/" target="_blank">Docs for This Template</a></li>
12+
</ul>
13+
<h2>Ecosystem</h2>
14+
<ul>
15+
<li><a href="http://router.vuejs.org/" target="_blank">vue-router</a></li>
16+
<li><a href="http://vuex.vuejs.org/" target="_blank">vuex</a></li>
17+
<li><a href="http://vue-loader.vuejs.org/" target="_blank">vue-loader</a></li>
18+
<li><a href="https://github.com/vuejs/awesome-vue" target="_blank">awesome-vue</a></li>
19+
</ul>
20+
</div>
21+
</template>
22+
23+
<script>
24+
export default {
25+
name: 'hello',
26+
data () {
27+
return {
28+
msg: 'Welcome to Your Vue.js App'
29+
}
30+
}
31+
}
32+
</script>
33+
34+
<!-- Add "scoped" attribute to limit CSS to this component only -->
35+
<style scoped>
36+
h1, h2 {
37+
font-weight: normal;
38+
}
39+
40+
ul {
41+
list-style-type: none;
42+
padding: 0;
43+
}
44+
45+
li {
46+
display: inline-block;
47+
margin: 0 10px;
48+
}
49+
50+
a {
51+
color: #42b983;
52+
}
53+
</style>

fixtures/vuejs/main.js

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
import Vue from 'vue'
2+
import App from './App'
3+
4+
new Vue({
5+
el: '#app',
6+
template: '<App/>',
7+
components: { App }
8+
})

index.js

Lines changed: 9 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -330,7 +330,8 @@ module.exports = {
330330
},
331331

332332
/**
333-
* If enabled, the react preset is added to Babel:
333+
* If enabled, the react preset is added to Babel.
334+
*
334335
* https://babeljs.io/docs/plugins/preset-react/
335336
*
336337
* @returns {exports}
@@ -342,14 +343,15 @@ module.exports = {
342343
},
343344

344345
/**
345-
* If enabled, the vue-loader is added:
346-
* https://vue-loader.vuejs.org/en/
346+
* If enabled, the Vue.js loader is enabled.
347347
*
348-
* @param {object} options see https://vue-loader.vuejs.org/en/configurations/advanced.html
349-
* @return {exports}
348+
* https://github.com/vuejs/vue-loader
349+
*
350+
* @param {object} vueLoaderOptions: https://vue-loader.vuejs.org/en/configurations/advanced.html
351+
* @returns {exports}
350352
*/
351-
enableVueLoader(options = {}) {
352-
webpackConfig.enableVueLoader(options);
353+
enableVueLoader(vueLoaderOptions = {}) {
354+
webpackConfig.enableVueLoader(vueLoaderOptions);
353355

354356
return this;
355357
},

lib/WebpackConfig.js

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -45,13 +45,13 @@ class WebpackConfig {
4545
resolve_url_loader: true
4646
};
4747
this.useLessLoader = false;
48-
this.useVueLoader = false;
49-
this.vueOptions = {};
5048
this.cleanupOutput = false;
5149
this.sharedCommonsEntryName = null;
5250
this.providedVariables = {};
5351
this.babelConfigurationCallback = function() {};
5452
this.useReact = false;
53+
this.useVueLoader = false;
54+
this.vueLoaderOptions = {};
5555
this.loaders = [];
5656
}
5757

@@ -224,9 +224,9 @@ class WebpackConfig {
224224
this.useReact = true;
225225
}
226226

227-
enableVueLoader(options) {
227+
enableVueLoader(vueLoaderOptions = {}) {
228228
this.useVueLoader = true;
229-
this.vueOptions = options;
229+
this.vueLoaderOptions = vueLoaderOptions;
230230
}
231231

232232
cleanupOutputBeforeBuild() {

lib/config-generator.js

Lines changed: 11 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@
1111

1212
const webpack = require('webpack');
1313
const ExtractTextPlugin = require('extract-text-webpack-plugin');
14+
const extractText = require('./loaders/extract-text');
1415
const ManifestPlugin = require('./webpack/webpack-manifest-plugin');
1516
const DeleteUnusedEntriesJSPlugin = require('./webpack/delete-unused-entries-js-plugin');
1617
const AssetOutputDisplayPlugin = require('./friendly-errors/asset-output-display-plugin');
@@ -26,6 +27,7 @@ const cssLoaderUtil = require('./loaders/css');
2627
const sassLoaderUtil = require('./loaders/sass');
2728
const lessLoaderUtil = require('./loaders/less');
2829
const babelLoaderUtil = require('./loaders/babel');
30+
const vueLoaderUtil = require('./loaders/vue');
2931

3032
class ConfigGenerator {
3133
/**
@@ -68,7 +70,10 @@ class ConfigGenerator {
6870
config.stats = this.buildStatsConfig();
6971

7072
config.resolve = {
71-
extensions: ['.js', '.jsx']
73+
extensions: ['.js', '.jsx', '.vue'],
74+
alias: {
75+
'vue$': 'vue/dist/vue.esm.js',
76+
}
7277
};
7378

7479
return config;
@@ -111,10 +116,7 @@ class ConfigGenerator {
111116
},
112117
{
113118
test: /\.css$/,
114-
use: ExtractTextPlugin.extract({
115-
fallback: 'style-loader' + this.getSourceMapOption(),
116-
use: cssLoaderUtil.getLoaders(this.webpackConfig)
117-
})
119+
use: extractText.extract(this.webpackConfig, cssLoaderUtil.getLoaders(this.webpackConfig, false))
118120
},
119121
{
120122
test: /\.(png|jpg|jpeg|gif|ico|svg)$/,
@@ -137,30 +139,21 @@ class ConfigGenerator {
137139
if (this.webpackConfig.useSassLoader) {
138140
rules.push({
139141
test: /\.s[ac]ss$/,
140-
use: ExtractTextPlugin.extract({
141-
fallback: 'style-loader' + this.getSourceMapOption(),
142-
use: sassLoaderUtil.getLoaders(this.webpackConfig)
143-
})
142+
use: extractText.extract(this.webpackConfig, sassLoaderUtil.getLoaders(this.webpackConfig))
144143
});
145144
}
146145

147146
if (this.webpackConfig.useLessLoader) {
148147
rules.push({
149148
test: /\.less/,
150-
use: ExtractTextPlugin.extract({
151-
fallback: 'style-loader' + this.getSourceMapOption(),
152-
use: lessLoaderUtil.getLoaders(this.webpackConfig)
153-
})
149+
use: extractText.extract(this.webpackConfig, lessLoaderUtil.getLoaders(this.webpackConfig))
154150
});
155151
}
156152

157153
if (this.webpackConfig.useVueLoader) {
158-
loaderFeatures.ensureLoaderPackagesExist('vue');
159-
160154
rules.push({
161-
test: /\.vue/,
162-
loader: 'vue-loader',
163-
options: this.webpackConfig.vueOptions
155+
test: /\.vue$/,
156+
use: vueLoaderUtil.getLoaders(this.webpackConfig, this.webpackConfig.vueLoaderOptions)
164157
});
165158
}
166159

@@ -387,10 +380,6 @@ class ConfigGenerator {
387380
https: this.webpackConfig.useDevServerInHttps()
388381
};
389382
}
390-
391-
getSourceMapOption() {
392-
return this.webpackConfig.useSourceMaps ? '?sourceMap' : '';
393-
}
394383
}
395384

396385
/**

lib/loader-features.js

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -38,7 +38,9 @@ const loaderFeatures = {
3838
},
3939
vue: {
4040
method: 'enableVueLoader()',
41-
packages: ['vue-loader', 'vue-template-compiler'],
41+
// vue is needed so the end-user can do things
42+
// vue-template-compiler is a peer dep of vue-loader
43+
packages: ['vue', 'vue-loader', 'vue-template-compiler'],
4244
description: 'load VUE files'
4345
}
4446
};

lib/loaders/css.js

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -13,10 +13,11 @@ const loaderFeatures = require('../loader-features');
1313

1414
/**
1515
* @param {WebpackConfig} webpackConfig
16+
* @param {bool} ignorePostCssLoader If true, postcss-loader will never be added
1617
* @return {Array} of loaders to use for CSS files
1718
*/
1819
module.exports = {
19-
getLoaders(webpackConfig) {
20+
getLoaders(webpackConfig, skipPostCssLoader) {
2021
const cssLoaders = [
2122
{
2223
loader: 'css-loader',
@@ -27,7 +28,7 @@ module.exports = {
2728
},
2829
];
2930

30-
if (webpackConfig.usePostCssLoader) {
31+
if (webpackConfig.usePostCssLoader && !skipPostCssLoader) {
3132
loaderFeatures.ensureLoaderPackagesExist('postcss');
3233

3334
cssLoaders.push({

lib/loaders/extract-text.js

Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,29 @@
1+
/*
2+
* This file is part of the Symfony package.
3+
*
4+
* (c) Fabien Potencier <[email protected]>
5+
*
6+
* For the full copyright and license information, please view the LICENSE
7+
* file that was distributed with this source code.
8+
*/
9+
10+
'use strict';
11+
12+
const ExtractTextPlugin = require('extract-text-webpack-plugin');
13+
14+
/**
15+
* Wraps style loaders with the ExtractTextPlugin.
16+
*
17+
* @param {WebpackConfig} webpackConfig
18+
* @param {Array} loaders An array of some style loaders
19+
* @param {bool} useVueStyleLoader
20+
* @return {Array}
21+
*/
22+
module.exports = {
23+
extract(webpackConfig, loaders, useVueStyleLoader = false) {
24+
return ExtractTextPlugin.extract({
25+
fallback: (useVueStyleLoader ? 'vue-style-loader' : 'style-loader') + (webpackConfig.useSourceMaps ? '?sourceMap' : ''),
26+
use: loaders
27+
});
28+
}
29+
};

lib/loaders/less.js

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -14,14 +14,15 @@ const cssLoader = require('./css');
1414

1515
/**
1616
* @param {WebpackConfig} webpackConfig
17+
* @param {bool} ignorePostCssLoader If true, postcss-loader will never be added
1718
* @return {Array} of loaders to use for Less files
1819
*/
1920
module.exports = {
20-
getLoaders(webpackConfig) {
21+
getLoaders(webpackConfig, ignorePostCssLoader = false) {
2122
loaderFeatures.ensureLoaderPackagesExist('less');
2223

2324
return [
24-
...cssLoader.getLoaders(webpackConfig),
25+
...cssLoader.getLoaders(webpackConfig, ignorePostCssLoader),
2526
{
2627
loader: 'less-loader',
2728
options: {

lib/loaders/sass.js

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -14,13 +14,15 @@ const cssLoader = require('./css');
1414

1515
/**
1616
* @param {WebpackConfig} webpackConfig
17+
* @param {Object} sassOption Options to pass to the loader
18+
* @param {bool} ignorePostCssLoader If true, postcss-loader will never be added
1719
* @return {Array} of loaders to use for Sass files
1820
*/
1921
module.exports = {
20-
getLoaders(webpackConfig) {
22+
getLoaders(webpackConfig, sassOptions = {}, ignorePostCssLoader = false) {
2123
loaderFeatures.ensureLoaderPackagesExist('sass');
2224

23-
const sassLoaders = [...cssLoader.getLoaders(webpackConfig)];
25+
const sassLoaders = [...cssLoader.getLoaders(webpackConfig, ignorePostCssLoader)];
2426
if (true === webpackConfig.sassOptions.resolve_url_loader) {
2527
// responsible for resolving SASS url() paths
2628
// without this, all url() paths must be relative to the
@@ -35,10 +37,10 @@ module.exports = {
3537

3638
sassLoaders.push({
3739
loader: 'sass-loader',
38-
options: {
40+
options: Object.assign(sassOptions, {
3941
// needed by the resolve-url-loader
4042
sourceMap: (true === webpackConfig.sassOptions.resolve_url_loader) || webpackConfig.useSourceMaps
41-
}
43+
}),
4244
});
4345

4446
return sassLoaders;

0 commit comments

Comments
 (0)