Compare commits
25 Commits
master
...
version-3.
| Author | SHA1 | Date |
|---|---|---|
|
|
8039058daa | |
|
|
cd5fe7334b | |
|
|
7804cc3bbb | |
|
|
426dfc7ce2 | |
|
|
aa137c987e | |
|
|
57bb6286bc | |
|
|
4404f9d09c | |
|
|
374e23eadd | |
|
|
d64827acc4 | |
|
|
ae4a49ecf8 | |
|
|
0b4ce98b2e | |
|
|
0ba21651a2 | |
|
|
717eb6818b | |
|
|
d937cb2ffa | |
|
|
c5b8382ad5 | |
|
|
ed00a67437 | |
|
|
9628e6504c | |
|
|
f30426e028 | |
|
|
76e05ef39e | |
|
|
7c0ad5093b | |
|
|
78cb9867e1 | |
|
|
82bba6a5f6 | |
|
|
3d1e403ece | |
|
|
e8f749f6ba | |
|
|
0a7d2244f4 |
|
|
@ -0,0 +1,9 @@
|
||||||
|
{
|
||||||
|
"ignore": [
|
||||||
|
"**/examples/**",
|
||||||
|
"**/node_modules/**",
|
||||||
|
],
|
||||||
|
"test": [
|
||||||
|
"**/spec/**"
|
||||||
|
]
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1 @@
|
||||||
|
4.3.2
|
||||||
|
|
@ -1,12 +1,12 @@
|
||||||
language: node_js
|
language: node_js
|
||||||
node_js:
|
node_js:
|
||||||
- "0.12"
|
|
||||||
- "0.10"
|
|
||||||
- "4"
|
- "4"
|
||||||
- "5"
|
- "5"
|
||||||
- "6"
|
- "6"
|
||||||
env:
|
env:
|
||||||
- WEBPACK=webpack
|
- WEBPACK=webpack
|
||||||
|
before_install:
|
||||||
|
- stty columns 120
|
||||||
install:
|
install:
|
||||||
- npm install --ignore-scripts
|
- npm install --ignore-scripts
|
||||||
- npm rm webpack
|
- npm rm webpack
|
||||||
|
|
|
||||||
|
|
@ -1,6 +1,13 @@
|
||||||
Change History
|
Change History
|
||||||
==============
|
==============
|
||||||
|
|
||||||
|
v3.x
|
||||||
|
---
|
||||||
|
* Rename `closingTag` into `voidTag` like in the official w3c spec.
|
||||||
|
* Provide a `createHtmlTagObject` helper for plugin authors to create new tags.
|
||||||
|
* Remove build in html minification
|
||||||
|
* Support same node version like webpack 2: node 4 and higher
|
||||||
|
|
||||||
v2.26.0
|
v2.26.0
|
||||||
---
|
---
|
||||||
* Allow plugins to add attributes without values to the `<script>` and `<link>` tags
|
* Allow plugins to add attributes without values to the `<script>` and `<link>` tags
|
||||||
|
|
|
||||||
28
README.md
28
README.md
|
|
@ -1,6 +1,6 @@
|
||||||
HTML Webpack Plugin
|
HTML Webpack Plugin
|
||||||
===================
|
===================
|
||||||
[](http://badge.fury.io/js/html-webpack-plugin) [](https://david-dm.org/ampedandwired/html-webpack-plugin) [](https://travis-ci.org/ampedandwired/html-webpack-plugin) [](https://ci.appveyor.com/project/jantimon/html-webpack-plugin) [](https://github.com/Flet/semistandard) [](https://www.bithound.io/github/ampedandwired/html-webpack-plugin/master/dependencies/npm) []()
|
[](http://badge.fury.io/js/html-webpack-plugin) [](https://david-dm.org/jantimon/html-webpack-plugin) [](https://travis-ci.org/jantimon/html-webpack-plugin) [](https://ci.appveyor.com/project/jantimon/html-webpack-plugin) [](https://github.com/Flet/semistandard) [](https://www.bithound.io/github/jantimon/html-webpack-plugin/master/dependencies/npm) []()
|
||||||
|
|
||||||
[](https://nodei.co/npm/html-webpack-plugin/)
|
[](https://nodei.co/npm/html-webpack-plugin/)
|
||||||
|
|
||||||
|
|
@ -21,7 +21,7 @@ $ npm install html-webpack-plugin --save-dev
|
||||||
Third party addons:
|
Third party addons:
|
||||||
-------------
|
-------------
|
||||||
|
|
||||||
The html-webpack-plugin provides [hooks](https://github.com/ampedandwired/html-webpack-plugin#events) to extend it to your needs.
|
The html-webpack-plugin provides [hooks](https://github.com/jantimon/html-webpack-plugin#events) to extend it to your needs.
|
||||||
There are already some really powerful plugins which can be integrated with zero configuration:
|
There are already some really powerful plugins which can be integrated with zero configuration:
|
||||||
|
|
||||||
* [webpack-subresource-integrity](https://www.npmjs.com/package/webpack-subresource-integrity) for enhanced asset security
|
* [webpack-subresource-integrity](https://www.npmjs.com/package/webpack-subresource-integrity) for enhanced asset security
|
||||||
|
|
@ -30,6 +30,10 @@ There are already some really powerful plugins which can be integrated with zero
|
||||||
* [html-webpack-harddisk-plugin](https://github.com/jantimon/html-webpack-harddisk-plugin)
|
* [html-webpack-harddisk-plugin](https://github.com/jantimon/html-webpack-harddisk-plugin)
|
||||||
* [html-webpack-inline-source-plugin](https://github.com/DustinJackson/html-webpack-inline-source-plugin) to inline your assets in the resulting HTML file
|
* [html-webpack-inline-source-plugin](https://github.com/DustinJackson/html-webpack-inline-source-plugin) to inline your assets in the resulting HTML file
|
||||||
* [html-webpack-exclude-assets-plugin](https://github.com/jamesjieye/html-webpack-exclude-assets-plugin) for excluding assets using regular expressions
|
* [html-webpack-exclude-assets-plugin](https://github.com/jamesjieye/html-webpack-exclude-assets-plugin) for excluding assets using regular expressions
|
||||||
|
* [html-webpack-include-assets-plugin](https://github.com/jharris4/html-webpack-include-assets-plugin) for including lists of js or css file paths (such as those copied by the copy-webpack-plugin).
|
||||||
|
* [script-ext-html-webpack-plugin](https://github.com/numical/script-ext-html-webpack-plugin) to add `async`, `defer` or `module` attributes to your`<script>` elements, or even in-line them
|
||||||
|
* [style-ext-html-webpack-plugin](https://github.com/numical/style-ext-html-webpack-plugin) to convert your `<link>`s to external stylesheets into `<style>` elements containing internal CSS
|
||||||
|
* [resource-hints-webpack-plugin](https://github.com/jantimon/resource-hints-webpack-plugin) to add resource hints for faster initial page loads
|
||||||
|
|
||||||
Basic Usage
|
Basic Usage
|
||||||
-----------
|
-----------
|
||||||
|
|
@ -55,7 +59,7 @@ This will generate a file `dist/index.html` containing the following:
|
||||||
<!DOCTYPE html>
|
<!DOCTYPE html>
|
||||||
<html>
|
<html>
|
||||||
<head>
|
<head>
|
||||||
<meta charset="UTF-8">
|
<meta charset="utf-8">
|
||||||
<title>Webpack App</title>
|
<title>Webpack App</title>
|
||||||
</head>
|
</head>
|
||||||
<body>
|
<body>
|
||||||
|
|
@ -79,10 +83,9 @@ Allowed values are as follows:
|
||||||
- `title`: The title to use for the generated HTML document.
|
- `title`: The title to use for the generated HTML document.
|
||||||
- `filename`: The file to write the HTML to. Defaults to `index.html`.
|
- `filename`: The file to write the HTML to. Defaults to `index.html`.
|
||||||
You can specify a subdirectory here too (eg: `assets/admin.html`).
|
You can specify a subdirectory here too (eg: `assets/admin.html`).
|
||||||
- `template`: Webpack require path to the template. Please see the [docs](https://github.com/ampedandwired/html-webpack-plugin/blob/master/docs/template-option.md) for details.
|
- `template`: Webpack require path to the template. Please see the [docs](https://github.com/jantimon/html-webpack-plugin/blob/master/docs/template-option.md) for details.
|
||||||
- `inject`: `true | 'head' | 'body' | false` Inject all assets into the given `template` or `templateContent` - When passing `true` or `'body'` all javascript resources will be placed at the bottom of the body element. `'head'` will place the scripts in the head element.
|
- `inject`: `true | 'head' | 'body' | false` Inject all assets into the given `template` or `templateContent` - When passing `true` or `'body'` all javascript resources will be placed at the bottom of the body element. `'head'` will place the scripts in the head element.
|
||||||
- `favicon`: Adds the given favicon path to the output html.
|
- `favicon`: Adds the given favicon path to the output html.
|
||||||
- `minify`: `{...} | false` Pass a [html-minifier](https://github.com/kangax/html-minifier#options-quick-reference) options object to minify the output.
|
|
||||||
- `hash`: `true | false` if `true` then append a unique webpack compilation hash to all
|
- `hash`: `true | false` if `true` then append a unique webpack compilation hash to all
|
||||||
included scripts and CSS files. This is useful for cache busting.
|
included scripts and CSS files. This is useful for cache busting.
|
||||||
- `cache`: `true | false` if `true` (default) try to emit the file only if it was changed.
|
- `cache`: `true | false` if `true` (default) try to emit the file only if it was changed.
|
||||||
|
|
@ -112,9 +115,9 @@ Here's an example webpack config illustrating how to use these options:
|
||||||
FAQ
|
FAQ
|
||||||
----
|
----
|
||||||
|
|
||||||
* [Why is my HTML minified?](https://github.com/ampedandwired/html-webpack-plugin/blob/master/docs/template-option.md)
|
* [Why is my HTML minified?](https://github.com/jantimon/html-webpack-plugin/blob/master/docs/template-option.md)
|
||||||
* [Why is my `<% ... %>` template not working?](https://github.com/ampedandwired/html-webpack-plugin/blob/master/docs/template-option.md)
|
* [Why is my `<% ... %>` template not working?](https://github.com/jantimon/html-webpack-plugin/blob/master/docs/template-option.md)
|
||||||
* [How can I use handlebars/pug/ejs as template engine](https://github.com/ampedandwired/html-webpack-plugin/blob/master/docs/template-option.md)
|
* [How can I use handlebars/pug/ejs as template engine](https://github.com/jantimon/html-webpack-plugin/blob/master/docs/template-option.md)
|
||||||
|
|
||||||
Generating Multiple HTML Files
|
Generating Multiple HTML Files
|
||||||
------------------------------
|
------------------------------
|
||||||
|
|
@ -159,7 +162,7 @@ plugins: [
|
||||||
<!DOCTYPE html>
|
<!DOCTYPE html>
|
||||||
<html>
|
<html>
|
||||||
<head>
|
<head>
|
||||||
<meta http-equiv="Content-type" content="text/html; charset=utf-8"/>
|
<meta charset="utf-8"/>
|
||||||
<title><%= htmlWebpackPlugin.options.title %></title>
|
<title><%= htmlWebpackPlugin.options.title %></title>
|
||||||
</head>
|
</head>
|
||||||
<body>
|
<body>
|
||||||
|
|
@ -305,9 +308,12 @@ Note that the callback must be passed the htmlPluginData in order to pass this o
|
||||||
|
|
||||||
# Contribution
|
# Contribution
|
||||||
|
|
||||||
You're free to contribute to this project by submitting [issues](https://github.com/ampedandwired/html-webpack-plugin/issues) and/or [pull requests](https://github.com/ampedandwired/html-webpack-plugin/pulls). This project is test-driven, so keep in mind that every change and new feature should be covered by tests.
|
You're free to contribute to this project by submitting [issues](https://github.com/jantimon/html-webpack-plugin/issues) and/or [pull requests](https://github.com/jantimon/html-webpack-plugin/pulls). This project is test-driven, so keep in mind that every change and new feature should be covered by tests.
|
||||||
This project uses the [semistandard code style](https://github.com/Flet/semistandard).
|
This project uses the [semistandard code style](https://github.com/Flet/semistandard).
|
||||||
|
This plugin follows the webpack teams decision to support [node 4+](http://node.green/).
|
||||||
|
|
||||||
|
Before running the tests, make sure to execute `yarn link` and `yarn link html-webpack-plugin` (or the npm variant of this).
|
||||||
|
|
||||||
# License
|
# License
|
||||||
|
|
||||||
This project is licensed under [MIT](https://github.com/ampedandwired/html-webpack-plugin/blob/master/LICENSE).
|
This project is licensed under [MIT](https://github.com/jantimon/html-webpack-plugin/blob/master/LICENSE).
|
||||||
|
|
|
||||||
|
|
@ -1,7 +1,7 @@
|
||||||
<!DOCTYPE html>
|
<!DOCTYPE html>
|
||||||
<html>
|
<html>
|
||||||
<head>
|
<head>
|
||||||
<meta charset="UTF-8">
|
<meta charset="utf-8">
|
||||||
<title><%= htmlWebpackPlugin.options.title %></title>
|
<title><%= htmlWebpackPlugin.options.title %></title>
|
||||||
</head>
|
</head>
|
||||||
<body>
|
<body>
|
||||||
|
|
|
||||||
|
|
@ -1 +1,11 @@
|
||||||
<!doctype html><html lang="en" manifest="manifest.appcache"><head><meta charset="utf-8"><title>Example template</title><meta name="viewport" content="width=device-width,initial-scale=1"><link href="styles.css" rel="stylesheet"></head><body><img src="0714810ae3fb211173e2964249507195.png"><script type="text/javascript" src="bundle.js"></script></body></html>
|
<!doctype html>
|
||||||
|
<html lang="en" manifest="manifest.appcache">
|
||||||
|
<head>
|
||||||
|
<meta charset="utf-8">
|
||||||
|
<title>Example template</title>
|
||||||
|
<meta name="viewport" content="width=device-width, initial-scale=1">
|
||||||
|
<link href="styles.css" rel="stylesheet"></head>
|
||||||
|
<body>
|
||||||
|
<img src="0714810ae3fb211173e2964249507195.png">
|
||||||
|
<script src="bundle.js"></script></body>
|
||||||
|
</html>
|
||||||
|
|
@ -1 +1,11 @@
|
||||||
<!doctype html><html lang="en" manifest="manifest.appcache"><head><meta charset="utf-8"><title>Example template</title><meta name="viewport" content="width=device-width,initial-scale=1"><link href="styles.css" rel="stylesheet"></head><body><img src="0714810ae3fb211173e2964249507195.png"><script type="text/javascript" src="bundle.js"></script></body></html>
|
<!doctype html>
|
||||||
|
<html lang="en" manifest="manifest.appcache">
|
||||||
|
<head>
|
||||||
|
<meta charset="utf-8">
|
||||||
|
<title>Example template</title>
|
||||||
|
<meta name="viewport" content="width=device-width, initial-scale=1">
|
||||||
|
<link href="styles.css" rel="stylesheet"></head>
|
||||||
|
<body>
|
||||||
|
<img src="0714810ae3fb211173e2964249507195.png">
|
||||||
|
<script src="bundle.js"></script></body>
|
||||||
|
</html>
|
||||||
|
|
@ -22,11 +22,7 @@ module.exports = {
|
||||||
new AppCachePlugin(),
|
new AppCachePlugin(),
|
||||||
new HtmlWebpackPlugin({
|
new HtmlWebpackPlugin({
|
||||||
filename: 'index.html',
|
filename: 'index.html',
|
||||||
template: 'template.html',
|
template: 'template.html'
|
||||||
minify: {
|
|
||||||
removeComments: true,
|
|
||||||
collapseWhitespace: true
|
|
||||||
}
|
|
||||||
}),
|
}),
|
||||||
new ExtractTextPlugin('styles.css')
|
new ExtractTextPlugin('styles.css')
|
||||||
]
|
]
|
||||||
|
|
|
||||||
|
|
@ -8,5 +8,5 @@
|
||||||
<body>
|
<body>
|
||||||
<h2>Partial</h2>
|
<h2>Partial</h2>
|
||||||
<img src="0714810ae3fb211173e2964249507195.png">
|
<img src="0714810ae3fb211173e2964249507195.png">
|
||||||
<script type="text/javascript" src="bundle.js"></script></body>
|
<script src="bundle.js"></script></body>
|
||||||
</html>
|
</html>
|
||||||
|
|
@ -8,5 +8,5 @@
|
||||||
<body>
|
<body>
|
||||||
<h2>Partial</h2>
|
<h2>Partial</h2>
|
||||||
<img src="0714810ae3fb211173e2964249507195.png">
|
<img src="0714810ae3fb211173e2964249507195.png">
|
||||||
<script type="text/javascript" src="bundle.js"></script></body>
|
<script src="bundle.js"></script></body>
|
||||||
</html>
|
</html>
|
||||||
|
|
@ -1,9 +1,9 @@
|
||||||
<!DOCTYPE html>
|
<!DOCTYPE html>
|
||||||
<html>
|
<html>
|
||||||
<head>
|
<head>
|
||||||
<meta charset="UTF-8">
|
<meta charset="utf-8">
|
||||||
<title>Webpack App</title>
|
<title>Webpack App</title>
|
||||||
</head>
|
</head>
|
||||||
<body>
|
<body>
|
||||||
<script type="text/javascript" src="bundle.js"></script></body>
|
<script src="bundle.js"></script></body>
|
||||||
</html>
|
</html>
|
||||||
|
|
@ -1,9 +1,9 @@
|
||||||
<!DOCTYPE html>
|
<!DOCTYPE html>
|
||||||
<html>
|
<html>
|
||||||
<head>
|
<head>
|
||||||
<meta charset="UTF-8">
|
<meta charset="utf-8">
|
||||||
<title>Webpack App</title>
|
<title>Webpack App</title>
|
||||||
</head>
|
</head>
|
||||||
<body>
|
<body>
|
||||||
<script type="text/javascript" src="bundle.js"></script></body>
|
<script src="bundle.js"></script></body>
|
||||||
</html>
|
</html>
|
||||||
|
|
@ -1,9 +1,9 @@
|
||||||
<!DOCTYPE html>
|
<!DOCTYPE html>
|
||||||
<html>
|
<html>
|
||||||
<head>
|
<head>
|
||||||
<meta charset="UTF-8">
|
<meta charset="utf-8">
|
||||||
<title>HtmlWebpackPlugin example</title>
|
<title>HtmlWebpackPlugin example</title>
|
||||||
<link rel="shortcut icon" href="favicon.ico"><link href="styles.css" rel="stylesheet"></head>
|
<link rel="shortcut icon" href="favicon.ico"><link href="styles.css" rel="stylesheet"></head>
|
||||||
<body>
|
<body>
|
||||||
<script type="text/javascript" src="bundle.js"></script></body>
|
<script src="bundle.js"></script></body>
|
||||||
</html>
|
</html>
|
||||||
|
|
@ -1,9 +1,9 @@
|
||||||
<!DOCTYPE html>
|
<!DOCTYPE html>
|
||||||
<html>
|
<html>
|
||||||
<head>
|
<head>
|
||||||
<meta charset="UTF-8">
|
<meta charset="utf-8">
|
||||||
<title>HtmlWebpackPlugin example</title>
|
<title>HtmlWebpackPlugin example</title>
|
||||||
<link rel="shortcut icon" href="favicon.ico"><link href="styles.css" rel="stylesheet"></head>
|
<link rel="shortcut icon" href="favicon.ico"><link href="styles.css" rel="stylesheet"></head>
|
||||||
<body>
|
<body>
|
||||||
<script type="text/javascript" src="bundle.js"></script></body>
|
<script src="bundle.js"></script></body>
|
||||||
</html>
|
</html>
|
||||||
|
|
@ -7,5 +7,5 @@
|
||||||
<link rel="shortcut icon" href="favicon.ico"><link href="styles.css" rel="stylesheet"></head>
|
<link rel="shortcut icon" href="favicon.ico"><link href="styles.css" rel="stylesheet"></head>
|
||||||
<body>
|
<body>
|
||||||
<img src="0714810ae3fb211173e2964249507195.png">
|
<img src="0714810ae3fb211173e2964249507195.png">
|
||||||
<script type="text/javascript" src="bundle.js"></script></body>
|
<script src="bundle.js"></script></body>
|
||||||
</html>
|
</html>
|
||||||
|
|
@ -7,5 +7,5 @@
|
||||||
<link rel="shortcut icon" href="favicon.ico"><link href="styles.css" rel="stylesheet"></head>
|
<link rel="shortcut icon" href="favicon.ico"><link href="styles.css" rel="stylesheet"></head>
|
||||||
<body>
|
<body>
|
||||||
<img src="0714810ae3fb211173e2964249507195.png">
|
<img src="0714810ae3fb211173e2964249507195.png">
|
||||||
<script type="text/javascript" src="bundle.js"></script></body>
|
<script src="bundle.js"></script></body>
|
||||||
</html>
|
</html>
|
||||||
|
|
@ -7,5 +7,5 @@
|
||||||
<link rel="shortcut icon" href="favicon.ico"><link href="styles.css" rel="stylesheet"></head>
|
<link rel="shortcut icon" href="favicon.ico"><link href="styles.css" rel="stylesheet"></head>
|
||||||
<body>
|
<body>
|
||||||
<img src="0714810ae3fb211173e2964249507195.png">
|
<img src="0714810ae3fb211173e2964249507195.png">
|
||||||
<script type="text/javascript" src="bundle.js"></script></body>
|
<script src="bundle.js"></script></body>
|
||||||
</html>
|
</html>
|
||||||
|
|
@ -7,5 +7,5 @@
|
||||||
<link rel="shortcut icon" href="favicon.ico"><link href="styles.css" rel="stylesheet"></head>
|
<link rel="shortcut icon" href="favicon.ico"><link href="styles.css" rel="stylesheet"></head>
|
||||||
<body>
|
<body>
|
||||||
<img src="0714810ae3fb211173e2964249507195.png">
|
<img src="0714810ae3fb211173e2964249507195.png">
|
||||||
<script type="text/javascript" src="bundle.js"></script></body>
|
<script src="bundle.js"></script></body>
|
||||||
</html>
|
</html>
|
||||||
|
|
@ -1,6 +1,6 @@
|
||||||
<!DOCTYPE html><html><head><meta http-equiv="Content-type" content="text/html; charset=utf-8"><title>Jade demo</title></head><body><style>body {
|
<!DOCTYPE html><html><head><meta charset="utf-8"><title>Jade demo</title></head><body><style>body {
|
||||||
background: snow;
|
background: snow;
|
||||||
}</style><script type="text/javascript">/******/ (function(modules) { // webpackBootstrap
|
}</style><script>/******/ (function(modules) { // webpackBootstrap
|
||||||
/******/ // The module cache
|
/******/ // The module cache
|
||||||
/******/ var installedModules = {};
|
/******/ var installedModules = {};
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -1,6 +1,6 @@
|
||||||
<!DOCTYPE html><html><head><meta http-equiv="Content-type" content="text/html; charset=utf-8"><title>Jade demo</title></head><body><style>body {
|
<!DOCTYPE html><html><head><meta charset="utf-8"><title>Jade demo</title></head><body><style>body {
|
||||||
background: snow;
|
background: snow;
|
||||||
}</style><script type="text/javascript">/******/ (function(modules) { // webpackBootstrap
|
}</style><script>/******/ (function(modules) { // webpackBootstrap
|
||||||
/******/ // The module cache
|
/******/ // The module cache
|
||||||
/******/ var installedModules = {};
|
/******/ var installedModules = {};
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -1,10 +1,10 @@
|
||||||
doctype html
|
doctype html
|
||||||
html
|
html
|
||||||
head
|
head
|
||||||
meta(http-equiv="Content-type" content="text/html; charset=utf-8")
|
meta(charset="utf-8")
|
||||||
title #{htmlWebpackPlugin.options.title}
|
title #{htmlWebpackPlugin.options.title}
|
||||||
body
|
body
|
||||||
each cssFile in htmlWebpackPlugin.files.css
|
each cssFile in htmlWebpackPlugin.files.css
|
||||||
style !{compilation.assets[cssFile.substr(htmlWebpackPlugin.files.publicPath.length)].source()}
|
style !{compilation.assets[cssFile.substr(htmlWebpackPlugin.files.publicPath.length)].source()}
|
||||||
each jsFile in htmlWebpackPlugin.files.js
|
each jsFile in htmlWebpackPlugin.files.js
|
||||||
script(type="text/javascript") !{compilation.assets[jsFile.substr(htmlWebpackPlugin.files.publicPath.length)].source()}
|
script !{compilation.assets[jsFile.substr(htmlWebpackPlugin.files.publicPath.length)].source()}
|
||||||
|
|
|
||||||
|
|
@ -1 +1 @@
|
||||||
<!DOCTYPE html><html><head><title>Jade demo</title><link rel="shortcut icon" href="favicon.ico"><link href="styles.css" rel="stylesheet"></head><body><div id="main"><!-- this partial is used for frontend and backend--><div class="time"> <b>Current time</b><p>1998-12-31T23:00:00.000Z</p></div><img src="0714810ae3fb211173e2964249507195.png"></div><script type="text/javascript" src="bundle.js"></script></body></html>
|
<!DOCTYPE html><html><head><title>Jade demo</title><link rel="shortcut icon" href="favicon.ico"><link href="styles.css" rel="stylesheet"></head><body><div id="main"><!-- this partial is used for frontend and backend--><div class="time"> <b>Current time</b><p>1998-12-31T23:00:00.000Z</p></div><img src="0714810ae3fb211173e2964249507195.png"></div><script src="bundle.js"></script></body></html>
|
||||||
|
|
@ -1 +1 @@
|
||||||
<!DOCTYPE html><html><head><title>Jade demo</title><link rel="shortcut icon" href="favicon.ico"><link href="styles.css" rel="stylesheet"></head><body><div id="main"><!-- this partial is used for frontend and backend--><div class="time"> <b>Current time</b><p>1998-12-31T23:00:00.000Z</p></div><img src="0714810ae3fb211173e2964249507195.png"></div><script type="text/javascript" src="bundle.js"></script></body></html>
|
<!DOCTYPE html><html><head><title>Jade demo</title><link rel="shortcut icon" href="favicon.ico"><link href="styles.css" rel="stylesheet"></head><body><div id="main"><!-- this partial is used for frontend and backend--><div class="time"> <b>Current time</b><p>1998-12-31T23:00:00.000Z</p></div><img src="0714810ae3fb211173e2964249507195.png"></div><script src="bundle.js"></script></body></html>
|
||||||
|
|
@ -13,7 +13,7 @@ module.exports = {
|
||||||
loaders: [
|
loaders: [
|
||||||
{ test: /\.css$/, loader: ExtractTextPlugin.extract('style-loader', 'css-loader') },
|
{ test: /\.css$/, loader: ExtractTextPlugin.extract('style-loader', 'css-loader') },
|
||||||
{ test: /\.png$/, loader: 'file-loader' },
|
{ test: /\.png$/, loader: 'file-loader' },
|
||||||
{ test: /\.jade$/, loader: 'jade' }
|
{ test: /\.jade$/, loader: 'jade-loader' }
|
||||||
]
|
]
|
||||||
},
|
},
|
||||||
plugins: [
|
plugins: [
|
||||||
|
|
|
||||||
|
|
@ -1,2 +1,2 @@
|
||||||
<html><head><title>Webpack App</title><link href="styles.css" rel="stylesheet"></head><body>Hello World from backend - <h2>Partial</h2>
|
<html><head><title>Webpack App</title><link href="styles.css" rel="stylesheet"></head><body>Hello World from backend - <h2>Partial</h2>
|
||||||
<img src="0714810ae3fb211173e2964249507195.png"><script type="text/javascript" src="bundle.js"></script></body></html>
|
<img src="0714810ae3fb211173e2964249507195.png"><script src="bundle.js"></script></body></html>
|
||||||
|
|
@ -1,2 +1,2 @@
|
||||||
<html><head><title>Webpack App</title><link href="styles.css" rel="stylesheet"></head><body>Hello World from backend - <h2>Partial</h2>
|
<html><head><title>Webpack App</title><link href="styles.css" rel="stylesheet"></head><body>Hello World from backend - <h2>Partial</h2>
|
||||||
<img src="0714810ae3fb211173e2964249507195.png"><script type="text/javascript" src="bundle.js"></script></body></html>
|
<img src="0714810ae3fb211173e2964249507195.png"><script src="bundle.js"></script></body></html>
|
||||||
|
|
@ -1,2 +1,2 @@
|
||||||
<head><link href="styles.css" rel="stylesheet"></head>Hello World from backend2016-10-29T07:02:05.646Z<h2>Partial</h2>
|
<head><link href="styles.css" rel="stylesheet"></head>Hello World from backend2016-10-29T07:02:05.646Z<h2>Partial</h2>
|
||||||
<img src="0714810ae3fb211173e2964249507195.png"><script type="text/javascript" src="bundle.js"></script>
|
<img src="0714810ae3fb211173e2964249507195.png"><script src="bundle.js"></script>
|
||||||
|
|
@ -1,2 +1,2 @@
|
||||||
<head><link href="styles.css" rel="stylesheet"></head>Hello World from backend2016-07-02T10:27:15.263Z<h2>Partial</h2>
|
<head><link href="styles.css" rel="stylesheet"></head>Hello World from backend2016-07-02T10:27:15.263Z<h2>Partial</h2>
|
||||||
<img src="0714810ae3fb211173e2964249507195.png"><script type="text/javascript" src="bundle.js"></script>
|
<img src="0714810ae3fb211173e2964249507195.png"><script src="bundle.js"></script>
|
||||||
470
index.js
470
index.js
|
|
@ -1,15 +1,18 @@
|
||||||
'use strict';
|
'use strict';
|
||||||
var vm = require('vm');
|
const vm = require('vm');
|
||||||
var fs = require('fs');
|
const fs = require('fs');
|
||||||
var _ = require('lodash');
|
const _ = require('lodash');
|
||||||
var Promise = require('bluebird');
|
const Promise = require('bluebird');
|
||||||
var path = require('path');
|
const path = require('path');
|
||||||
var childCompiler = require('./lib/compiler.js');
|
const childCompiler = require('./lib/compiler.js');
|
||||||
var prettyError = require('./lib/errors.js');
|
const prettyError = require('./lib/errors.js');
|
||||||
var chunkSorter = require('./lib/chunksorter.js');
|
const chunkSorter = require('./lib/chunksorter.js');
|
||||||
|
const htmlTag = require('./lib/html-tags.js');
|
||||||
Promise.promisifyAll(fs);
|
Promise.promisifyAll(fs);
|
||||||
|
|
||||||
function HtmlWebpackPlugin (options) {
|
module.exports = class HtmlWebpackPlugin {
|
||||||
|
|
||||||
|
constructor (options) {
|
||||||
// Default options
|
// Default options
|
||||||
this.options = _.extend({
|
this.options = _.extend({
|
||||||
template: path.join(__dirname, 'default_index.ejs'),
|
template: path.join(__dirname, 'default_index.ejs'),
|
||||||
|
|
@ -18,7 +21,6 @@ function HtmlWebpackPlugin (options) {
|
||||||
inject: true,
|
inject: true,
|
||||||
compile: true,
|
compile: true,
|
||||||
favicon: false,
|
favicon: false,
|
||||||
minify: false,
|
|
||||||
cache: true,
|
cache: true,
|
||||||
showErrors: true,
|
showErrors: true,
|
||||||
chunks: 'all',
|
chunks: 'all',
|
||||||
|
|
@ -28,74 +30,76 @@ function HtmlWebpackPlugin (options) {
|
||||||
}, options);
|
}, options);
|
||||||
}
|
}
|
||||||
|
|
||||||
HtmlWebpackPlugin.prototype.apply = function (compiler) {
|
/**
|
||||||
var self = this;
|
* The main function which is called by webpack to initialize the plugin
|
||||||
var isCompilationCached = false;
|
*/
|
||||||
var compilationPromise;
|
apply (compiler) {
|
||||||
|
let isCompilationCached = false;
|
||||||
|
let compilationPromise;
|
||||||
|
|
||||||
this.options.template = this.getFullTemplatePath(this.options.template, compiler.context);
|
this.options.template = this.getFullTemplatePath(this.options.template, compiler.context);
|
||||||
|
|
||||||
// convert absolute filename into relative so that webpack can
|
// convert absolute filename into relative so that webpack can
|
||||||
// generate it at correct location
|
// generate it at correct location
|
||||||
var filename = this.options.filename;
|
const filename = this.options.filename;
|
||||||
if (path.resolve(filename) === path.normalize(filename)) {
|
if (path.resolve(filename) === path.normalize(filename)) {
|
||||||
this.options.filename = path.relative(compiler.options.output.path, filename);
|
this.options.filename = path.relative(compiler.options.output.path, filename);
|
||||||
}
|
}
|
||||||
|
|
||||||
compiler.plugin('make', function (compilation, callback) {
|
compiler.plugin('make', (compilation, callback) => {
|
||||||
// Compile the template (queued)
|
// Compile the template (queued)
|
||||||
compilationPromise = childCompiler.compileTemplate(self.options.template, compiler.context, self.options.filename, compilation)
|
compilationPromise = childCompiler.compileTemplate(this.options.template, compiler.context, this.options.filename, compilation)
|
||||||
.catch(function (err) {
|
.catch(err => {
|
||||||
compilation.errors.push(prettyError(err, compiler.context).toString());
|
compilation.errors.push(prettyError(err, compiler.context).toString());
|
||||||
return {
|
return {
|
||||||
content: self.options.showErrors ? prettyError(err, compiler.context).toJsonHtml() : 'ERROR',
|
content: this.options.showErrors ? prettyError(err, compiler.context).toJsonHtml() : 'ERROR',
|
||||||
outputName: self.options.filename
|
outputName: this.options.filename
|
||||||
};
|
};
|
||||||
})
|
})
|
||||||
.then(function (compilationResult) {
|
.then(compilationResult => {
|
||||||
// If the compilation change didnt change the cache is valid
|
// If the compilation change didnt change the cache is valid
|
||||||
isCompilationCached = compilationResult.hash && self.childCompilerHash === compilationResult.hash;
|
isCompilationCached = compilationResult.hash && this.childCompilerHash === compilationResult.hash;
|
||||||
self.childCompilerHash = compilationResult.hash;
|
this.childCompilerHash = compilationResult.hash;
|
||||||
self.childCompilationOutputName = compilationResult.outputName;
|
this.childCompilationOutputName = compilationResult.outputName;
|
||||||
callback();
|
callback();
|
||||||
return compilationResult.content;
|
return compilationResult.content;
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
compiler.plugin('emit', function (compilation, callback) {
|
compiler.plugin('emit', (compilation, callback) => {
|
||||||
var applyPluginsAsyncWaterfall = self.applyPluginsAsyncWaterfall(compilation);
|
const applyPluginsAsyncWaterfall = this.applyPluginsAsyncWaterfall(compilation);
|
||||||
// Get all chunks
|
// Get all chunks
|
||||||
var allChunks = compilation.getStats().toJson().chunks;
|
const allChunks = compilation.getStats().toJson().chunks;
|
||||||
// Filter chunks (options.chunks and options.excludeCHunks)
|
// Filter chunks (options.chunks and options.excludeCHunks)
|
||||||
var chunks = self.filterChunks(allChunks, self.options.chunks, self.options.excludeChunks);
|
var chunks = this.filterChunks(allChunks, this.options.chunks, this.options.excludeChunks);
|
||||||
// Sort chunks
|
// Sort chunks
|
||||||
chunks = self.sortChunks(chunks, self.options.chunksSortMode);
|
chunks = this.sortChunks(chunks, this.options.chunksSortMode);
|
||||||
// Let plugins alter the chunks and the chunk sorting
|
// Let plugins alter the chunks and the chunk sorting
|
||||||
chunks = compilation.applyPluginsWaterfall('html-webpack-plugin-alter-chunks', chunks, { plugin: self });
|
chunks = compilation.applyPluginsWaterfall('html-webpack-plugin-alter-chunks', chunks, { plugin: this });
|
||||||
// Get assets
|
// Get assets
|
||||||
var assets = self.htmlWebpackPluginAssets(compilation, chunks);
|
const assets = this.htmlWebpackPluginAssets(compilation, chunks);
|
||||||
// If this is a hot update compilation, move on!
|
// If this is a hot update compilation, move on!
|
||||||
// This solves a problem where an `index.html` file is generated for hot-update js files
|
// This solves a problem where an `index.html` file is generated for hot-update js files
|
||||||
// It only happens in Webpack 2, where hot updates are emitted separately before the full bundle
|
// It only happens in Webpack 2, where hot updates are emitted separately before the full bundle
|
||||||
if (self.isHotUpdateCompilation(assets)) {
|
if (this.isHotUpdateCompilation(assets)) {
|
||||||
return callback();
|
return callback();
|
||||||
}
|
}
|
||||||
|
|
||||||
// If the template and the assets did not change we don't have to emit the html
|
// If the template and the assets did not change we don't have to emit the html
|
||||||
var assetJson = JSON.stringify(self.getAssetFiles(assets));
|
const assetJson = JSON.stringify(this.getAssetFiles(assets));
|
||||||
if (isCompilationCached && self.options.cache && assetJson === self.assetJson) {
|
if (isCompilationCached && this.options.cache && assetJson === this.assetJson) {
|
||||||
return callback();
|
return callback();
|
||||||
} else {
|
} else {
|
||||||
self.assetJson = assetJson;
|
this.assetJson = assetJson;
|
||||||
}
|
}
|
||||||
|
|
||||||
Promise.resolve()
|
Promise.resolve()
|
||||||
// Favicon
|
// Favicon
|
||||||
.then(function () {
|
.then(() => {
|
||||||
if (self.options.favicon) {
|
if (this.options.favicon) {
|
||||||
return self.addFileToAssets(self.options.favicon, compilation)
|
return this.addFileToAssets(this.options.favicon, compilation)
|
||||||
.then(function (faviconBasename) {
|
.then(faviconBasename => {
|
||||||
var publicPath = compilation.mainTemplate.getPublicPath({hash: compilation.hash}) || '';
|
let publicPath = compilation.mainTemplate.getPublicPath({hash: compilation.hash}) || '';
|
||||||
if (publicPath && publicPath.substr(-1) !== '/') {
|
if (publicPath && publicPath.substr(-1) !== '/') {
|
||||||
publicPath += '/';
|
publicPath += '/';
|
||||||
}
|
}
|
||||||
|
|
@ -104,81 +108,79 @@ HtmlWebpackPlugin.prototype.apply = function (compiler) {
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
// Wait for the compilation to finish
|
// Wait for the compilation to finish
|
||||||
.then(function () {
|
.then(() => compilationPromise)
|
||||||
return compilationPromise;
|
.then(compiledTemplate => {
|
||||||
})
|
|
||||||
.then(function (compiledTemplate) {
|
|
||||||
// Allow to use a custom function / string instead
|
// Allow to use a custom function / string instead
|
||||||
if (self.options.templateContent !== undefined) {
|
if (this.options.templateContent !== undefined) {
|
||||||
return self.options.templateContent;
|
return this.options.templateContent;
|
||||||
}
|
}
|
||||||
// Once everything is compiled evaluate the html factory
|
// Once everything is compiled evaluate the html factory
|
||||||
// and replace it with its content
|
// and replace it with its content
|
||||||
return self.evaluateCompilationResult(compilation, compiledTemplate);
|
return this.evaluateCompilationResult(compilation, compiledTemplate);
|
||||||
})
|
})
|
||||||
// Allow plugins to make changes to the assets before invoking the template
|
// Allow plugins to make changes to the assets before invoking the template
|
||||||
// This only makes sense to use if `inject` is `false`
|
// This only makes sense to use if `inject` is `false`
|
||||||
.then(function (compilationResult) {
|
.then(compilationResult => applyPluginsAsyncWaterfall('html-webpack-plugin-before-html-generation', false, {
|
||||||
return applyPluginsAsyncWaterfall('html-webpack-plugin-before-html-generation', false, {
|
|
||||||
assets: assets,
|
assets: assets,
|
||||||
outputName: self.childCompilationOutputName,
|
outputName: this.childCompilationOutputName,
|
||||||
plugin: self
|
plugin: this
|
||||||
})
|
|
||||||
.then(function () {
|
|
||||||
return compilationResult;
|
|
||||||
});
|
|
||||||
})
|
})
|
||||||
|
.then(() => compilationResult))
|
||||||
// Execute the template
|
// Execute the template
|
||||||
.then(function (compilationResult) {
|
.then(compilationResult => {
|
||||||
// If the loader result is a function execute it to retrieve the html
|
// If the loader result is a function execute it to retrieve the html
|
||||||
// otherwise use the returned html
|
// otherwise use the returned html
|
||||||
return typeof compilationResult !== 'function'
|
return typeof compilationResult !== 'function'
|
||||||
? compilationResult
|
? compilationResult
|
||||||
: self.executeTemplate(compilationResult, chunks, assets, compilation);
|
: this.executeTemplate(compilationResult, chunks, assets, compilation);
|
||||||
})
|
})
|
||||||
// Allow plugins to change the html before assets are injected
|
// Allow plugins to change the html before assets are injected
|
||||||
.then(function (html) {
|
.then(html => {
|
||||||
var pluginArgs = {html: html, assets: assets, plugin: self, outputName: self.childCompilationOutputName};
|
const pluginArgs = {html: html, assets: assets, plugin: this, outputName: this.childCompilationOutputName};
|
||||||
return applyPluginsAsyncWaterfall('html-webpack-plugin-before-html-processing', true, pluginArgs);
|
return applyPluginsAsyncWaterfall('html-webpack-plugin-before-html-processing', true, pluginArgs);
|
||||||
})
|
})
|
||||||
.then(function (result) {
|
.then(result => {
|
||||||
var html = result.html;
|
const html = result.html;
|
||||||
var assets = result.assets;
|
const assets = result.assets;
|
||||||
var chunks = result.chunks;
|
|
||||||
// Prepare script and link tags
|
// Prepare script and link tags
|
||||||
var assetTags = self.generateAssetTags(assets);
|
const assetTags = this.generateAssetTags(assets);
|
||||||
var pluginArgs = {head: assetTags.head, body: assetTags.body, plugin: self, chunks: chunks, outputName: self.childCompilationOutputName};
|
const pluginArgs = {
|
||||||
|
head: assetTags.head,
|
||||||
|
body: assetTags.body,
|
||||||
|
plugin: this,
|
||||||
|
chunks: chunks,
|
||||||
|
outputName: this.childCompilationOutputName
|
||||||
|
};
|
||||||
// Allow plugins to change the assetTag definitions
|
// Allow plugins to change the assetTag definitions
|
||||||
return applyPluginsAsyncWaterfall('html-webpack-plugin-alter-asset-tags', true, pluginArgs)
|
return applyPluginsAsyncWaterfall('html-webpack-plugin-alter-asset-tags', true, pluginArgs)
|
||||||
.then(function (result) {
|
|
||||||
// Add the stylesheets, scripts and so on to the resulting html
|
// Add the stylesheets, scripts and so on to the resulting html
|
||||||
return self.postProcessHtml(html, assets, { body: result.body, head: result.head })
|
.then(result => this.postProcessHtml(html, assets, { body: result.body, head: result.head })
|
||||||
.then(function (html) {
|
.then(html => _.extend(result, {html: html, assets: assets})));
|
||||||
return _.extend(result, {html: html, assets: assets});
|
|
||||||
});
|
|
||||||
});
|
|
||||||
})
|
})
|
||||||
// Allow plugins to change the html after assets are injected
|
// Allow plugins to change the html after assets are injected
|
||||||
.then(function (result) {
|
.then(result => {
|
||||||
var html = result.html;
|
const html = result.html;
|
||||||
var assets = result.assets;
|
const assets = result.assets;
|
||||||
var pluginArgs = {html: html, assets: assets, plugin: self, outputName: self.childCompilationOutputName};
|
const pluginArgs = {
|
||||||
|
html: html,
|
||||||
|
assets: assets,
|
||||||
|
plugin: this,
|
||||||
|
outputName: this.childCompilationOutputName
|
||||||
|
};
|
||||||
return applyPluginsAsyncWaterfall('html-webpack-plugin-after-html-processing', true, pluginArgs)
|
return applyPluginsAsyncWaterfall('html-webpack-plugin-after-html-processing', true, pluginArgs)
|
||||||
.then(function (result) {
|
.then(result => result.html);
|
||||||
return result.html;
|
|
||||||
});
|
|
||||||
})
|
})
|
||||||
.catch(function (err) {
|
.catch(err => {
|
||||||
// In case anything went wrong the promise is resolved
|
// In case anything went wrong the promise is resolved
|
||||||
// with the error message and an error is logged
|
// with the error message and an error is logged
|
||||||
compilation.errors.push(prettyError(err, compiler.context).toString());
|
compilation.errors.push(prettyError(err, compiler.context).toString());
|
||||||
// Prevent caching
|
// Invalidate the cache by resetting the cache key
|
||||||
self.hash = null;
|
this.hash = null;
|
||||||
return self.options.showErrors ? prettyError(err, compiler.context).toHtml() : 'ERROR';
|
return this.options.showErrors ? prettyError(err, compiler.context).toHtml() : 'ERROR';
|
||||||
})
|
})
|
||||||
.then(function (html) {
|
.then(html => {
|
||||||
// Replace the compilation result with the evaluated html code
|
// Replace the compilation result with the evaluated html code
|
||||||
compilation.assets[self.childCompilationOutputName] = {
|
compilation.assets[this.childCompilationOutputName] = {
|
||||||
source: function () {
|
source: function () {
|
||||||
return html;
|
return html;
|
||||||
},
|
},
|
||||||
|
|
@ -187,21 +189,18 @@ HtmlWebpackPlugin.prototype.apply = function (compiler) {
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
})
|
})
|
||||||
.then(function () {
|
// Let other plugins know that we are done by sending an emit event
|
||||||
// Let other plugins know that we are done:
|
.then(() =>
|
||||||
return applyPluginsAsyncWaterfall('html-webpack-plugin-after-emit', false, {
|
applyPluginsAsyncWaterfall('html-webpack-plugin-after-emit', false, {
|
||||||
html: compilation.assets[self.childCompilationOutputName],
|
html: compilation.assets[this.childCompilationOutputName],
|
||||||
outputName: self.childCompilationOutputName,
|
outputName: this.childCompilationOutputName,
|
||||||
plugin: self
|
plugin: this
|
||||||
}).catch(function (err) {
|
}).catch(err => {
|
||||||
console.error(err);
|
console.error(err);
|
||||||
return null;
|
return null;
|
||||||
}).then(function () {
|
}).then(() => null))
|
||||||
return null;
|
|
||||||
});
|
|
||||||
})
|
|
||||||
// Let webpack continue with it
|
// Let webpack continue with it
|
||||||
.finally(function () {
|
.finally(() => {
|
||||||
callback();
|
callback();
|
||||||
// Tell blue bird that we don't want to wait for callback.
|
// Tell blue bird that we don't want to wait for callback.
|
||||||
// Fixes "Warning: a promise was created in a handler but none were returned from it"
|
// Fixes "Warning: a promise was created in a handler but none were returned from it"
|
||||||
|
|
@ -209,13 +208,13 @@ HtmlWebpackPlugin.prototype.apply = function (compiler) {
|
||||||
return null;
|
return null;
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
};
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Evaluates the child compilation result
|
* Evaluates the child compilation result
|
||||||
* Returns a promise
|
* Returns a promise
|
||||||
*/
|
*/
|
||||||
HtmlWebpackPlugin.prototype.evaluateCompilationResult = function (compilation, source) {
|
evaluateCompilationResult (compilation, source) {
|
||||||
if (!source) {
|
if (!source) {
|
||||||
return Promise.reject('The child compilation didn\'t provide a result');
|
return Promise.reject('The child compilation didn\'t provide a result');
|
||||||
}
|
}
|
||||||
|
|
@ -223,94 +222,85 @@ HtmlWebpackPlugin.prototype.evaluateCompilationResult = function (compilation, s
|
||||||
// The LibraryTemplatePlugin stores the template result in a local variable.
|
// The LibraryTemplatePlugin stores the template result in a local variable.
|
||||||
// To extract the result during the evaluation this part has to be removed.
|
// To extract the result during the evaluation this part has to be removed.
|
||||||
source = source.replace('var HTML_WEBPACK_PLUGIN_RESULT =', '');
|
source = source.replace('var HTML_WEBPACK_PLUGIN_RESULT =', '');
|
||||||
var template = this.options.template.replace(/^.+!/, '').replace(/\?.+$/, '');
|
const template = this.options.template.replace(/^.+!/, '').replace(/\?.+$/, '');
|
||||||
var vmContext = vm.createContext(_.extend({HTML_WEBPACK_PLUGIN: true, require: require}, global));
|
const vmContext = vm.createContext(_.extend({HTML_WEBPACK_PLUGIN: true, require: require}, global));
|
||||||
var vmScript = new vm.Script(source, {filename: template});
|
const vmScript = new vm.Script(source, {filename: template});
|
||||||
// Evaluate code and cast to string
|
// Evaluate code and cast to string
|
||||||
var newSource;
|
let newSource;
|
||||||
try {
|
try {
|
||||||
newSource = vmScript.runInContext(vmContext);
|
newSource = vmScript.runInContext(vmContext);
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
return Promise.reject(e);
|
return Promise.reject(e);
|
||||||
}
|
}
|
||||||
|
if (typeof newSource === 'object' && newSource.__esModule && newSource.default) {
|
||||||
|
newSource = newSource.default;
|
||||||
|
}
|
||||||
return typeof newSource === 'string' || typeof newSource === 'function'
|
return typeof newSource === 'string' || typeof newSource === 'function'
|
||||||
? Promise.resolve(newSource)
|
? Promise.resolve(newSource)
|
||||||
: Promise.reject('The loader "' + this.options.template + '" didn\'t return html.');
|
: Promise.reject(`The loader "${this.options.template}" didn't return html.`);
|
||||||
};
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Html post processing
|
* Html post processing
|
||||||
*
|
*
|
||||||
* Returns a promise
|
* Returns a promise
|
||||||
*/
|
*/
|
||||||
HtmlWebpackPlugin.prototype.executeTemplate = function (templateFunction, chunks, assets, compilation) {
|
executeTemplate (templateFunction, chunks, assets, compilation) {
|
||||||
var self = this;
|
|
||||||
return Promise.resolve()
|
return Promise.resolve()
|
||||||
// Template processing
|
// Template processing
|
||||||
.then(function () {
|
.then(() => {
|
||||||
var templateParams = {
|
const templateParams = {
|
||||||
compilation: compilation,
|
compilation: compilation,
|
||||||
webpack: compilation.getStats().toJson(),
|
webpack: compilation.getStats().toJson(),
|
||||||
webpackConfig: compilation.options,
|
webpackConfig: compilation.options,
|
||||||
htmlWebpackPlugin: {
|
htmlWebpackPlugin: {
|
||||||
files: assets,
|
files: assets,
|
||||||
options: self.options
|
options: this.options
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
var html = '';
|
let html = '';
|
||||||
try {
|
try {
|
||||||
html = templateFunction(templateParams);
|
html = templateFunction(templateParams);
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
compilation.errors.push(new Error('Template execution failed: ' + e));
|
compilation.errors.push(new Error(`Template execution failed: ${e}`));
|
||||||
return Promise.reject(e);
|
return Promise.reject(e);
|
||||||
}
|
}
|
||||||
return html;
|
return html;
|
||||||
});
|
});
|
||||||
};
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Html post processing
|
* Html post processing
|
||||||
*
|
*
|
||||||
* Returns a promise
|
* Returns a promise
|
||||||
*/
|
*/
|
||||||
HtmlWebpackPlugin.prototype.postProcessHtml = function (html, assets, assetTags) {
|
postProcessHtml (html, assets, assetTags) {
|
||||||
var self = this;
|
|
||||||
if (typeof html !== 'string') {
|
if (typeof html !== 'string') {
|
||||||
return Promise.reject('Expected html to be a string but got ' + JSON.stringify(html));
|
return Promise.reject(`Expected html to be a string but got ${JSON.stringify(html)}`);
|
||||||
}
|
}
|
||||||
return Promise.resolve()
|
return Promise.resolve()
|
||||||
// Inject
|
// Inject
|
||||||
.then(function () {
|
.then(() => {
|
||||||
if (self.options.inject) {
|
if (this.options.inject) {
|
||||||
return self.injectAssetsIntoHtml(html, assets, assetTags);
|
return this.injectAssetsIntoHtml(html, assets, assetTags);
|
||||||
} else {
|
} else {
|
||||||
return html;
|
return html;
|
||||||
}
|
}
|
||||||
})
|
|
||||||
// Minify
|
|
||||||
.then(function (html) {
|
|
||||||
if (self.options.minify) {
|
|
||||||
var minify = require('html-minifier').minify;
|
|
||||||
return minify(html, self.options.minify);
|
|
||||||
}
|
|
||||||
return html;
|
|
||||||
});
|
});
|
||||||
};
|
}
|
||||||
|
|
||||||
/*
|
/**
|
||||||
* Pushes the content of the given filename to the compilation assets
|
* Pushes the content of the given filename to the compilation assets
|
||||||
*/
|
*/
|
||||||
HtmlWebpackPlugin.prototype.addFileToAssets = function (filename, compilation) {
|
addFileToAssets (filename, compilation) {
|
||||||
filename = path.resolve(compilation.compiler.context, filename);
|
filename = path.resolve(compilation.compiler.context, filename);
|
||||||
return Promise.props({
|
return Promise.props({
|
||||||
size: fs.statAsync(filename),
|
size: fs.statAsync(filename),
|
||||||
source: fs.readFileAsync(filename)
|
source: fs.readFileAsync(filename)
|
||||||
})
|
})
|
||||||
.catch(function () {
|
.catch(() => Promise.reject(new Error(`HtmlWebpackPlugin: could not load file ${filename}`)))
|
||||||
return Promise.reject(new Error('HtmlWebpackPlugin: could not load file ' + filename));
|
.then(results => {
|
||||||
})
|
const basename = path.basename(filename);
|
||||||
.then(function (results) {
|
|
||||||
var basename = path.basename(filename);
|
|
||||||
compilation.fileDependencies.push(filename);
|
compilation.fileDependencies.push(filename);
|
||||||
compilation.assets[basename] = {
|
compilation.assets[basename] = {
|
||||||
source: function () {
|
source: function () {
|
||||||
|
|
@ -322,12 +312,12 @@ HtmlWebpackPlugin.prototype.addFileToAssets = function (filename, compilation) {
|
||||||
};
|
};
|
||||||
return basename;
|
return basename;
|
||||||
});
|
});
|
||||||
};
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Helper to sort chunks
|
* Helper to sort chunks
|
||||||
*/
|
*/
|
||||||
HtmlWebpackPlugin.prototype.sortChunks = function (chunks, sortMode) {
|
sortChunks (chunks, sortMode) {
|
||||||
// Sort mode auto by default:
|
// Sort mode auto by default:
|
||||||
if (typeof sortMode === 'undefined') {
|
if (typeof sortMode === 'undefined') {
|
||||||
sortMode = 'auto';
|
sortMode = 'auto';
|
||||||
|
|
@ -344,15 +334,15 @@ HtmlWebpackPlugin.prototype.sortChunks = function (chunks, sortMode) {
|
||||||
if (typeof chunkSorter[sortMode] !== 'undefined') {
|
if (typeof chunkSorter[sortMode] !== 'undefined') {
|
||||||
return chunkSorter[sortMode](chunks);
|
return chunkSorter[sortMode](chunks);
|
||||||
}
|
}
|
||||||
throw new Error('"' + sortMode + '" is not a valid chunk sort mode');
|
throw new Error(`"${sortMode}" is not a valid chunk sort mode`);
|
||||||
};
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Return all chunks from the compilation result which match the exclude and include filters
|
* Return all chunks from the compilation result which match the exclude and include filters
|
||||||
*/
|
*/
|
||||||
HtmlWebpackPlugin.prototype.filterChunks = function (chunks, includedChunks, excludedChunks) {
|
filterChunks (chunks, includedChunks, excludedChunks) {
|
||||||
return chunks.filter(function (chunk) {
|
return chunks.filter(chunk => {
|
||||||
var chunkName = chunk.names[0];
|
const chunkName = chunk.names[0];
|
||||||
// This chunk doesn't have a name. This script can't handled it.
|
// This chunk doesn't have a name. This script can't handled it.
|
||||||
if (chunkName === undefined) {
|
if (chunkName === undefined) {
|
||||||
return false;
|
return false;
|
||||||
|
|
@ -372,31 +362,34 @@ HtmlWebpackPlugin.prototype.filterChunks = function (chunks, includedChunks, exc
|
||||||
// Add otherwise
|
// Add otherwise
|
||||||
return true;
|
return true;
|
||||||
});
|
});
|
||||||
};
|
}
|
||||||
|
|
||||||
HtmlWebpackPlugin.prototype.isHotUpdateCompilation = function (assets) {
|
/**
|
||||||
return assets.js.length && assets.js.every(function (name) {
|
* Returns true if this asset is part of a hot update
|
||||||
return /\.hot-update\.js$/.test(name);
|
*/
|
||||||
});
|
isHotUpdateCompilation (assets) {
|
||||||
};
|
return assets.js.length && assets.js.every(name => /\.hot-update\.js$/.test(name));
|
||||||
|
}
|
||||||
|
|
||||||
HtmlWebpackPlugin.prototype.htmlWebpackPluginAssets = function (compilation, chunks) {
|
/**
|
||||||
var self = this;
|
* Returns all assets from the current compilation
|
||||||
var webpackStatsJson = compilation.getStats().toJson();
|
*/
|
||||||
|
htmlWebpackPluginAssets (compilation, chunks) {
|
||||||
|
const webpackStatsJson = compilation.getStats().toJson();
|
||||||
|
|
||||||
// Use the configured public path or build a relative path
|
// Use the configured public path or build a relative path
|
||||||
var publicPath = typeof compilation.options.output.publicPath !== 'undefined'
|
let publicPath = typeof compilation.options.output.publicPath !== 'undefined'
|
||||||
// If a hard coded public path exists use it
|
// If a hard coded public path exists use it
|
||||||
? compilation.mainTemplate.getPublicPath({hash: webpackStatsJson.hash})
|
? compilation.mainTemplate.getPublicPath({hash: webpackStatsJson.hash})
|
||||||
// If no public path was set get a relative url path
|
// If no public path was set get a relative url path
|
||||||
: path.relative(path.resolve(compilation.options.output.path, path.dirname(self.childCompilationOutputName)), compilation.options.output.path)
|
: path.relative(path.resolve(compilation.options.output.path, path.dirname(this.childCompilationOutputName)), compilation.options.output.path)
|
||||||
.split(path.sep).join('/');
|
.split(path.sep).join('/');
|
||||||
|
|
||||||
if (publicPath.length && publicPath.substr(-1, 1) !== '/') {
|
if (publicPath.length && publicPath.substr(-1, 1) !== '/') {
|
||||||
publicPath += '/';
|
publicPath += '/';
|
||||||
}
|
}
|
||||||
|
|
||||||
var assets = {
|
const assets = {
|
||||||
// The public path
|
// The public path
|
||||||
publicPath: publicPath,
|
publicPath: publicPath,
|
||||||
// Will contain all js & css files by chunk
|
// Will contain all js & css files by chunk
|
||||||
|
|
@ -406,49 +399,43 @@ HtmlWebpackPlugin.prototype.htmlWebpackPluginAssets = function (compilation, chu
|
||||||
// Will contain all css files
|
// Will contain all css files
|
||||||
css: [],
|
css: [],
|
||||||
// Will contain the html5 appcache manifest files if it exists
|
// Will contain the html5 appcache manifest files if it exists
|
||||||
manifest: Object.keys(compilation.assets).filter(function (assetFile) {
|
manifest: Object.keys(compilation.assets).filter(assetFile => path.extname(assetFile) === '.appcache')[0]
|
||||||
return path.extname(assetFile) === '.appcache';
|
|
||||||
})[0]
|
|
||||||
};
|
};
|
||||||
|
|
||||||
// Append a hash for cache busting
|
// Append a hash for cache busting
|
||||||
if (this.options.hash) {
|
if (this.options.hash) {
|
||||||
assets.manifest = self.appendHash(assets.manifest, webpackStatsJson.hash);
|
assets.manifest = this.appendHash(assets.manifest, webpackStatsJson.hash);
|
||||||
assets.favicon = self.appendHash(assets.favicon, webpackStatsJson.hash);
|
assets.favicon = this.appendHash(assets.favicon, webpackStatsJson.hash);
|
||||||
}
|
}
|
||||||
|
|
||||||
for (var i = 0; i < chunks.length; i++) {
|
for (let i = 0; i < chunks.length; i++) {
|
||||||
var chunk = chunks[i];
|
const chunk = chunks[i];
|
||||||
var chunkName = chunk.names[0];
|
const chunkName = chunk.names[0];
|
||||||
|
|
||||||
assets.chunks[chunkName] = {};
|
assets.chunks[chunkName] = {};
|
||||||
|
|
||||||
// Prepend the public path to all chunk files
|
// Prepend the public path to all chunk files
|
||||||
var chunkFiles = [].concat(chunk.files).map(function (chunkFile) {
|
let chunkFiles = [].concat(chunk.files).map(chunkFile => publicPath + chunkFile);
|
||||||
return publicPath + chunkFile;
|
|
||||||
});
|
|
||||||
|
|
||||||
// Append a hash for cache busting
|
// Append a hash for cache busting
|
||||||
if (this.options.hash) {
|
if (this.options.hash) {
|
||||||
chunkFiles = chunkFiles.map(function (chunkFile) {
|
chunkFiles = chunkFiles.map(chunkFile => this.appendHash(chunkFile, webpackStatsJson.hash));
|
||||||
return self.appendHash(chunkFile, webpackStatsJson.hash);
|
|
||||||
});
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Webpack outputs an array for each chunk when using sourcemaps
|
// Webpack outputs an array for each chunk when using sourcemaps
|
||||||
// But we need only the entry file
|
// But we need only the entry file
|
||||||
var entry = chunkFiles[0];
|
const entry = chunkFiles[0];
|
||||||
assets.chunks[chunkName].size = chunk.size;
|
assets.chunks[chunkName].size = chunk.size;
|
||||||
assets.chunks[chunkName].entry = entry;
|
assets.chunks[chunkName].entry = entry;
|
||||||
assets.chunks[chunkName].hash = chunk.hash;
|
assets.chunks[chunkName].hash = chunk.hash;
|
||||||
assets.js.push(entry);
|
assets.js.push(entry);
|
||||||
|
|
||||||
// Gather all css files
|
// Gather all css files
|
||||||
var css = chunkFiles.filter(function (chunkFile) {
|
var css = chunkFiles.filter(chunkFile =>
|
||||||
// Some chunks may contain content hash in their names, for ex. 'main.css?1e7cac4e4d8b52fd5ccd2541146ef03f'.
|
// Some chunks may contain content hash in their names, for ex. 'main.css?1e7cac4e4d8b52fd5ccd2541146ef03f'.
|
||||||
// We must proper handle such cases, so we use regexp testing here
|
// We must proper handle such cases, so we use regexp testing here
|
||||||
return /.css($|\?)/.test(chunkFile);
|
/.css($|\?)/.test(chunkFile)
|
||||||
});
|
);
|
||||||
assets.chunks[chunkName].css = css;
|
assets.chunks[chunkName].css = css;
|
||||||
assets.css = assets.css.concat(css);
|
assets.css = assets.css.concat(css);
|
||||||
}
|
}
|
||||||
|
|
@ -458,50 +445,31 @@ HtmlWebpackPlugin.prototype.htmlWebpackPluginAssets = function (compilation, chu
|
||||||
assets.css = _.uniq(assets.css);
|
assets.css = _.uniq(assets.css);
|
||||||
|
|
||||||
return assets;
|
return assets;
|
||||||
};
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Injects the assets into the given html string
|
* Injects the assets into the given html string
|
||||||
*/
|
*/
|
||||||
HtmlWebpackPlugin.prototype.generateAssetTags = function (assets) {
|
generateAssetTags (assets) {
|
||||||
// Turn script files into script tags
|
// Turn script files into script tags
|
||||||
var scripts = assets.js.map(function (scriptPath) {
|
const scripts = assets.js.map(scriptPath => htmlTag.createHtmlTagObject('script', {
|
||||||
return {
|
|
||||||
tagName: 'script',
|
|
||||||
closeTag: true,
|
|
||||||
attributes: {
|
|
||||||
type: 'text/javascript',
|
|
||||||
src: scriptPath
|
src: scriptPath
|
||||||
}
|
}));
|
||||||
};
|
|
||||||
});
|
|
||||||
// Make tags self-closing in case of xhtml
|
|
||||||
var selfClosingTag = !!this.options.xhtml;
|
|
||||||
// Turn css files into link tags
|
// Turn css files into link tags
|
||||||
var styles = assets.css.map(function (stylePath) {
|
const styles = assets.css.map(stylePath => htmlTag.createHtmlTagObject('link', {
|
||||||
return {
|
|
||||||
tagName: 'link',
|
|
||||||
selfClosingTag: selfClosingTag,
|
|
||||||
attributes: {
|
|
||||||
href: stylePath,
|
href: stylePath,
|
||||||
rel: 'stylesheet'
|
rel: 'stylesheet'
|
||||||
}
|
}));
|
||||||
};
|
|
||||||
});
|
|
||||||
// Injection targets
|
// Injection targets
|
||||||
var head = [];
|
let head = [];
|
||||||
var body = [];
|
let body = [];
|
||||||
|
|
||||||
// If there is a favicon present, add it to the head
|
// If there is a favicon present, add it to the head
|
||||||
if (assets.favicon) {
|
if (assets.favicon) {
|
||||||
head.push({
|
head.push(htmlTag.createHtmlTagObject('link', {
|
||||||
tagName: 'link',
|
|
||||||
selfClosingTag: selfClosingTag,
|
|
||||||
attributes: {
|
|
||||||
rel: 'shortcut icon',
|
rel: 'shortcut icon',
|
||||||
href: assets.favicon
|
href: assets.favicon
|
||||||
}
|
}));
|
||||||
});
|
|
||||||
}
|
}
|
||||||
// Add styles to the head
|
// Add styles to the head
|
||||||
head = head.concat(styles);
|
head = head.concat(styles);
|
||||||
|
|
@ -512,24 +480,28 @@ HtmlWebpackPlugin.prototype.generateAssetTags = function (assets) {
|
||||||
body = body.concat(scripts);
|
body = body.concat(scripts);
|
||||||
}
|
}
|
||||||
return {head: head, body: body};
|
return {head: head, body: body};
|
||||||
};
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Injects the assets into the given html string
|
* Injects the assets into the given html string
|
||||||
*/
|
*/
|
||||||
HtmlWebpackPlugin.prototype.injectAssetsIntoHtml = function (html, assets, assetTags) {
|
injectAssetsIntoHtml (html, assets, assetTags) {
|
||||||
var htmlRegExp = /(<html[^>]*>)/i;
|
const htmlRegExp = /(<html[^>]*>)/i;
|
||||||
var headRegExp = /(<\/head>)/i;
|
const headRegExp = /(<\/head>)/i;
|
||||||
var bodyRegExp = /(<\/body>)/i;
|
const bodyRegExp = /(<\/body>)/i;
|
||||||
var body = assetTags.body.map(this.createHtmlTag);
|
// Create the html strings for head
|
||||||
var head = assetTags.head.map(this.createHtmlTag);
|
const head = assetTags.head.map(
|
||||||
|
(htmlTagObject) => htmlTag.htmlTagObjectToString(htmlTagObject, this.options.xhtml)
|
||||||
|
);
|
||||||
|
// Create the html strings for body
|
||||||
|
const body = assetTags.body.map(
|
||||||
|
(htmlTagObject) => htmlTag.htmlTagObjectToString(htmlTagObject, this.options.xhtml)
|
||||||
|
);
|
||||||
|
|
||||||
if (body.length) {
|
if (body.length) {
|
||||||
if (bodyRegExp.test(html)) {
|
if (bodyRegExp.test(html)) {
|
||||||
// Append assets to body element
|
// Append assets to body element
|
||||||
html = html.replace(bodyRegExp, function (match) {
|
html = html.replace(bodyRegExp, (match) => body.join('') + match);
|
||||||
return body.join('') + match;
|
|
||||||
});
|
|
||||||
} else {
|
} else {
|
||||||
// Append scripts to the end of the file if no <body> element exists:
|
// Append scripts to the end of the file if no <body> element exists:
|
||||||
html += body.join('');
|
html += body.join('');
|
||||||
|
|
@ -540,107 +512,81 @@ HtmlWebpackPlugin.prototype.injectAssetsIntoHtml = function (html, assets, asset
|
||||||
// Create a head tag if none exists
|
// Create a head tag if none exists
|
||||||
if (!headRegExp.test(html)) {
|
if (!headRegExp.test(html)) {
|
||||||
if (!htmlRegExp.test(html)) {
|
if (!htmlRegExp.test(html)) {
|
||||||
html = '<head></head>' + html;
|
html = `<head></head>${html}`;
|
||||||
} else {
|
} else {
|
||||||
html = html.replace(htmlRegExp, function (match) {
|
html = html.replace(htmlRegExp, (match) => `${match}<head></head>`);
|
||||||
return match + '<head></head>';
|
|
||||||
});
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Append assets to head element
|
// Append assets to head element
|
||||||
html = html.replace(headRegExp, function (match) {
|
html = html.replace(headRegExp, match => head.join('') + match);
|
||||||
return head.join('') + match;
|
|
||||||
});
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Inject manifest into the opening html tag
|
// Inject manifest into the opening html tag
|
||||||
if (assets.manifest) {
|
if (assets.manifest) {
|
||||||
html = html.replace(/(<html[^>]*)(>)/i, function (match, start, end) {
|
html = html.replace(/(<html[^>]*)(>)/i, (match, start, end) => {
|
||||||
// Append the manifest only if no manifest was specified
|
// Append the manifest only if no manifest was specified
|
||||||
if (/\smanifest\s*=/.test(match)) {
|
if (/\smanifest\s*=/.test(match)) {
|
||||||
return match;
|
return match;
|
||||||
}
|
}
|
||||||
return start + ' manifest="' + assets.manifest + '"' + end;
|
return `${start} manifest="${assets.manifest}"${end}`;
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
return html;
|
return html;
|
||||||
};
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Appends a cache busting hash
|
* Appends a cache busting hash
|
||||||
*/
|
*/
|
||||||
HtmlWebpackPlugin.prototype.appendHash = function (url, hash) {
|
appendHash (url, hash) {
|
||||||
if (!url) {
|
if (!url) {
|
||||||
return url;
|
return url;
|
||||||
}
|
}
|
||||||
return url + (url.indexOf('?') === -1 ? '?' : '&') + hash;
|
return url + (url.indexOf('?') === -1 ? '?' : '&') + hash;
|
||||||
};
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Turn a tag definition into a html string
|
|
||||||
*/
|
|
||||||
HtmlWebpackPlugin.prototype.createHtmlTag = function (tagDefinition) {
|
|
||||||
var attributes = Object.keys(tagDefinition.attributes || {})
|
|
||||||
.filter(function (attributeName) {
|
|
||||||
return tagDefinition.attributes[attributeName] !== false;
|
|
||||||
})
|
|
||||||
.map(function (attributeName) {
|
|
||||||
if (tagDefinition.attributes[attributeName] === true) {
|
|
||||||
return attributeName;
|
|
||||||
}
|
}
|
||||||
return attributeName + '="' + tagDefinition.attributes[attributeName] + '"';
|
|
||||||
});
|
|
||||||
return '<' + [tagDefinition.tagName].concat(attributes).join(' ') + (tagDefinition.selfClosingTag ? '/' : '') + '>' +
|
|
||||||
(tagDefinition.innerHTML || '') +
|
|
||||||
(tagDefinition.closeTag ? '</' + tagDefinition.tagName + '>' : '');
|
|
||||||
};
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Helper to return the absolute template path with a fallback loader
|
* Helper to return the absolute template path with a fallback loader
|
||||||
*/
|
*/
|
||||||
HtmlWebpackPlugin.prototype.getFullTemplatePath = function (template, context) {
|
getFullTemplatePath (template, context) {
|
||||||
// If the template doesn't use a loader use the lodash template loader
|
// If the template doesn't use a loader use the lodash template loader
|
||||||
if (template.indexOf('!') === -1) {
|
if (template.indexOf('!') === -1) {
|
||||||
template = 'html-webpack-plugin/lib/loader.js!' + path.resolve(context, template);
|
template = `html-webpack-plugin/lib/loader.js!${path.resolve(context, template)}`;
|
||||||
}
|
}
|
||||||
// Resolve template path
|
// Resolve template path
|
||||||
return template.replace(
|
return template.replace(
|
||||||
/([!])([^/\\][^!?]+|[^/\\!?])($|\?.+$)/,
|
/([!])([^/\\][^!?]+|[^/\\!?])($|\?[^!?\n]+$)/,
|
||||||
function (match, prefix, filepath, postfix) {
|
(match, prefix, filepath, postfix) => prefix + path.resolve(filepath) + postfix
|
||||||
return prefix + path.resolve(filepath) + postfix;
|
);
|
||||||
});
|
}
|
||||||
};
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Helper to return a sorted unique array of all asset files out of the
|
* Helper to return a sorted unique array of all asset files out of the
|
||||||
* asset object
|
* asset object
|
||||||
*/
|
*/
|
||||||
HtmlWebpackPlugin.prototype.getAssetFiles = function (assets) {
|
getAssetFiles (assets) {
|
||||||
var files = _.uniq(Object.keys(assets).filter(function (assetType) {
|
const files = Object.keys(assets)
|
||||||
return assetType !== 'chunks' && assets[assetType];
|
.filter(assetType => assetType !== 'chunks' && assets[assetType])
|
||||||
}).reduce(function (files, assetType) {
|
.reduce((files, assetType) => files.concat(assets[assetType]), []);
|
||||||
return files.concat(assets[assetType]);
|
const uniqFiles = _.uniq(files);
|
||||||
}, []));
|
uniqFiles.sort();
|
||||||
files.sort();
|
return uniqFiles;
|
||||||
return files;
|
}
|
||||||
};
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Helper to promisify compilation.applyPluginsAsyncWaterfall that returns
|
* Helper to promisify compilation.applyPluginsAsyncWaterfall that returns
|
||||||
* a function that helps to merge given plugin arguments with processed ones
|
* a function that helps to merge given plugin arguments with processed ones
|
||||||
*/
|
*/
|
||||||
HtmlWebpackPlugin.prototype.applyPluginsAsyncWaterfall = function (compilation) {
|
applyPluginsAsyncWaterfall (compilation) {
|
||||||
var promisedApplyPluginsAsyncWaterfall = Promise.promisify(compilation.applyPluginsAsyncWaterfall, {context: compilation});
|
const promisedApplyPluginsAsyncWaterfall = Promise.promisify(compilation.applyPluginsAsyncWaterfall, {context: compilation});
|
||||||
return function (eventName, requiresResult, pluginArgs) {
|
return function (eventName, requiresResult, pluginArgs) {
|
||||||
return promisedApplyPluginsAsyncWaterfall(eventName, pluginArgs)
|
return promisedApplyPluginsAsyncWaterfall(eventName, pluginArgs)
|
||||||
.then(function (result) {
|
.then(result => {
|
||||||
if (requiresResult && !result) {
|
if (requiresResult && !result) {
|
||||||
compilation.warnings.push(new Error('Using ' + eventName + ' without returning a result is deprecated.'));
|
compilation.warnings.push(new Error(`Using ${eventName} without returning a result is deprecated.`));
|
||||||
}
|
}
|
||||||
return _.extend(pluginArgs, result);
|
return _.extend(pluginArgs, result);
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
module.exports = HtmlWebpackPlugin;
|
|
||||||
|
|
|
||||||
|
|
@ -1,6 +1,7 @@
|
||||||
'use strict';
|
'use strict';
|
||||||
|
|
||||||
var toposort = require('toposort');
|
const toposort = require('toposort');
|
||||||
|
const _ = require('lodash');
|
||||||
|
|
||||||
/*
|
/*
|
||||||
Sorts dependencies between chunks by their "parents" attribute.
|
Sorts dependencies between chunks by their "parents" attribute.
|
||||||
|
|
@ -27,20 +28,21 @@ module.exports.dependency = function (chunks) {
|
||||||
}
|
}
|
||||||
|
|
||||||
// We build a map (chunk-id -> chunk) for faster access during graph building.
|
// We build a map (chunk-id -> chunk) for faster access during graph building.
|
||||||
var nodeMap = {};
|
const nodeMap = {};
|
||||||
|
|
||||||
chunks.forEach(function (chunk) {
|
chunks.forEach(chunk => {
|
||||||
nodeMap[chunk.id] = chunk;
|
nodeMap[chunk.id] = chunk;
|
||||||
});
|
});
|
||||||
|
|
||||||
// Next, we add an edge for each parent relationship into the graph
|
// Next, we add an edge for each parent relationship into the graph
|
||||||
var edges = [];
|
const edges = [];
|
||||||
|
|
||||||
chunks.forEach(function (chunk) {
|
chunks.forEach(chunk => {
|
||||||
if (chunk.parents) {
|
if (chunk.parents) {
|
||||||
// Add an edge for each parent (parent -> child)
|
// Add an edge for each parent (parent -> child)
|
||||||
chunk.parents.forEach(function (parentId) {
|
chunk.parents.forEach(parentId => {
|
||||||
var parentChunk = nodeMap[parentId];
|
// webpack2 chunk.parents are chunks instead of string id(s)
|
||||||
|
const parentChunk = _.isObject(parentId) ? parentId : nodeMap[parentId];
|
||||||
// If the parent chunk does not exist (e.g. because of an excluded chunk)
|
// If the parent chunk does not exist (e.g. because of an excluded chunk)
|
||||||
// we ignore that parent
|
// we ignore that parent
|
||||||
if (parentChunk) {
|
if (parentChunk) {
|
||||||
|
|
|
||||||
|
|
@ -5,14 +5,14 @@
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
'use strict';
|
'use strict';
|
||||||
var Promise = require('bluebird');
|
const Promise = require('bluebird');
|
||||||
var _ = require('lodash');
|
const _ = require('lodash');
|
||||||
var path = require('path');
|
const path = require('path');
|
||||||
var NodeTemplatePlugin = require('webpack/lib/node/NodeTemplatePlugin');
|
const NodeTemplatePlugin = require('webpack/lib/node/NodeTemplatePlugin');
|
||||||
var NodeTargetPlugin = require('webpack/lib/node/NodeTargetPlugin');
|
const NodeTargetPlugin = require('webpack/lib/node/NodeTargetPlugin');
|
||||||
var LoaderTargetPlugin = require('webpack/lib/LoaderTargetPlugin');
|
const LoaderTargetPlugin = require('webpack/lib/LoaderTargetPlugin');
|
||||||
var LibraryTemplatePlugin = require('webpack/lib/LibraryTemplatePlugin');
|
const LibraryTemplatePlugin = require('webpack/lib/LibraryTemplatePlugin');
|
||||||
var SingleEntryPlugin = require('webpack/lib/SingleEntryPlugin');
|
const SingleEntryPlugin = require('webpack/lib/SingleEntryPlugin');
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Compiles the template into a nodejs factory, adds its to the compilation.assets
|
* Compiles the template into a nodejs factory, adds its to the compilation.assets
|
||||||
|
|
@ -33,17 +33,17 @@ var SingleEntryPlugin = require('webpack/lib/SingleEntryPlugin');
|
||||||
module.exports.compileTemplate = function compileTemplate (template, context, outputFilename, compilation) {
|
module.exports.compileTemplate = function compileTemplate (template, context, outputFilename, compilation) {
|
||||||
// The entry file is just an empty helper as the dynamic template
|
// The entry file is just an empty helper as the dynamic template
|
||||||
// require is added in "loader.js"
|
// require is added in "loader.js"
|
||||||
var outputOptions = {
|
const outputOptions = {
|
||||||
filename: outputFilename,
|
filename: outputFilename,
|
||||||
publicPath: compilation.outputOptions.publicPath
|
publicPath: compilation.outputOptions.publicPath
|
||||||
};
|
};
|
||||||
// Store the result of the parent compilation before we start the child compilation
|
// Store the result of the parent compilation before we start the child compilation
|
||||||
var assetsBeforeCompilation = _.assign({}, compilation.assets[outputOptions.filename]);
|
const assetsBeforeCompilation = _.assign({}, compilation.assets[outputOptions.filename]);
|
||||||
// Create an additional child compiler which takes the template
|
// Create an additional child compiler which takes the template
|
||||||
// and turns it into an Node.JS html factory.
|
// and turns it into an Node.JS html factory.
|
||||||
// This allows us to use loaders during the compilation
|
// This allows us to use loaders during the compilation
|
||||||
var compilerName = getCompilerName(context, outputFilename);
|
const compilerName = getCompilerName(context, outputFilename);
|
||||||
var childCompiler = compilation.createChildCompiler(compilerName, outputOptions);
|
const childCompiler = compilation.createChildCompiler(compilerName, outputOptions);
|
||||||
childCompiler.context = context;
|
childCompiler.context = context;
|
||||||
childCompiler.apply(
|
childCompiler.apply(
|
||||||
new NodeTemplatePlugin(outputOptions),
|
new NodeTemplatePlugin(outputOptions),
|
||||||
|
|
@ -56,7 +56,7 @@ module.exports.compileTemplate = function compileTemplate (template, context, ou
|
||||||
// Fix for "Uncaught TypeError: __webpack_require__(...) is not a function"
|
// Fix for "Uncaught TypeError: __webpack_require__(...) is not a function"
|
||||||
// Hot module replacement requires that every child compiler has its own
|
// Hot module replacement requires that every child compiler has its own
|
||||||
// cache. @see https://github.com/ampedandwired/html-webpack-plugin/pull/179
|
// cache. @see https://github.com/ampedandwired/html-webpack-plugin/pull/179
|
||||||
childCompiler.plugin('compilation', function (compilation) {
|
childCompiler.plugin('compilation', compilation => {
|
||||||
if (compilation.cache) {
|
if (compilation.cache) {
|
||||||
if (!compilation.cache[compilerName]) {
|
if (!compilation.cache[compilerName]) {
|
||||||
compilation.cache[compilerName] = {};
|
compilation.cache[compilerName] = {};
|
||||||
|
|
@ -66,19 +66,17 @@ module.exports.compileTemplate = function compileTemplate (template, context, ou
|
||||||
});
|
});
|
||||||
|
|
||||||
// Compile and return a promise
|
// Compile and return a promise
|
||||||
return new Promise(function (resolve, reject) {
|
return new Promise((resolve, reject) => {
|
||||||
childCompiler.runAsChild(function (err, entries, childCompilation) {
|
childCompiler.runAsChild((err, entries, childCompilation) => {
|
||||||
// Resolve / reject the promise
|
// Resolve / reject the promise
|
||||||
if (childCompilation && childCompilation.errors && childCompilation.errors.length) {
|
if (childCompilation && childCompilation.errors && childCompilation.errors.length) {
|
||||||
var errorDetails = childCompilation.errors.map(function (error) {
|
const errorDetails = childCompilation.errors.map(error => error.message + ((error.error ? `:\n${error.error}` : ''))).join('\n');
|
||||||
return error.message + (error.error ? ':\n' + error.error : '');
|
reject(new Error(`Child compilation failed:\n${errorDetails}`));
|
||||||
}).join('\n');
|
|
||||||
reject(new Error('Child compilation failed:\n' + errorDetails));
|
|
||||||
} else if (err) {
|
} else if (err) {
|
||||||
reject(err);
|
reject(err);
|
||||||
} else {
|
} else {
|
||||||
// Replace [hash] placeholders in filename
|
// Replace [hash] placeholders in filename
|
||||||
var outputName = compilation.mainTemplate.applyPluginsWaterfall('asset-path', outputOptions.filename, {
|
const outputName = compilation.mainTemplate.applyPluginsWaterfall('asset-path', outputOptions.filename, {
|
||||||
hash: childCompilation.hash,
|
hash: childCompilation.hash,
|
||||||
chunk: entries[0]
|
chunk: entries[0]
|
||||||
});
|
});
|
||||||
|
|
@ -106,7 +104,7 @@ module.exports.compileTemplate = function compileTemplate (template, context, ou
|
||||||
* Returns the child compiler name e.g. 'html-webpack-plugin for "index.html"'
|
* Returns the child compiler name e.g. 'html-webpack-plugin for "index.html"'
|
||||||
*/
|
*/
|
||||||
function getCompilerName (context, filename) {
|
function getCompilerName (context, filename) {
|
||||||
var absolutePath = path.resolve(context, filename);
|
const absolutePath = path.resolve(context, filename);
|
||||||
var relativePath = path.relative(context, absolutePath);
|
const relativePath = path.relative(context, absolutePath);
|
||||||
return 'html-webpack-plugin for "' + (absolutePath.length < relativePath.length ? absolutePath : relativePath) + '"';
|
return `html-webpack-plugin for "${absolutePath.length < relativePath.length ? absolutePath : relativePath}"`;
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -1,17 +1,15 @@
|
||||||
'use strict';
|
'use strict';
|
||||||
var PrettyError = require('pretty-error');
|
const PrettyError = require('pretty-error');
|
||||||
var prettyError = new PrettyError();
|
const prettyError = new PrettyError();
|
||||||
prettyError.withoutColors();
|
prettyError.withoutColors();
|
||||||
prettyError.skipPackage(['html-plugin-evaluation']);
|
prettyError.skipPackage(['html-plugin-evaluation']);
|
||||||
prettyError.skipNodeFiles();
|
prettyError.skipNodeFiles();
|
||||||
prettyError.skip(function (traceLine) {
|
prettyError.skip(traceLine => traceLine.path === 'html-plugin-evaluation');
|
||||||
return traceLine.path === 'html-plugin-evaluation';
|
|
||||||
});
|
|
||||||
|
|
||||||
module.exports = function (err, context) {
|
module.exports = function (err, context) {
|
||||||
return {
|
return {
|
||||||
toHtml: function () {
|
toHtml: function () {
|
||||||
return 'Html Webpack Plugin:\n<pre>\n' + this.toString() + '</pre>';
|
return `Html Webpack Plugin:\n<pre>\n${this.toString()}</pre>`;
|
||||||
},
|
},
|
||||||
toJsonHtml: function () {
|
toJsonHtml: function () {
|
||||||
return JSON.stringify(this.toHtml());
|
return JSON.stringify(this.toHtml());
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,41 @@
|
||||||
|
/**
|
||||||
|
* This file helps to work with html tags as objects which are easy to modify
|
||||||
|
* and turn into a string
|
||||||
|
*/
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Turn a tag definition into a html string
|
||||||
|
*/
|
||||||
|
function htmlTagObjectToString (tagDefinition, xhtml) {
|
||||||
|
const attributes = Object.keys(tagDefinition.attributes || {})
|
||||||
|
.filter(attributeName => tagDefinition.attributes[attributeName] !== false)
|
||||||
|
.map(attributeName => {
|
||||||
|
if (tagDefinition.attributes[attributeName] === true) {
|
||||||
|
return xhtml ? `${attributeName}="${attributeName}"` : attributeName;
|
||||||
|
}
|
||||||
|
return `${attributeName}="${tagDefinition.attributes[attributeName]}"`;
|
||||||
|
});
|
||||||
|
|
||||||
|
return `<${[tagDefinition.tagName].concat(attributes).join(' ')}${tagDefinition.voidTag && xhtml ? '/' : ''}>${tagDefinition.innerHTML || ''}${tagDefinition.voidTag ? '' : `</${tagDefinition.tagName}>`}`;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Static helper to create a tag object to be get injected into the dom
|
||||||
|
*
|
||||||
|
* @param {String} tagName - the name of the tage e.g. 'div'
|
||||||
|
* @param {Object} attributes - tag attributes e.g. `{ 'class': 'example', disabled: true }`
|
||||||
|
*/
|
||||||
|
function createHtmlTagObject (tagName, attributes) {
|
||||||
|
// https://www.w3.org/TR/html5/syntax.html#void-elements
|
||||||
|
const voidTags = ['area', 'base', 'br', 'col', 'embed', 'hr', 'img', 'input', 'keygen', 'link', 'meta', 'param', 'source', 'track', 'wbr'];
|
||||||
|
return {
|
||||||
|
tagName: tagName,
|
||||||
|
voidTag: voidTags.indexOf(tagName) !== -1,
|
||||||
|
attributes: attributes
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
module.exports = {
|
||||||
|
createHtmlTagObject: createHtmlTagObject,
|
||||||
|
htmlTagObjectToString: htmlTagObjectToString
|
||||||
|
};
|
||||||
|
|
@ -1,14 +1,14 @@
|
||||||
/* This loader renders the template with underscore if no other loader was found */
|
/* This loader renders the template with underscore if no other loader was found */
|
||||||
'use strict';
|
'use strict';
|
||||||
|
|
||||||
var _ = require('lodash');
|
const _ = require('lodash');
|
||||||
var loaderUtils = require('loader-utils');
|
const loaderUtils = require('loader-utils');
|
||||||
|
|
||||||
module.exports = function (source) {
|
module.exports = function (source) {
|
||||||
if (this.cacheable) {
|
if (this.cacheable) {
|
||||||
this.cacheable();
|
this.cacheable();
|
||||||
}
|
}
|
||||||
var allLoadersButThisOne = this.loaders.filter(function (loader) {
|
const allLoadersButThisOne = this.loaders.filter(loader => {
|
||||||
// Loader API changed from `loader.module` to `loader.normal` in Webpack 2.
|
// Loader API changed from `loader.module` to `loader.normal` in Webpack 2.
|
||||||
return (loader.module || loader.normal) !== module.exports;
|
return (loader.module || loader.normal) !== module.exports;
|
||||||
});
|
});
|
||||||
|
|
@ -24,28 +24,26 @@ module.exports = function (source) {
|
||||||
// The following part renders the tempalte with lodash as aminimalistic loader
|
// The following part renders the tempalte with lodash as aminimalistic loader
|
||||||
//
|
//
|
||||||
// Get templating options
|
// Get templating options
|
||||||
var options = loaderUtils.parseQuery(this.query);
|
const options = loaderUtils.parseQuery(this.query);
|
||||||
// Webpack 2 does not allow with() statements, which lodash templates use to unwrap
|
// Webpack 2 does not allow with() statements, which lodash templates use to unwrap
|
||||||
// the parameters passed to the compiled template inside the scope. We therefore
|
// the parameters passed to the compiled template inside the scope. We therefore
|
||||||
// need to unwrap them ourselves here. This is essentially what lodash does internally
|
// need to unwrap them ourselves here. This is essentially what lodash does internally
|
||||||
// To tell lodash it should not use with we set a variable
|
// To tell lodash it should not use with we set a variable
|
||||||
var template = _.template(source, _.defaults(options, { variable: 'data' }));
|
const template = _.template(source, _.defaults(options, { variable: 'data' }));
|
||||||
// All templateVariables which should be available
|
// All templateVariables which should be available
|
||||||
// @see HtmlWebpackPlugin.prototype.executeTemplate
|
// @see HtmlWebpackPlugin.prototype.executeTemplate
|
||||||
var templateVariables = [
|
const templateVariables = [
|
||||||
'compilation',
|
'compilation',
|
||||||
'webpack',
|
'webpack',
|
||||||
'webpackConfig',
|
'webpackConfig',
|
||||||
'htmlWebpackPlugin'
|
'htmlWebpackPlugin'
|
||||||
];
|
];
|
||||||
return 'var _ = require(' + loaderUtils.stringifyRequest(this, require.resolve('lodash')) + ');' +
|
return `var _ = require(${loaderUtils.stringifyRequest(this, require.resolve('lodash'))});
|
||||||
'module.exports = function (templateParams) {' +
|
module.exports = function (templateParams) {
|
||||||
// Declare the template variables in the outer scope of the
|
${// Declare the template variables in the outer scope of the
|
||||||
// lodash template to unwrap them
|
// lodash template to unwrap them
|
||||||
templateVariables.map(function (variableName) {
|
templateVariables.map(variableName => `var ${variableName} = templateParams.${variableName}`).join(';')
|
||||||
return 'var ' + variableName + ' = templateParams.' + variableName;
|
};
|
||||||
}).join(';') + ';' +
|
return (${template.source})();
|
||||||
// Execute the lodash template
|
}`;
|
||||||
'return (' + template.source + ')();' +
|
|
||||||
'}';
|
|
||||||
};
|
};
|
||||||
|
|
|
||||||
14
package.json
14
package.json
|
|
@ -1,6 +1,6 @@
|
||||||
{
|
{
|
||||||
"name": "html-webpack-plugin",
|
"name": "html-webpack-plugin",
|
||||||
"version": "2.26.0",
|
"version": "3.0.0",
|
||||||
"description": "Simplifies creation of HTML files to serve your webpack bundles",
|
"description": "Simplifies creation of HTML files to serve your webpack bundles",
|
||||||
"main": "index.js",
|
"main": "index.js",
|
||||||
"files": [
|
"files": [
|
||||||
|
|
@ -16,7 +16,7 @@
|
||||||
},
|
},
|
||||||
"repository": {
|
"repository": {
|
||||||
"type": "git",
|
"type": "git",
|
||||||
"url": "https://github.com/ampedandwired/html-webpack-plugin.git"
|
"url": "https://github.com/jantimon/html-webpack-plugin.git"
|
||||||
},
|
},
|
||||||
"keywords": [
|
"keywords": [
|
||||||
"webpack",
|
"webpack",
|
||||||
|
|
@ -27,9 +27,9 @@
|
||||||
"author": "Charles Blaxland <charles.blaxland@gmail.com> (https://github.com/ampedandwired)",
|
"author": "Charles Blaxland <charles.blaxland@gmail.com> (https://github.com/ampedandwired)",
|
||||||
"license": "MIT",
|
"license": "MIT",
|
||||||
"bugs": {
|
"bugs": {
|
||||||
"url": "https://github.com/ampedandwired/html-webpack-plugin/issues"
|
"url": "https://github.com/jantimon/html-webpack-plugin/issues"
|
||||||
},
|
},
|
||||||
"homepage": "https://github.com/ampedandwired/html-webpack-plugin",
|
"homepage": "https://github.com/jantimon/html-webpack-plugin",
|
||||||
"semistandard": {
|
"semistandard": {
|
||||||
"ignore": [
|
"ignore": [
|
||||||
"examples/*/dist/**/*.*"
|
"examples/*/dist/**/*.*"
|
||||||
|
|
@ -47,7 +47,7 @@
|
||||||
"jade-loader": "^0.8.0",
|
"jade-loader": "^0.8.0",
|
||||||
"jasmine": "^2.5.2",
|
"jasmine": "^2.5.2",
|
||||||
"rimraf": "^2.5.4",
|
"rimraf": "^2.5.4",
|
||||||
"semistandard": "8.0.0",
|
"semistandard": "9.2.1",
|
||||||
"style-loader": "^0.13.1",
|
"style-loader": "^0.13.1",
|
||||||
"underscore-template-loader": "^0.7.3",
|
"underscore-template-loader": "^0.7.3",
|
||||||
"url-loader": "^0.5.7",
|
"url-loader": "^0.5.7",
|
||||||
|
|
@ -56,7 +56,6 @@
|
||||||
},
|
},
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"bluebird": "^3.4.7",
|
"bluebird": "^3.4.7",
|
||||||
"html-minifier": "^3.2.3",
|
|
||||||
"loader-utils": "^0.2.16",
|
"loader-utils": "^0.2.16",
|
||||||
"lodash": "^4.17.3",
|
"lodash": "^4.17.3",
|
||||||
"pretty-error": "^2.0.2",
|
"pretty-error": "^2.0.2",
|
||||||
|
|
@ -64,5 +63,8 @@
|
||||||
},
|
},
|
||||||
"peerDependencies": {
|
"peerDependencies": {
|
||||||
"webpack": "1 || ^2 || ^2.1.0-beta || ^2.2.0-rc"
|
"webpack": "1 || ^2 || ^2.1.0-beta || ^2.2.0-rc"
|
||||||
|
},
|
||||||
|
"engines": {
|
||||||
|
"node": ">= 4.3.2"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -100,7 +100,7 @@ describe('HtmlWebpackPlugin', function () {
|
||||||
filename: 'index_bundle.js'
|
filename: 'index_bundle.js'
|
||||||
},
|
},
|
||||||
plugins: [new HtmlWebpackPlugin()]
|
plugins: [new HtmlWebpackPlugin()]
|
||||||
}, [/<body>[\s]*<script type="text\/javascript" src="index_bundle.js"><\/script>[\s]*<\/body>/], null, done);
|
}, [/<body>[\s]*<script src="index_bundle.js"><\/script>[\s]*<\/body>/], null, done);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('generates a default index.html file with multiple entry points', function (done) {
|
it('generates a default index.html file with multiple entry points', function (done) {
|
||||||
|
|
@ -114,7 +114,7 @@ describe('HtmlWebpackPlugin', function () {
|
||||||
filename: '[name]_bundle.js'
|
filename: '[name]_bundle.js'
|
||||||
},
|
},
|
||||||
plugins: [new HtmlWebpackPlugin()]
|
plugins: [new HtmlWebpackPlugin()]
|
||||||
}, ['<script type="text/javascript" src="util_bundle.js"', '<script type="text/javascript" src="app_bundle.js"'], null, done);
|
}, ['<script src="util_bundle.js"', '<script src="app_bundle.js"'], null, done);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('allows you to specify a custom loader without injection', function (done) {
|
it('allows you to specify a custom loader without injection', function (done) {
|
||||||
|
|
@ -131,7 +131,7 @@ describe('HtmlWebpackPlugin', function () {
|
||||||
template: 'jade-loader!' + path.join(__dirname, 'fixtures/template.jade')
|
template: 'jade-loader!' + path.join(__dirname, 'fixtures/template.jade')
|
||||||
})]
|
})]
|
||||||
},
|
},
|
||||||
['<script type="text/javascript" src="app_bundle.js', 'Some unique text'], null, done);
|
['<script src="app_bundle.js', 'Some unique text'], null, done);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should pass through loader errors', function (done) {
|
it('should pass through loader errors', function (done) {
|
||||||
|
|
@ -170,7 +170,7 @@ describe('HtmlWebpackPlugin', function () {
|
||||||
template: path.join(__dirname, 'fixtures/template.jade')
|
template: path.join(__dirname, 'fixtures/template.jade')
|
||||||
})]
|
})]
|
||||||
},
|
},
|
||||||
['<script type="text/javascript" src="app_bundle.js', 'Some unique text'], null, done);
|
['<script src="app_bundle.js', 'Some unique text'], null, done);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('works when using html-loader', function (done) {
|
it('works when using html-loader', function (done) {
|
||||||
|
|
@ -187,7 +187,7 @@ describe('HtmlWebpackPlugin', function () {
|
||||||
template: 'html-loader!' + path.join(__dirname, 'fixtures/plain.html')
|
template: 'html-loader!' + path.join(__dirname, 'fixtures/plain.html')
|
||||||
})]
|
})]
|
||||||
},
|
},
|
||||||
['<script type="text/javascript" src="app_bundle.js"'], null, done);
|
['<script src="app_bundle.js"'], null, done);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('allows you to specify your own HTML template file', function (done) {
|
it('allows you to specify your own HTML template file', function (done) {
|
||||||
|
|
@ -204,7 +204,7 @@ describe('HtmlWebpackPlugin', function () {
|
||||||
inject: false
|
inject: false
|
||||||
})]
|
})]
|
||||||
},
|
},
|
||||||
['<script type="text/javascript" src="app_bundle.js', 'Some unique text'], null, done);
|
['<script src="app_bundle.js', 'Some unique text'], null, done);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('allows you to inject the assets into a given html file', function (done) {
|
it('allows you to inject the assets into a given html file', function (done) {
|
||||||
|
|
@ -221,7 +221,7 @@ describe('HtmlWebpackPlugin', function () {
|
||||||
inject: true,
|
inject: true,
|
||||||
template: path.join(__dirname, 'fixtures/plain.html')
|
template: path.join(__dirname, 'fixtures/plain.html')
|
||||||
})]
|
})]
|
||||||
}, ['<script type="text/javascript" src="util_bundle.js"', '<script type="text/javascript" src="app_bundle.js"'], null, done);
|
}, ['<script src="util_bundle.js"', '<script src="app_bundle.js"'], null, done);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('allows you to inject the assets into the body of the given template', function (done) {
|
it('allows you to inject the assets into the body of the given template', function (done) {
|
||||||
|
|
@ -238,7 +238,7 @@ describe('HtmlWebpackPlugin', function () {
|
||||||
inject: 'body',
|
inject: 'body',
|
||||||
template: path.join(__dirname, 'fixtures/plain.html')
|
template: path.join(__dirname, 'fixtures/plain.html')
|
||||||
})]
|
})]
|
||||||
}, ['<script type="text/javascript" src="util_bundle.js"', '<script type="text/javascript" src="app_bundle.js"'], null, done);
|
}, ['<script src="util_bundle.js"', '<script src="app_bundle.js"'], null, done);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('allows you to inject the assets into the head of the given template', function (done) {
|
it('allows you to inject the assets into the head of the given template', function (done) {
|
||||||
|
|
@ -255,7 +255,7 @@ describe('HtmlWebpackPlugin', function () {
|
||||||
inject: 'head',
|
inject: 'head',
|
||||||
template: path.join(__dirname, 'fixtures/plain.html')
|
template: path.join(__dirname, 'fixtures/plain.html')
|
||||||
})]
|
})]
|
||||||
}, ['<script type="text/javascript" src="util_bundle.js"', '<script type="text/javascript" src="app_bundle.js"'], null, done);
|
}, ['<script src="util_bundle.js"', '<script src="app_bundle.js"'], null, done);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('allows you to inject a specified asset into a given html file', function (done) {
|
it('allows you to inject a specified asset into a given html file', function (done) {
|
||||||
|
|
@ -273,7 +273,7 @@ describe('HtmlWebpackPlugin', function () {
|
||||||
chunks: ['app'],
|
chunks: ['app'],
|
||||||
template: path.join(__dirname, 'fixtures/plain.html')
|
template: path.join(__dirname, 'fixtures/plain.html')
|
||||||
})]
|
})]
|
||||||
}, ['<script type="text/javascript" src="app_bundle.js"'], null, done);
|
}, ['<script src="app_bundle.js"'], null, done);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('allows you to inject a specified asset into a given html file', function (done) {
|
it('allows you to inject a specified asset into a given html file', function (done) {
|
||||||
|
|
@ -291,7 +291,7 @@ describe('HtmlWebpackPlugin', function () {
|
||||||
excludeChunks: ['util'],
|
excludeChunks: ['util'],
|
||||||
template: path.join(__dirname, 'fixtures/plain.html')
|
template: path.join(__dirname, 'fixtures/plain.html')
|
||||||
})]
|
})]
|
||||||
}, ['<script type="text/javascript" src="app_bundle.js"'], null, done);
|
}, ['<script src="app_bundle.js"'], null, done);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('allows you to use chunkhash with asset into a given html file', function (done) {
|
it('allows you to use chunkhash with asset into a given html file', function (done) {
|
||||||
|
|
@ -310,7 +310,7 @@ describe('HtmlWebpackPlugin', function () {
|
||||||
}, [{
|
}, [{
|
||||||
type: 'chunkhash',
|
type: 'chunkhash',
|
||||||
chunkName: 'app',
|
chunkName: 'app',
|
||||||
containStr: '<script type="text/javascript" src="app_bundle.js?%chunkhash%"'
|
containStr: '<script src="app_bundle.js?%chunkhash%"'
|
||||||
}], null, done);
|
}], null, done);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
@ -344,7 +344,7 @@ describe('HtmlWebpackPlugin', function () {
|
||||||
}
|
}
|
||||||
})]
|
})]
|
||||||
},
|
},
|
||||||
['<script type="text/javascript" src="app_bundle.js"'], null, done);
|
['<script src="app_bundle.js"'], null, done);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('works with source maps', function (done) {
|
it('works with source maps', function (done) {
|
||||||
|
|
@ -356,7 +356,7 @@ describe('HtmlWebpackPlugin', function () {
|
||||||
filename: 'index_bundle.js'
|
filename: 'index_bundle.js'
|
||||||
},
|
},
|
||||||
plugins: [new HtmlWebpackPlugin()]
|
plugins: [new HtmlWebpackPlugin()]
|
||||||
}, ['<script type="text/javascript" src="index_bundle.js"'], null, done);
|
}, ['<script src="index_bundle.js"'], null, done);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('handles hashes in bundle filenames', function (done) {
|
it('handles hashes in bundle filenames', function (done) {
|
||||||
|
|
@ -367,7 +367,7 @@ describe('HtmlWebpackPlugin', function () {
|
||||||
filename: 'index_bundle_[hash].js'
|
filename: 'index_bundle_[hash].js'
|
||||||
},
|
},
|
||||||
plugins: [new HtmlWebpackPlugin()]
|
plugins: [new HtmlWebpackPlugin()]
|
||||||
}, [/<script type="text\/javascript" src="index_bundle_[0-9a-f]+\.js"*/], null, done);
|
}, [/<script src="index_bundle_[0-9a-f]+\.js"*/], null, done);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('handles hashes in the directory which has the bundle file', function (done) {
|
it('handles hashes in the directory which has the bundle file', function (done) {
|
||||||
|
|
@ -379,7 +379,7 @@ describe('HtmlWebpackPlugin', function () {
|
||||||
filename: 'index_bundle_[hash].js'
|
filename: 'index_bundle_[hash].js'
|
||||||
},
|
},
|
||||||
plugins: [new HtmlWebpackPlugin()]
|
plugins: [new HtmlWebpackPlugin()]
|
||||||
}, [/<script type="text\/javascript" src="\/dist\/[0-9a-f]+\/index_bundle_[0-9a-f]+\.js"*/], null, done);
|
}, [/<script src="\/dist\/[0-9a-f]+\/index_bundle_[0-9a-f]+\.js"*/], null, done);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('allows to append hashes to the assets', function (done) {
|
it('allows to append hashes to the assets', function (done) {
|
||||||
|
|
@ -390,7 +390,7 @@ describe('HtmlWebpackPlugin', function () {
|
||||||
filename: 'index_bundle.js'
|
filename: 'index_bundle.js'
|
||||||
},
|
},
|
||||||
plugins: [new HtmlWebpackPlugin({hash: true})]
|
plugins: [new HtmlWebpackPlugin({hash: true})]
|
||||||
}, ['<script type="text/javascript" src="index_bundle.js?%hash%"'], null, done);
|
}, ['<script src="index_bundle.js?%hash%"'], null, done);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('allows to append hashes to the assets', function (done) {
|
it('allows to append hashes to the assets', function (done) {
|
||||||
|
|
@ -401,7 +401,7 @@ describe('HtmlWebpackPlugin', function () {
|
||||||
filename: 'index_bundle.js'
|
filename: 'index_bundle.js'
|
||||||
},
|
},
|
||||||
plugins: [new HtmlWebpackPlugin({hash: true, inject: true})]
|
plugins: [new HtmlWebpackPlugin({hash: true, inject: true})]
|
||||||
}, ['<script type="text/javascript" src="index_bundle.js?%hash%"'], null, done);
|
}, ['<script src="index_bundle.js?%hash%"'], null, done);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should work with the css extract plugin', function (done) {
|
it('should work with the css extract plugin', function (done) {
|
||||||
|
|
@ -534,7 +534,7 @@ describe('HtmlWebpackPlugin', function () {
|
||||||
publicPath: 'http://cdn.example.com/assets/'
|
publicPath: 'http://cdn.example.com/assets/'
|
||||||
},
|
},
|
||||||
plugins: [new HtmlWebpackPlugin()]
|
plugins: [new HtmlWebpackPlugin()]
|
||||||
}, ['<script type="text/javascript" src="http://cdn.example.com/assets/index_bundle.js"'], null, done);
|
}, ['<script src="http://cdn.example.com/assets/index_bundle.js"'], null, done);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('handles subdirectories in the webpack output bundles', function (done) {
|
it('handles subdirectories in the webpack output bundles', function (done) {
|
||||||
|
|
@ -545,7 +545,7 @@ describe('HtmlWebpackPlugin', function () {
|
||||||
filename: 'assets/index_bundle.js'
|
filename: 'assets/index_bundle.js'
|
||||||
},
|
},
|
||||||
plugins: [new HtmlWebpackPlugin()]
|
plugins: [new HtmlWebpackPlugin()]
|
||||||
}, ['<script type="text/javascript" src="assets/index_bundle.js"'], null, done);
|
}, ['<script src="assets/index_bundle.js"'], null, done);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('handles subdirectories in the webpack output bundles along with a public path', function (done) {
|
it('handles subdirectories in the webpack output bundles along with a public path', function (done) {
|
||||||
|
|
@ -557,7 +557,7 @@ describe('HtmlWebpackPlugin', function () {
|
||||||
publicPath: 'http://cdn.example.com/'
|
publicPath: 'http://cdn.example.com/'
|
||||||
},
|
},
|
||||||
plugins: [new HtmlWebpackPlugin()]
|
plugins: [new HtmlWebpackPlugin()]
|
||||||
}, ['<script type="text/javascript" src="http://cdn.example.com/assets/index_bundle.js"'], null, done);
|
}, ['<script src="http://cdn.example.com/assets/index_bundle.js"'], null, done);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('allows you to configure the title of the generated HTML page', function (done) {
|
it('allows you to configure the title of the generated HTML page', function (done) {
|
||||||
|
|
@ -579,7 +579,7 @@ describe('HtmlWebpackPlugin', function () {
|
||||||
filename: 'index_bundle.js'
|
filename: 'index_bundle.js'
|
||||||
},
|
},
|
||||||
plugins: [new HtmlWebpackPlugin({filename: 'test.html'})]
|
plugins: [new HtmlWebpackPlugin({filename: 'test.html'})]
|
||||||
}, ['<script type="text/javascript" src="index_bundle.js"'], 'test.html', done);
|
}, ['<script src="index_bundle.js"'], 'test.html', done);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('will replace [hash] in the filename with the child compilation hash', function (done) {
|
it('will replace [hash] in the filename with the child compilation hash', function (done) {
|
||||||
|
|
@ -592,7 +592,7 @@ describe('HtmlWebpackPlugin', function () {
|
||||||
plugins: [new HtmlWebpackPlugin({
|
plugins: [new HtmlWebpackPlugin({
|
||||||
filename: 'test-[hash].html'
|
filename: 'test-[hash].html'
|
||||||
})]
|
})]
|
||||||
}, ['<script type="text/javascript" src="index_bundle.js"'], /test-\S+\.html$/, done);
|
}, ['<script src="index_bundle.js"'], /test-\S+\.html$/, done);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('allows you to use an absolute output filename', function (done) {
|
it('allows you to use an absolute output filename', function (done) {
|
||||||
|
|
@ -605,7 +605,7 @@ describe('HtmlWebpackPlugin', function () {
|
||||||
plugins: [new HtmlWebpackPlugin({
|
plugins: [new HtmlWebpackPlugin({
|
||||||
filename: path.resolve(OUTPUT_DIR, 'subfolder', 'test.html')
|
filename: path.resolve(OUTPUT_DIR, 'subfolder', 'test.html')
|
||||||
})]
|
})]
|
||||||
}, ['<script type="text/javascript" src="../index_bundle.js"'], path.join('subfolder', 'test.html'), done);
|
}, ['<script src="../index_bundle.js"'], path.join('subfolder', 'test.html'), done);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('allows you to use an absolute output filename outside the output path', function (done) {
|
it('allows you to use an absolute output filename outside the output path', function (done) {
|
||||||
|
|
@ -618,7 +618,7 @@ describe('HtmlWebpackPlugin', function () {
|
||||||
plugins: [new HtmlWebpackPlugin({
|
plugins: [new HtmlWebpackPlugin({
|
||||||
filename: path.resolve(OUTPUT_DIR, 'test.html')
|
filename: path.resolve(OUTPUT_DIR, 'test.html')
|
||||||
})]
|
})]
|
||||||
}, ['<script type="text/javascript" src="app/index_bundle.js"'], 'test.html', done);
|
}, ['<script src="app/index_bundle.js"'], 'test.html', done);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('allows you to use an relative output filename outside the output path', function (done) {
|
it('allows you to use an relative output filename outside the output path', function (done) {
|
||||||
|
|
@ -631,7 +631,7 @@ describe('HtmlWebpackPlugin', function () {
|
||||||
plugins: [new HtmlWebpackPlugin({
|
plugins: [new HtmlWebpackPlugin({
|
||||||
filename: '../test.html'
|
filename: '../test.html'
|
||||||
})]
|
})]
|
||||||
}, ['<script type="text/javascript" src="app/index_bundle.js"'], 'test.html', done);
|
}, ['<script src="app/index_bundle.js"'], 'test.html', done);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('will try to use a relative name if the filename is in a subdirectory', function (done) {
|
it('will try to use a relative name if the filename is in a subdirectory', function (done) {
|
||||||
|
|
@ -642,7 +642,7 @@ describe('HtmlWebpackPlugin', function () {
|
||||||
filename: 'index_bundle.js'
|
filename: 'index_bundle.js'
|
||||||
},
|
},
|
||||||
plugins: [new HtmlWebpackPlugin({filename: 'assets/test.html'})]
|
plugins: [new HtmlWebpackPlugin({filename: 'assets/test.html'})]
|
||||||
}, ['<script type="text/javascript" src="../index_bundle.js"'], 'assets/test.html', done);
|
}, ['<script src="../index_bundle.js"'], 'assets/test.html', done);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('will try to use a relative name if the filename and the script are in a subdirectory', function (done) {
|
it('will try to use a relative name if the filename and the script are in a subdirectory', function (done) {
|
||||||
|
|
@ -653,7 +653,7 @@ describe('HtmlWebpackPlugin', function () {
|
||||||
filename: 'assets/index_bundle.js'
|
filename: 'assets/index_bundle.js'
|
||||||
},
|
},
|
||||||
plugins: [new HtmlWebpackPlugin({filename: 'assets/demo/test.html'})]
|
plugins: [new HtmlWebpackPlugin({filename: 'assets/demo/test.html'})]
|
||||||
}, ['<script type="text/javascript" src="../../assets/index_bundle.js"'], 'assets/demo/test.html', done);
|
}, ['<script src="../../assets/index_bundle.js"'], 'assets/demo/test.html', done);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('allows you write multiple HTML files', function (done) {
|
it('allows you write multiple HTML files', function (done) {
|
||||||
|
|
@ -676,7 +676,7 @@ describe('HtmlWebpackPlugin', function () {
|
||||||
template: path.join(__dirname, 'fixtures/test.html')
|
template: path.join(__dirname, 'fixtures/test.html')
|
||||||
})
|
})
|
||||||
]
|
]
|
||||||
}, ['<script type="text/javascript" src="index_bundle.js"'], null, function () {
|
}, ['<script src="index_bundle.js"'], null, function () {
|
||||||
expect(fs.existsSync(path.join(OUTPUT_DIR, 'second-file.html'))).toBe(true);
|
expect(fs.existsSync(path.join(OUTPUT_DIR, 'second-file.html'))).toBe(true);
|
||||||
expect(fs.existsSync(path.join(OUTPUT_DIR, 'third-file.html'))).toBe(true);
|
expect(fs.existsSync(path.join(OUTPUT_DIR, 'third-file.html'))).toBe(true);
|
||||||
done();
|
done();
|
||||||
|
|
@ -700,7 +700,7 @@ describe('HtmlWebpackPlugin', function () {
|
||||||
new HtmlWebpackPlugin({template: path.join(__dirname, 'fixtures/empty_html.html')}),
|
new HtmlWebpackPlugin({template: path.join(__dirname, 'fixtures/empty_html.html')}),
|
||||||
new ExtractTextPlugin('styles.css')
|
new ExtractTextPlugin('styles.css')
|
||||||
]
|
]
|
||||||
}, ['<link href="styles.css"', '<script type="text/javascript" src="index_bundle.js"'], null, done);
|
}, ['<link href="styles.css"', '<script src="index_bundle.js"'], null, done);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('exposes the webpack configuration to templates', function (done) {
|
it('exposes the webpack configuration to templates', function (done) {
|
||||||
|
|
@ -750,6 +750,36 @@ describe('HtmlWebpackPlugin', function () {
|
||||||
}, false, true);
|
}, false, true);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
it('passes chunks to the html-webpack-plugin-alter-asset-tags event', function (done) {
|
||||||
|
var chunks;
|
||||||
|
var examplePlugin = {
|
||||||
|
apply: function (compiler) {
|
||||||
|
compiler.plugin('compilation', function (compilation) {
|
||||||
|
compilation.plugin('html-webpack-plugin-alter-asset-tags', function (object, callback) {
|
||||||
|
chunks = object.chunks;
|
||||||
|
callback();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
}
|
||||||
|
};
|
||||||
|
testHtmlPlugin({
|
||||||
|
entry: {
|
||||||
|
app: path.join(__dirname, 'fixtures/index.js')
|
||||||
|
},
|
||||||
|
output: {
|
||||||
|
path: OUTPUT_DIR,
|
||||||
|
filename: '[name]_bundle.js'
|
||||||
|
},
|
||||||
|
plugins: [
|
||||||
|
new HtmlWebpackPlugin(),
|
||||||
|
examplePlugin
|
||||||
|
]
|
||||||
|
}, [], null, function () {
|
||||||
|
expect(chunks).toBeDefined();
|
||||||
|
done();
|
||||||
|
}, false, true);
|
||||||
|
});
|
||||||
|
|
||||||
it('allows events to add a no-value attribute', function (done) {
|
it('allows events to add a no-value attribute', function (done) {
|
||||||
var examplePlugin = {
|
var examplePlugin = {
|
||||||
apply: function (compiler) {
|
apply: function (compiler) {
|
||||||
|
|
@ -779,7 +809,7 @@ describe('HtmlWebpackPlugin', function () {
|
||||||
examplePlugin
|
examplePlugin
|
||||||
]
|
]
|
||||||
},
|
},
|
||||||
[/<body>[\s]*<script type="text\/javascript" src="app_bundle.js" async><\/script>[\s]*<\/body>/],
|
[/<body>[\s]*<script src="app_bundle.js" async><\/script>[\s]*<\/body>/],
|
||||||
null, done, false, false);
|
null, done, false, false);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
@ -812,7 +842,7 @@ describe('HtmlWebpackPlugin', function () {
|
||||||
examplePlugin
|
examplePlugin
|
||||||
]
|
]
|
||||||
},
|
},
|
||||||
[/<body>[\s]*<script type="text\/javascript" src="app_bundle.js"><\/script>[\s]*<\/body>/],
|
[/<body>[\s]*<script src="app_bundle.js"><\/script>[\s]*<\/body>/],
|
||||||
null, done, false, false);
|
null, done, false, false);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
@ -1107,7 +1137,7 @@ describe('HtmlWebpackPlugin', function () {
|
||||||
new HtmlWebpackPlugin(),
|
new HtmlWebpackPlugin(),
|
||||||
examplePlugin
|
examplePlugin
|
||||||
]
|
]
|
||||||
}, ['Injected by plugin', '<script type="text/javascript" src="funky-script.js"'], null, function () {
|
}, ['Injected by plugin', '<script src="funky-script.js"'], null, function () {
|
||||||
expect(eventFired).toBe(true);
|
expect(eventFired).toBe(true);
|
||||||
done();
|
done();
|
||||||
}, false, true);
|
}, false, true);
|
||||||
|
|
@ -1141,7 +1171,7 @@ describe('HtmlWebpackPlugin', function () {
|
||||||
}),
|
}),
|
||||||
examplePlugin
|
examplePlugin
|
||||||
]
|
]
|
||||||
}, ['<script type="text/javascript" src="funky-script.js"'], null, function () {
|
}, ['<script src="funky-script.js"'], null, function () {
|
||||||
expect(eventFired).toBe(true);
|
expect(eventFired).toBe(true);
|
||||||
done();
|
done();
|
||||||
});
|
});
|
||||||
|
|
@ -1167,8 +1197,8 @@ describe('HtmlWebpackPlugin', function () {
|
||||||
new HtmlWebpackPlugin()
|
new HtmlWebpackPlugin()
|
||||||
]
|
]
|
||||||
}, [
|
}, [
|
||||||
/<script type="text\/javascript" src="common_bundle.js">[\s\S]*<script type="text\/javascript" src="util_bundle.js">/,
|
/<script src="common_bundle.js">[\s\S]*<script src="util_bundle.js">/,
|
||||||
/<script type="text\/javascript" src="common_bundle.js"[\s\S]*<script type="text\/javascript" src="index_bundle.js">/], null, done);
|
/<script src="common_bundle.js"[\s\S]*<script src="index_bundle.js">/], null, done);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('adds a favicon', function (done) {
|
it('adds a favicon', function (done) {
|
||||||
|
|
@ -1364,7 +1394,7 @@ describe('HtmlWebpackPlugin', function () {
|
||||||
})
|
})
|
||||||
]
|
]
|
||||||
}, [
|
}, [
|
||||||
/<script type="text\/javascript" src="common_bundle.js">.+<script type="text\/javascript" src="util_bundle.js">.+<script type="text\/javascript" src="index_bundle.js">/], null, done);
|
/<script src="common_bundle.js">.+<script src="util_bundle.js">.+<script src="index_bundle.js">/], null, done);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should sort the chunks in custom (reverse alphabetical) order', function (done) {
|
it('should sort the chunks in custom (reverse alphabetical) order', function (done) {
|
||||||
|
|
@ -1391,7 +1421,7 @@ describe('HtmlWebpackPlugin', function () {
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
]
|
]
|
||||||
}, [/<script type="text\/javascript" src="c_bundle.js">.+<script type="text\/javascript" src="b_bundle.js">.+<script type="text\/javascript" src="a_bundle.js">/], null, done);
|
}, [/<script src="c_bundle.js">.+<script src="b_bundle.js">.+<script src="a_bundle.js">/], null, done);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should sort the chunks by chunk dependencies', function (done) {
|
it('should sort the chunks by chunk dependencies', function (done) {
|
||||||
|
|
@ -1419,7 +1449,7 @@ describe('HtmlWebpackPlugin', function () {
|
||||||
})
|
})
|
||||||
]
|
]
|
||||||
}, [
|
}, [
|
||||||
/<script type="text\/javascript" src="common_bundle.js">.+<script type="text\/javascript" src="aTheme_bundle.js">.+<script type="text\/javascript" src="util_bundle.js">/], null, done);
|
/<script src="common_bundle.js">.+<script src="aTheme_bundle.js">.+<script src="util_bundle.js">/], null, done);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should sort the chunks by chunk dependencies even if a parent chunk is excluded', function (done) {
|
it('should sort the chunks by chunk dependencies even if a parent chunk is excluded', function (done) {
|
||||||
|
|
@ -1448,7 +1478,7 @@ describe('HtmlWebpackPlugin', function () {
|
||||||
})
|
})
|
||||||
]
|
]
|
||||||
}, [
|
}, [
|
||||||
/<script type="text\/javascript" src="aTheme_bundle.js">.+<script type="text\/javascript" src="util_bundle.js">/], null, done);
|
/<script src="aTheme_bundle.js">.+<script src="util_bundle.js">/], null, done);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should add the webpack compilation object as a property of the templateParam object', function (done) {
|
it('should add the webpack compilation object as a property of the templateParam object', function (done) {
|
||||||
|
|
@ -1478,6 +1508,6 @@ describe('HtmlWebpackPlugin', function () {
|
||||||
templateContent: ''
|
templateContent: ''
|
||||||
})]
|
})]
|
||||||
},
|
},
|
||||||
[/^<script type="text\/javascript" src="app_bundle\.js"><\/script>$/], null, done);
|
[/^<script src="app_bundle\.js"><\/script>$/], null, done);
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
|
||||||
|
|
@ -44,6 +44,10 @@ function runExample (exampleName, done) {
|
||||||
|
|
||||||
expect(err).toBeFalsy();
|
expect(err).toBeFalsy();
|
||||||
expect(res.same).toBe(true);
|
expect(res.same).toBe(true);
|
||||||
|
if (!res.same) {
|
||||||
|
console.log(
|
||||||
|
console.log(exampleName, res));
|
||||||
|
}
|
||||||
done();
|
done();
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
|
||||||
|
|
@ -1,11 +1,11 @@
|
||||||
<!DOCTYPE html>
|
<!DOCTYPE html>
|
||||||
<html>
|
<html>
|
||||||
<head>
|
<head>
|
||||||
<meta http-equiv="Content-type" content="text/html; charset=utf-8"/>
|
<meta charset="utf-8"/>
|
||||||
<title>Test</title>
|
<title>Test</title>
|
||||||
</head>
|
</head>
|
||||||
<body>
|
<body>
|
||||||
<p>Some unique text</p>
|
<p>Some unique text</p>
|
||||||
<script type="text/javascript" src="<%=foo.bar%>"></script>
|
<script src="<%=foo.bar%>"></script>
|
||||||
</body>
|
</body>
|
||||||
</html>
|
</html>
|
||||||
|
|
|
||||||
|
|
@ -1,11 +1,11 @@
|
||||||
<!DOCTYPE html>
|
<!DOCTYPE html>
|
||||||
<html>
|
<html>
|
||||||
<head>
|
<head>
|
||||||
<meta http-equiv="Content-type" content="text/html; charset=utf-8"/>
|
<meta charset="utf-8"/>
|
||||||
<title>Test</title>
|
<title>Test</title>
|
||||||
</head>
|
</head>
|
||||||
<body>
|
<body>
|
||||||
<p>Some unique text</p>
|
<p>Some unique text</p>
|
||||||
<script type="text/javascript" src="{%=o.htmlWebpackPlugin.assets.app%}"></script>
|
<script src="{%=o.htmlWebpackPlugin.assets.app%}"></script>
|
||||||
</body>
|
</body>
|
||||||
</html>
|
</html>
|
||||||
|
|
|
||||||
|
|
@ -1,9 +1,9 @@
|
||||||
doctype html
|
doctype html
|
||||||
html
|
html
|
||||||
head
|
head
|
||||||
meta(http-equiv="Content-type" content="text/html; charset=utf-8")
|
meta(charset="utf-8")
|
||||||
title Demo
|
title Demo
|
||||||
body
|
body
|
||||||
p Some unique text
|
p Some unique text
|
||||||
each jsFile in htmlWebpackPlugin.files.js
|
each jsFile in htmlWebpackPlugin.files.js
|
||||||
script(type="text/javascript" src!=jsFile)
|
script(src!=jsFile)
|
||||||
|
|
|
||||||
|
|
@ -1,11 +1,11 @@
|
||||||
<!DOCTYPE html>
|
<!DOCTYPE html>
|
||||||
<html>
|
<html>
|
||||||
<head>
|
<head>
|
||||||
<meta http-equiv="Content-type" content="text/html; charset=utf-8"/>
|
<meta charset="utf-8"/>
|
||||||
<title>Test</title>
|
<title>Test</title>
|
||||||
</head>
|
</head>
|
||||||
<body>
|
<body>
|
||||||
<p>Some unique text</p>
|
<p>Some unique text</p>
|
||||||
<script type="text/javascript" src="<%=htmlWebpackPlugin.files.chunks.app.entry%>"></script>
|
<script src="<%=htmlWebpackPlugin.files.chunks.app.entry%>"></script>
|
||||||
</body>
|
</body>
|
||||||
</html>
|
</html>
|
||||||
|
|
|
||||||
|
|
@ -1,11 +1,11 @@
|
||||||
<!DOCTYPE html>
|
<!DOCTYPE html>
|
||||||
<html>
|
<html>
|
||||||
<head>
|
<head>
|
||||||
<meta http-equiv="Content-type" content="text/html; charset=utf-8"/>
|
<meta charset="utf-8"/>
|
||||||
<title>Test</title>
|
<title>Test</title>
|
||||||
</head>
|
</head>
|
||||||
<body>
|
<body>
|
||||||
<p>Public path is <%= webpackConfig.output.publicPath %></p>
|
<p>Public path is <%= webpackConfig.output.publicPath %></p>
|
||||||
<script type="text/javascript" src="<%= htmlWebpackPlugin.files.chunks.app.entry %>?<%= htmlWebpackPlugin.files.chunks.app.hash %>"></script>
|
<script src="<%= htmlWebpackPlugin.files.chunks.app.entry %>?<%= htmlWebpackPlugin.files.chunks.app.hash %>"></script>
|
||||||
</body>
|
</body>
|
||||||
</html>
|
</html>
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue