-
Notifications
You must be signed in to change notification settings - Fork 90
/
plugin.js
77 lines (68 loc) 路 2.68 KB
/
plugin.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
const url = require('url')
const path = require('path')
const progressiveLoaderModule = require('../progressive-loader/module')
const { isVueLoader, getVueRules } = require('./getVueRules')
class VuetifyLoaderPlugin {
constructor (options) {
this.options = options || {}
}
apply (compiler) {
const vueRules = getVueRules(compiler)
if (!vueRules.length) {
throw new Error(
`[VuetifyLoaderPlugin Error] No matching rule for vue-loader found.\n` +
`Make sure there is at least one root-level rule that uses vue-loader and VuetifyLoaderPlugin is applied after VueLoaderPlugin.`
)
}
compiler.options.module.rules.unshift({
test: /\.vue$/,
use: {
loader: require.resolve('./loader'),
options: {
match: this.options.match || [],
attrsMatch: this.options.attrsMatch || [],
registerStylesSSR: this.options.registerStylesSSR || false
}
},
})
vueRules.forEach(this.updateVueRule.bind(this))
if (this.options.progressiveImages) {
const options = typeof this.options.progressiveImages === 'boolean'
? undefined
: this.options.progressiveImages
const resourceQuery = options && options.resourceQuery || 'vuetify-preload'
compiler.hooks.compilation.tap('VuetifyLoaderPlugin', compilation => {
compilation.hooks.buildModule.tap('VuetifyLoaderPlugin', module => {
if (!module.resource) return
const resource = url.parse(module.resource)
if (
resource.query === resourceQuery &&
['.png', '.jpg', '.jpeg', '.webp', '.gif'].includes(path.extname(resource.pathname))
) {
if (/^asset\/?/.test(module.type)) {
compilation.errors.push(new Error(
'vuetify-loader: progressiveImages does not work with asset modules, use file-loader or url-loader\n' +
`"${module.rawRequest}" will be loaded normally\n` +
'See https://webpack.js.org/guides/asset-modules/'
))
} else {
module.loaders.unshift({
loader: require.resolve('vuetify-loader/progressive-loader'),
options
})
}
}
})
})
}
}
updateVueRule ({ rule }) {
if (this.options.progressiveImages) {
const vueLoaderOptions = rule.use.find(isVueLoader).options
vueLoaderOptions.compilerOptions = vueLoaderOptions.compilerOptions || {}
vueLoaderOptions.compilerOptions.modules = vueLoaderOptions.compilerOptions.modules || []
vueLoaderOptions.compilerOptions.modules.push(progressiveLoaderModule)
}
}
}
module.exports = VuetifyLoaderPlugin