You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
71 lines
2.6 KiB
71 lines
2.6 KiB
// https://gist.github.com/samthor/64b114e4a4f539915a95b91ffd340acc |
|
const safariFix = `!function(){var e=document,t=e.createElement("script");if(!("noModule"in t)&&"onbeforeload"in t){var n=!1;e.addEventListener("beforeload",function(e){if(e.target===t)n=!0;else if(!e.target.hasAttribute("nomodule")||!n)return;e.preventDefault()},!0),t.type="module",t.src=".",e.head.appendChild(t),t.remove()}}();` |
|
|
|
const path = require('path') |
|
const HtmlWebpackPlugin = require('html-webpack-plugin') |
|
const { semver } = require('@vue/cli-shared-utils') |
|
const { projectModuleTargets } = require('../util/targets') |
|
|
|
const minSafariVersion = projectModuleTargets.safari |
|
const minIOSVersion = projectModuleTargets.ios |
|
const supportsSafari10 = |
|
(minSafariVersion && semver.lt(semver.coerce(minSafariVersion), '11.0.0')) || |
|
(minIOSVersion && semver.lt(semver.coerce(minIOSVersion), '11.0.0')) |
|
const needsSafariFix = supportsSafari10 |
|
|
|
class SafariNomoduleFixPlugin { |
|
constructor ({ unsafeInline, jsDirectory }) { |
|
this.unsafeInline = unsafeInline |
|
this.jsDirectory = jsDirectory |
|
} |
|
|
|
apply (compiler) { |
|
if (!needsSafariFix) { |
|
return |
|
} |
|
const { RawSource } = compiler.webpack |
|
? compiler.webpack.sources |
|
: require('webpack-sources') |
|
|
|
const ID = 'SafariNomoduleFixPlugin' |
|
compiler.hooks.compilation.tap(ID, compilation => { |
|
HtmlWebpackPlugin.getHooks(compilation).alterAssetTagGroups.tap(ID, data => { |
|
let scriptTag |
|
|
|
if (this.unsafeInline) { |
|
// inject inline Safari 10 nomodule fix |
|
scriptTag = { |
|
tagName: 'script', |
|
closeTag: true, |
|
innerHTML: safariFix |
|
} |
|
} else { |
|
// inject the fix as an external script |
|
const safariFixPath = path.join(this.jsDirectory, 'safari-nomodule-fix.js') |
|
const fullSafariFixPath = path.join(compilation.options.output.publicPath, safariFixPath) |
|
compilation.assets[safariFixPath] = new RawSource(safariFix) |
|
scriptTag = { |
|
tagName: 'script', |
|
closeTag: true, |
|
attributes: { |
|
src: fullSafariFixPath |
|
} |
|
} |
|
} |
|
|
|
let tags = data.bodyTags |
|
if (data.plugin.options.scriptLoading === 'defer') { |
|
tags = data.headTags |
|
} |
|
|
|
// insert just before the first actual script tag, |
|
// and after all other tags such as `meta` |
|
const firstScriptIndex = tags.findIndex(tag => tag.tagName === 'script') |
|
tags.splice(firstScriptIndex, 0, scriptTag) |
|
}) |
|
}) |
|
} |
|
} |
|
|
|
SafariNomoduleFixPlugin.safariFix = safariFix |
|
module.exports = SafariNomoduleFixPlugin
|
|
|