Skip to content

Commit 28b24f7

Browse files
pldgsapegin
authored andcommitted
Feat: Add cssAttributes and jsAttributes options (resolve #5) (#11)
* Fixes #5
1 parent 97e53f5 commit 28b24f7

File tree

5 files changed

+189
-57
lines changed

5 files changed

+189
-57
lines changed

README.md

Lines changed: 55 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@ The plugin writes CSS and JS asset paths for you automatically. Works with webpa
88

99
## Usage
1010

11-
```
11+
```sh
1212
npm install mini-html-webpack-plugin
1313
```
1414

@@ -18,11 +18,19 @@ const MiniHtmlWebpackPlugin = require('mini-html-webpack-plugin');
1818
const config = {
1919
plugins: [
2020
new MiniHtmlWebpackPlugin({
21+
// Optional, defaults to `index.html`
22+
filename: 'demo.html',
23+
// Optional
24+
publicPath: 'demo/',
2125
context: {
2226
title: 'Webpack demo',
23-
htmlAttributes: { lang: 'en' } // Optional, defaults to { lang: 'en' }
24-
},
25-
filename: 'demo.html' // Optional, defaults to `index.html`
27+
// Optional, defaults to `{ lang: 'en' }`
28+
htmlAttributes: { lang: 'en' },
29+
// Optional
30+
cssAttributes: { rel: 'preload' },
31+
// Optional
32+
jsAttributes: { defer: 'defer' }
33+
}
2634
})
2735
]
2836
};
@@ -56,31 +64,58 @@ Or define a template function to generate your own code:
5664
```js
5765
const MiniHtmlWebpackPlugin = require('mini-html-webpack-plugin');
5866
const {
67+
generateAttributes,
5968
generateCSSReferences,
6069
generateJSReferences
6170
} = MiniHtmlWebpackPlugin;
6271

6372
const config = {
6473
plugins: [
6574
new MiniHtmlWebpackPlugin({
75+
filename: 'demo.html',
76+
publicPath: 'demo/',
77+
// `context` is available in `template` below
6678
context: {
67-
title: 'Custom template' // Available in the context below
79+
title: 'Webpack demo',
80+
htmlAttributes: { lang: 'en' },
81+
cssAttributes: { rel: 'preload' },
82+
jsAttributes: { defer: 'defer' }
6883
},
69-
template: ({ css, js, title, htmlAttributes, publicPath }) =>
70-
`<!DOCTYPE html>
71-
<html ${Object.entries(htmlAttributes)
72-
.map(attribute => `${attribute[0]}="${attribute[1]}"`)
73-
.join(' ')}>
74-
<head>
75-
<meta charset="UTF-8">
76-
<title>${title}</title>
77-
${generateCSSReferences(css, publicPath)}
78-
</head>
79-
<body>
80-
<div id="app"></div>
81-
${generateJSReferences(js, publicPath)}
82-
</body>
83-
</html>`
84+
template: ({
85+
css,
86+
js,
87+
publicPath,
88+
title,
89+
htmlAttributes,
90+
cssAttributes,
91+
jsAttributes
92+
}) => {
93+
const htmlAttrs = generateAttributes(htmlAttributes);
94+
95+
const cssTags = generateCSSReferences({
96+
files: css,
97+
attributes: cssAttributes,
98+
publicPath
99+
});
100+
101+
const jsTags = generateJSReferences({
102+
files: js,
103+
attributes: jsAttributes,
104+
publicPath
105+
});
106+
107+
return `<!DOCTYPE html>
108+
<html${htmlAttrs}>
109+
<head>
110+
<meta charset="UTF-8">
111+
<title>${title}</title>
112+
${cssTags}
113+
</head>
114+
<body>
115+
${jsTags}
116+
</body>
117+
</html>`;
118+
}
84119
})
85120
]
86121
};

__snapshots__/test.js.snap

Lines changed: 28 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,6 @@ exports[`custom filename 1`] = `
66
<head>
77
<meta charset=\\"UTF-8\\">
88
<title></title>
9-
109
1110
</head>
1211
<body>
@@ -15,13 +14,26 @@ exports[`custom filename 1`] = `
1514
</html>"
1615
`;
1716
17+
exports[`custom js attribute 1`] = `
18+
"<!DOCTYPE html>
19+
<html lang=\\"en\\">
20+
<head>
21+
<meta charset=\\"UTF-8\\">
22+
<title></title>
23+
24+
</head>
25+
<body>
26+
<script src=\\"runtime~main.js\\" defer=\\"defer\\"></script><script src=\\"main.js\\" defer=\\"defer\\"></script>
27+
</body>
28+
</html>"
29+
`;
30+
1831
exports[`custom lang 1`] = `
1932
"<!DOCTYPE html>
2033
<html lang=\\"ru\\">
2134
<head>
2235
<meta charset=\\"UTF-8\\">
2336
<title></title>
24-
2537
2638
</head>
2739
<body>
@@ -30,6 +42,20 @@ exports[`custom lang 1`] = `
3042
</html>"
3143
`;
3244
45+
exports[`custom publicPath 1`] = `
46+
"<!DOCTYPE html>
47+
<html lang=\\"en\\">
48+
<head>
49+
<meta charset=\\"UTF-8\\">
50+
<title></title>
51+
52+
</head>
53+
<body>
54+
<script src=\\"pizza/runtime~main.js\\"></script><script src=\\"pizza/main.js\\"></script>
55+
</body>
56+
</html>"
57+
`;
58+
3359
exports[`custom template 1`] = `"<div>Pizza</div>"`;
3460
3561
exports[`custom title 1`] = `
@@ -38,7 +64,6 @@ exports[`custom title 1`] = `
3864
<head>
3965
<meta charset=\\"UTF-8\\">
4066
<title>Pizza</title>
41-
4267
4368
</head>
4469
<body>
@@ -53,7 +78,6 @@ exports[`default options 1`] = `
5378
<head>
5479
<meta charset=\\"UTF-8\\">
5580
<title></title>
56-
5781
5882
</head>
5983
<body>

index.js

Lines changed: 64 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -8,15 +8,19 @@ class MiniHtmlWebpackPlugin {
88
}
99

1010
plugin(compilation, callback) {
11-
const { publicPath } = compilation.options.output;
12-
const { filename = 'index.html', template, context } = this.options;
11+
const {
12+
filename = 'index.html',
13+
publicPath = '',
14+
template,
15+
context,
16+
} = this.options;
1317

1418
const files = getFiles(normalizeEntrypoints(compilation.entrypoints));
1519

20+
const options = Object.assign({}, { publicPath }, context, files);
21+
1622
compilation.assets[filename] = new RawSource(
17-
(template || defaultTemplate)(
18-
Object.assign({}, { publicPath }, context, files)
19-
)
23+
(template || defaultTemplate)(options)
2024
);
2125

2226
callback();
@@ -64,39 +68,82 @@ function normalizeEntrypoints(entrypoints) {
6468
function defaultTemplate({
6569
css,
6670
js,
71+
publicPath = '',
6772
title = '',
68-
htmlAttributes = { lang: 'en' },
69-
publicPath,
73+
htmlAttributes = {
74+
lang: 'en',
75+
},
76+
cssAttributes = {},
77+
jsAttributes = {},
7078
}) {
79+
const htmlAttrs = generateAttributes(htmlAttributes);
80+
81+
const cssTags = generateCSSReferences({
82+
files: css,
83+
attributes: cssAttributes,
84+
publicPath,
85+
});
86+
87+
const jsTags = generateJSReferences({
88+
files: js,
89+
attributes: jsAttributes,
90+
publicPath,
91+
});
92+
7193
return `<!DOCTYPE html>
72-
<html ${Object.entries(htmlAttributes)
73-
.map(attribute => `${attribute[0]}="${attribute[1]}"`)
74-
.join(' ')}>
94+
<html${htmlAttrs}>
7595
<head>
7696
<meta charset="UTF-8">
7797
<title>${title}</title>
78-
79-
${generateCSSReferences(css, publicPath)}
98+
${cssTags}
8099
</head>
81100
<body>
82-
${generateJSReferences(js, publicPath)}
101+
${jsTags}
83102
</body>
84103
</html>`;
85104
}
86105

87-
function generateCSSReferences(files = [], publicPath = '') {
106+
function generateCSSReferences({
107+
files = [],
108+
publicPath = '',
109+
attributes = {},
110+
}) {
111+
attributes = generateAttributes(attributes);
112+
88113
return files
89-
.map(file => `<link href="${publicPath}${file}" rel="stylesheet">`)
114+
.map(
115+
file => `<link href="${publicPath}${file}" rel="stylesheet"${attributes}>`
116+
)
90117
.join('');
91118
}
92119

93-
function generateJSReferences(files = [], publicPath = '') {
120+
function generateJSReferences({
121+
files = [],
122+
publicPath = '',
123+
attributes = {},
124+
}) {
125+
attributes = generateAttributes(attributes);
126+
94127
return files
95-
.map(file => `<script src="${publicPath}${file}"></script>`)
128+
.map(file => `<script src="${publicPath}${file}"${attributes}></script>`)
96129
.join('');
97130
}
98131

132+
function generateAttributes(attributes = {}) {
133+
attributes = Object.entries(attributes);
134+
135+
if (attributes.length === 0) {
136+
return '';
137+
}
138+
139+
return (
140+
' ' +
141+
attributes.map(attribute => `${attribute[0]}="${attribute[1]}"`).join(' ')
142+
);
143+
}
144+
99145
module.exports = MiniHtmlWebpackPlugin;
100146
module.exports.defaultTemplate = defaultTemplate;
147+
module.exports.generateAttributes = generateAttributes;
101148
module.exports.generateCSSReferences = generateCSSReferences;
102149
module.exports.generateJSReferences = generateJSReferences;

0 commit comments

Comments
 (0)