Skip to content

Commit

Permalink
feat: Add publicPath support relative path
Browse files Browse the repository at this point in the history
  • Loading branch information
Wind4 authored and jantimon committed Oct 3, 2018
1 parent f4bccb7 commit dbbdd81
Show file tree
Hide file tree
Showing 2 changed files with 159 additions and 6 deletions.
23 changes: 19 additions & 4 deletions index.js
Original file line number Diff line number Diff line change
Expand Up @@ -517,6 +517,21 @@ class HtmlWebpackPlugin {
return assets.js.length && assets.js.every((assetPath) => /\.hot-update\.js$/.test(assetPath));
}

/**
* Check the path is a absolute url path
*
* @param {string | undefined} path
*/
isAbsolutePath (path) {
if (typeof path === 'undefined' || path === '') return false;
// If the path start with '/'
if (path.indexOf('/') === 0) return true;
// If the path contain the '://' scheme
if (path.indexOf('://') !== -1) return true;

return false;
}

/**
* The htmlWebpackPluginAssets extracts the asset information of a webpack compilation
* for all given entry names
Expand All @@ -535,13 +550,13 @@ class HtmlWebpackPlugin {

/**
* @type {string} the configured public path to the asset root
* if a publicPath is set in the current webpack config use it otherwise
* if the absolute path publicPath is set in the current webpack config use it otherwise
* fallback to a realtive path
*/
let publicPath = typeof compilation.options.output.publicPath !== 'undefined'
// If a hard coded public path exists use it
let publicPath = this.isAbsolutePath(compilation.options.output.publicPath)
// If a absolute path is set in the publicPath use it
? compilation.mainTemplate.getPublicPath({hash: compilationHash})
// If no public path was set get a relative url path
// If publicPath was a relative path get the realtive path
: path.relative(path.resolve(compilation.options.output.path, path.dirname(childCompilationOutputName)), compilation.options.output.path)
.split(path.sep).join('/');

Expand Down
142 changes: 140 additions & 2 deletions spec/basic.spec.js
Original file line number Diff line number Diff line change
Expand Up @@ -485,6 +485,51 @@ describe('HtmlWebpackPlugin', () => {
}, ['<link href="styles.css?%hash%"'], null, done);
});

it('should allow to add cache hashes to with the css assets', done => {
testHtmlPlugin({
mode: 'production',
entry: path.join(__dirname, 'fixtures/theme.js'),
output: {
path: OUTPUT_DIR,
filename: 'index_bundle.js',
publicPath: 'some/'
},
module: {
rules: [
{ test: /\.css$/, use: [MiniCssExtractPlugin.loader, 'css-loader'] }
]
},
plugins: [
new HtmlWebpackPlugin({hash: true}),
new MiniCssExtractPlugin({filename: 'styles.css'})
]
}, ['<link href="styles.css?%hash%"'], null, done);
});

it('should allow to add cache hashes to with the css assets', done => {
testHtmlPlugin({
mode: 'production',
entry: path.join(__dirname, 'fixtures/theme.js'),
output: {
path: OUTPUT_DIR,
filename: 'index_bundle.js',
publicPath: 'some/'
},
module: {
rules: [
{ test: /\.css$/, use: [MiniCssExtractPlugin.loader, 'css-loader'] }
]
},
plugins: [
new HtmlWebpackPlugin({
hash: true,
filename: path.resolve(OUTPUT_DIR, 'subfolder', 'test.html')
}),
new MiniCssExtractPlugin({filename: 'styles.css'})
]
}, ['<link href="../styles.css?%hash%"'], path.join('subfolder', 'test.html'), done);
});

it('should inject css files when using the extract text plugin', done => {
testHtmlPlugin({
mode: 'production',
Expand Down Expand Up @@ -550,6 +595,19 @@ describe('HtmlWebpackPlugin', () => {
}, ['<link href="styles.css" rel="stylesheet"/>'], null, done);
});

it('prepends the webpack public path to relative path', done => {
testHtmlPlugin({
mode: 'production',
entry: path.join(__dirname, 'fixtures/index.js'),
output: {
path: OUTPUT_DIR,
filename: 'index_bundle.js',
publicPath: 'assets/'
},
plugins: [new HtmlWebpackPlugin()]
}, ['<script src="index_bundle.js"'], null, done);
});

it('prepends the webpack public path to script src', done => {
testHtmlPlugin({
mode: 'production',
Expand All @@ -575,7 +633,35 @@ describe('HtmlWebpackPlugin', () => {
}, ['<script src="assets/index_bundle.js"'], null, done);
});

it('handles subdirectories in the webpack output bundles along with a public path', done => {
it('handles subdirectories in the webpack output bundles along with a relative path', done => {
testHtmlPlugin({
mode: 'production',
entry: path.join(__dirname, 'fixtures/index.js'),
output: {
path: OUTPUT_DIR,
filename: 'assets/index_bundle.js',
publicPath: 'some/'
},
plugins: [new HtmlWebpackPlugin()]
}, ['<script src="assets/index_bundle.js"'], null, done);
});

it('handles subdirectories in the webpack output bundles along with a relative path', done => {
testHtmlPlugin({
mode: 'production',
entry: path.join(__dirname, 'fixtures/index.js'),
output: {
path: OUTPUT_DIR,
filename: 'assets/index_bundle.js',
publicPath: 'some/'
},
plugins: [new HtmlWebpackPlugin({
filename: path.resolve(OUTPUT_DIR, 'subfolder', 'test.html')
})]
}, ['<script src="../assets/index_bundle.js"'], path.join('subfolder', 'test.html'), done);
});

it('handles subdirectories in the webpack output bundles along with a absolute path', done => {
testHtmlPlugin({
mode: 'production',
entry: path.join(__dirname, 'fixtures/index.js'),
Expand Down Expand Up @@ -1433,7 +1519,42 @@ describe('HtmlWebpackPlugin', () => {
}, [/<link rel="shortcut icon" href="\/some\/+[^"]+\.ico">/], null, done);
});

it('adds a favicon with a publichPath set to [hash]/ and replaces the hash', done => {
it('adds a favicon with publicPath set to some/', done => {
testHtmlPlugin({
mode: 'production',
entry: path.join(__dirname, 'fixtures/index.js'),
output: {
path: OUTPUT_DIR,
publicPath: 'some/',
filename: 'index_bundle.js'
},
plugins: [
new HtmlWebpackPlugin({
favicon: path.join(__dirname, 'fixtures/favicon.ico')
})
]
}, [/<link rel="shortcut icon" href="[^"]+\.ico">/], null, done);
});

it('adds a favicon with publicPath set to some/', done => {
testHtmlPlugin({
mode: 'production',
entry: path.join(__dirname, 'fixtures/index.js'),
output: {
path: OUTPUT_DIR,
publicPath: 'some/',
filename: 'index_bundle.js'
},
plugins: [
new HtmlWebpackPlugin({
favicon: path.join(__dirname, 'fixtures/favicon.ico'),
filename: path.resolve(OUTPUT_DIR, 'subfolder', 'test.html')
})
]
}, [/<link rel="shortcut icon" href="\.\.\/[^"]+\.ico">/], path.join('subfolder', 'test.html'), done);
});

it('adds a favicon with a publichPath set to /[hash]/ and replaces the hash', done => {
testHtmlPlugin({
mode: 'production',
entry: path.join(__dirname, 'fixtures/index.js'),
Expand All @@ -1450,6 +1571,23 @@ describe('HtmlWebpackPlugin', () => {
}, [/<link rel="shortcut icon" href="\/[a-z0-9]{20}\/favicon\.ico">/], null, done);
});

it('adds a favicon with a publichPath set to [hash]/ and replaces the hash', done => {
testHtmlPlugin({
mode: 'production',
entry: path.join(__dirname, 'fixtures/index.js'),
output: {
path: OUTPUT_DIR,
publicPath: '[hash]/',
filename: 'index_bundle.js'
},
plugins: [
new HtmlWebpackPlugin({
favicon: path.join(__dirname, 'fixtures/favicon.ico')
})
]
}, [/<link rel="shortcut icon" href="favicon\.ico">/], null, done);
});

it('adds a favicon with inject enabled', done => {
testHtmlPlugin({
mode: 'production',
Expand Down

0 comments on commit dbbdd81

Please sign in to comment.