-
Notifications
You must be signed in to change notification settings - Fork 11
/
Copy pathindex.js
92 lines (78 loc) · 2.7 KB
/
index.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
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
const HtmlWebpackPlugin = require("html-webpack-plugin");
function getHeadAndBodyChunks(chunks) {
const headChunks = [];
const bodyChunks = [];
chunks.forEach(chunk => {
if (chunk.attributes && ((chunk.attributes.src && chunk.attributes.src.includes("_head")) || chunk.attributes.href)) {
headChunks.push(chunk);
} else {
bodyChunks.push(chunk);
}
});
return {headChunks, bodyChunks};
}
function addAttributesToTag(tag, name, attributes) {
if (tag.attributes.src) {
const regex = new RegExp(`(\/${name}\\.)|(${name}\\.)`);
if (tag.attributes.src.match(regex)) {
tag.attributes = {...tag.attributes, ...attributes}
}
}
}
function handleChunksConfig(data, tags) {
if (data.plugin.options.chunksConfig) {
const asyncNames = data.plugin.options.chunksConfig.async;
const deferNames = data.plugin.options.chunksConfig.defer;
if(asyncNames && typeof asyncNames === "object" && asyncNames.length){
tags.forEach(tag => {
// add async only on script tags.
if (!tag.attributes.href && tag.attributes.src) {
asyncNames.forEach(name => {
addAttributesToTag(tag, name, {async: true});
});
}
});
}
if(deferNames && typeof deferNames === "object" && deferNames.length){
tags.forEach(tag => {
// add defer only on script tags.
if (!tag.attributes.href && tag.attributes.src) {
deferNames.forEach(name => {
addAttributesToTag(tag, name, {defer: true});
})
}
});
}
}
}
class HtmlWebpackInjectorPlugin {
apply(compiler) {
// HtmlWebpackPlugin version 4.0.0-beta.5
if (HtmlWebpackPlugin.getHooks) {
compiler.hooks.compilation.tap('HtmlWebpackInjectorPlugin', (compilation) => {
HtmlWebpackPlugin.getHooks(compilation).alterAssetTagGroups.tapAsync(
'HtmlWebpackInjectorPlugin', (data, callback) => {
const tags = [...data.bodyTags, ...data.headTags];
handleChunksConfig(data, tags);
const chunks = getHeadAndBodyChunks(tags);
data.headTags = chunks.headChunks;
data.bodyTags = chunks.bodyChunks;
callback(null, data)
}
)
});
} else {
// HtmlWebpackPlugin version 3.2.0
compiler.plugin("compilation", compilation => {
compilation.plugin("html-webpack-plugin-alter-asset-tags", data => {
const tags = [...data.body, ...data.head];
handleChunksConfig(data, tags);
const chunks = getHeadAndBodyChunks(tags);
data.head = chunks.headChunks;
data.body = chunks.bodyChunks;
});
});
}
}
}
module.exports = HtmlWebpackInjectorPlugin;