Spaces:
Sleeping
Sleeping
| const path = require('path') | |
| const semver = require('semver') | |
| const defaultPolyfills = [ | |
| // promise polyfill alone doesn't work in IE, | |
| // needs this as well. see: #1642 | |
| 'es.array.iterator', | |
| // this is required for webpack code splitting, vuex etc. | |
| 'es.promise', | |
| // this is needed for object rest spread support in templates | |
| // as vue-template-es2015-compiler 1.8+ compiles it to Object.assign() calls. | |
| 'es.object.assign', | |
| // #2012 es.promise replaces native Promise in FF and causes missing finally | |
| 'es.promise.finally' | |
| ] | |
| const { | |
| default: getTargets, | |
| isRequired | |
| } = require('@babel/helper-compilation-targets') | |
| function getIntersectionTargets (targets, constraintTargets) { | |
| const intersection = Object.keys(constraintTargets).reduce( | |
| (results, browser) => { | |
| // exclude the browsers that the user does not need | |
| if (!targets[browser]) { | |
| return results | |
| } | |
| // if the user-specified version is higher the minimum version that supports esmodule, than use it | |
| results[browser] = semver.gt( | |
| semver.coerce(constraintTargets[browser]), | |
| semver.coerce(targets[browser]) | |
| ) | |
| ? constraintTargets[browser] | |
| : targets[browser] | |
| return results | |
| }, | |
| {} | |
| ) | |
| return intersection | |
| } | |
| function getModernTargets (targets) { | |
| const allModernTargets = getTargets( | |
| { esmodules: true }, | |
| { ignoreBrowserslistConfig: true } | |
| ) | |
| // use the intersection of modern mode browsers and user defined targets config | |
| const result = getIntersectionTargets(targets, allModernTargets) | |
| // webpack 4 uses acorn 6, which does not support newer syntaxes such as optional chaining | |
| // so we have to add samsung 12 as a target to force transpiling these syntaxes | |
| // https://github.com/vuejs/vue-cli/issues/6449#issuecomment-828559068 | |
| result.samsung = '12.0.0' | |
| return result | |
| } | |
| function getWCTargets (targets) { | |
| // targeting browsers that at least support ES2015 classes | |
| // https://github.com/babel/babel/blob/v7.9.6/packages/babel-compat-data/data/plugins.json#L194-L204 | |
| const allWCTargets = getTargets( | |
| { | |
| browsers: [ | |
| 'Chrome >= 46', | |
| 'Firefox >= 45', | |
| 'Safari >= 10', | |
| 'Edge >= 13', | |
| 'iOS >= 10', | |
| 'Electron >= 0.36' | |
| ] | |
| }, | |
| { ignoreBrowserslistConfig: true } | |
| ) | |
| // use the intersection of browsers supporting Web Components and user defined targets config | |
| return getIntersectionTargets(targets, allWCTargets) | |
| } | |
| function getPolyfills (targets, includes) { | |
| // if no targets specified, include all default polyfills | |
| if (!targets || !Object.keys(targets).length) { | |
| return includes | |
| } | |
| const compatData = require('core-js-compat').data | |
| return includes.filter(item => { | |
| if (!compatData[item]) { | |
| throw new Error(`Cannot find polyfill ${item}, please refer to 'core-js-compat' for a complete list of available modules`) | |
| } | |
| return isRequired(item, targets, { compatData }) | |
| }) | |
| } | |
| module.exports = (context, options = {}) => { | |
| const presets = [] | |
| const plugins = [] | |
| const defaultEntryFiles = JSON.parse(process.env.VUE_CLI_ENTRY_FILES || '[]') | |
| // Though in the vue-cli repo, we only use the two environment variables | |
| // for tests, users may have relied on them for some features, | |
| // dropping them may break some projects. | |
| // So in the following blocks we don't directly test the `NODE_ENV`. | |
| // Rather, we turn it into the two commonly used feature flags. | |
| if (!process.env.VUE_CLI_TEST && process.env.NODE_ENV === 'test') { | |
| // Both Jest & Mocha set NODE_ENV to 'test'. | |
| // And both requires the `node` target. | |
| process.env.VUE_CLI_BABEL_TARGET_NODE = 'true' | |
| // Jest runs without bundling so it needs this. | |
| // With the node target, tree shaking is not a necessity, | |
| // so we set it for maximum compatibility. | |
| process.env.VUE_CLI_BABEL_TRANSPILE_MODULES = 'true' | |
| } | |
| // JSX | |
| if (options.jsx !== false) { | |
| let jsxOptions = {} | |
| if (typeof options.jsx === 'object') { | |
| jsxOptions = options.jsx | |
| } | |
| let vueVersion = 2 | |
| try { | |
| const Vue = require('vue') | |
| vueVersion = semver.major(Vue.version) | |
| } catch (e) {} | |
| if (vueVersion === 2) { | |
| presets.push([require('@vue/babel-preset-jsx'), jsxOptions]) | |
| } else if (vueVersion === 3) { | |
| plugins.push([require('@vue/babel-plugin-jsx'), jsxOptions]) | |
| } | |
| } | |
| const runtimePath = path.dirname(require.resolve('@babel/runtime/package.json')) | |
| const runtimeVersion = require('@babel/runtime/package.json').version | |
| const { | |
| polyfills: userPolyfills, | |
| loose = false, | |
| debug = false, | |
| useBuiltIns = 'usage', | |
| modules = false, | |
| bugfixes = true, | |
| targets: rawTargets, | |
| spec, | |
| ignoreBrowserslistConfig, | |
| configPath, | |
| include, | |
| exclude, | |
| shippedProposals, | |
| forceAllTransforms, | |
| decoratorsBeforeExport, | |
| decoratorsLegacy, | |
| // entry file list | |
| entryFiles = defaultEntryFiles, | |
| // Undocumented option of @babel/plugin-transform-runtime. | |
| // When enabled, an absolute path is used when importing a runtime helper after transforming. | |
| // This ensures the transpiled file always use the runtime version required in this package. | |
| // However, this may cause hash inconsistency if the project is moved to another directory. | |
| // So here we allow user to explicit disable this option if hash consistency is a requirement | |
| // and the runtime version is sure to be correct. | |
| absoluteRuntime = runtimePath, | |
| // https://babeljs.io/docs/en/babel-plugin-transform-runtime#version | |
| // By default transform-runtime assumes that @babel/runtime@7.0.0-beta.0 is installed, which means helpers introduced later than 7.0.0-beta.0 will be inlined instead of imported. | |
| // See https://github.com/babel/babel/issues/10261 | |
| // And https://github.com/facebook/docusaurus/pull/2111 | |
| version = runtimeVersion | |
| } = options | |
| // resolve targets for preset-env | |
| let targets = getTargets(rawTargets, { ignoreBrowserslistConfig, configPath }) | |
| // Webpack 4 uses acorn 6 underlyingly; | |
| // The highest ESLint version that Vue CLI v4 supports is 6.x; | |
| // Both can only parse ES2019 syntax + BigInt at most. | |
| // Thus, newer syntaxes such as optional chaining and nullish coalescing won't | |
| // be accept by webpack / ESLint, and must be processed by Babel first. | |
| // Chrome 79 is the last Chrome version that doesn't support these syntaxes. | |
| // So the targets set by the user cannot be higher than Chrome 79. | |
| if (!targets.chrome || semver.gt(targets.chrome, '79.0.0')) { | |
| targets.chrome = '79.0.0' | |
| } | |
| if (process.env.VUE_CLI_BABEL_TARGET_NODE) { | |
| // running tests in Node.js | |
| targets = { node: '12' } | |
| } else if (process.env.VUE_CLI_BUILD_TARGET === 'wc' || process.env.VUE_CLI_BUILD_TARGET === 'wc-async') { | |
| // targeting browsers that at least support ES2015 classes | |
| targets = getWCTargets(targets) | |
| } else if (process.env.VUE_CLI_MODERN_BUILD) { | |
| // targeting browsers that at least support <script type="module"> | |
| targets = getModernTargets(targets) | |
| } | |
| // included-by-default polyfills. These are common polyfills that 3rd party | |
| // dependencies may rely on (e.g. Vuex relies on Promise), but since with | |
| // useBuiltIns: 'usage' we won't be running Babel on these deps, they need to | |
| // be force-included. | |
| let polyfills | |
| const buildTarget = process.env.VUE_CLI_BUILD_TARGET || 'app' | |
| if ( | |
| buildTarget === 'app' && | |
| useBuiltIns === 'usage' && | |
| !process.env.VUE_CLI_BABEL_TARGET_NODE | |
| ) { | |
| polyfills = getPolyfills(targets, userPolyfills || defaultPolyfills) | |
| plugins.push([ | |
| require('./polyfillsPlugin'), | |
| { polyfills, entryFiles, useAbsolutePath: !!absoluteRuntime } | |
| ]) | |
| } else { | |
| polyfills = [] | |
| } | |
| const envOptions = { | |
| bugfixes, | |
| corejs: useBuiltIns ? require('core-js/package.json').version : false, | |
| spec, | |
| loose, | |
| debug, | |
| modules, | |
| targets, | |
| useBuiltIns, | |
| ignoreBrowserslistConfig, | |
| configPath, | |
| include, | |
| exclude: polyfills.concat(exclude || []), | |
| shippedProposals, | |
| forceAllTransforms | |
| } | |
| // cli-plugin-jest sets this to true because Jest runs without bundling | |
| if (process.env.VUE_CLI_BABEL_TRANSPILE_MODULES) { | |
| envOptions.modules = 'commonjs' | |
| if (process.env.VUE_CLI_BABEL_TARGET_NODE) { | |
| // necessary for dynamic import to work in tests | |
| plugins.push(require('babel-plugin-dynamic-import-node')) | |
| } | |
| } | |
| // pass options along to babel-preset-env | |
| presets.unshift([require('@babel/preset-env'), envOptions]) | |
| // additional <= stage-3 plugins | |
| // Babel 7 is removing stage presets altogether because people are using | |
| // too many unstable proposals. Let's be conservative in the defaults here. | |
| plugins.push( | |
| require('@babel/plugin-syntax-dynamic-import'), | |
| [require('@babel/plugin-proposal-decorators'), { | |
| decoratorsBeforeExport, | |
| legacy: decoratorsLegacy !== false | |
| }], | |
| [require('@babel/plugin-proposal-class-properties'), { loose }] | |
| ) | |
| // transform runtime, but only for helpers | |
| plugins.push([require('@babel/plugin-transform-runtime'), { | |
| regenerator: useBuiltIns !== 'usage', | |
| // polyfills are injected by preset-env & polyfillsPlugin, so no need to add them again | |
| corejs: false, | |
| helpers: useBuiltIns === 'usage', | |
| useESModules: !process.env.VUE_CLI_BABEL_TRANSPILE_MODULES, | |
| absoluteRuntime, | |
| version | |
| }]) | |
| return { | |
| sourceType: 'unambiguous', | |
| overrides: [{ | |
| exclude: [/@babel[\/|\\\\]runtime/, /core-js/], | |
| presets, | |
| plugins | |
| }, { | |
| // there are some untranspiled code in @babel/runtime | |
| // https://github.com/babel/babel/issues/9903 | |
| include: [/@babel[\/|\\\\]runtime/], | |
| presets: [ | |
| [require('@babel/preset-env'), envOptions] | |
| ] | |
| }] | |
| } | |
| } | |
| // a special flag to tell @vue/cli-plugin-babel to include @babel/runtime for transpilation | |
| // otherwise the above `include` option won't take effect | |
| process.env.VUE_CLI_TRANSPILE_BABEL_RUNTIME = true | |