# 从 v14 迁移

注意

我们正在将 Vue CLI 3 beta 升级到使用 webpack 4 + Vue Loader v15,因此如果您计划升级到 Vue CLI 3,您可能需要等待。

# 重大变更

# 现在需要一个插件

Vue Loader v15 现在需要一个配套的 webpack 插件才能正常工作。

// webpack.config.js
const { VueLoaderPlugin } = require('vue-loader')

module.exports = {
  // ...
  plugins: [
    new VueLoaderPlugin()
  ]
}

# 加载器推断

Vue Loader v15 现在使用不同的策略来推断用于语言块的加载器。

<style lang="less"> 为例:在 v14 及更低版本中,它将尝试使用 less-loader 加载块,并隐式地在它之后链接 css-loadervue-style-loader,所有这些都使用内联加载器字符串。

在 v15 中,<style lang="less"> 的行为就像它是一个实际的 *.less 文件被加载一样。因此,为了处理它,您需要在您的主 webpack 配置中提供一个显式规则。

{
  module: {
    rules: [
      // ... other rules
      {
        test: /\.less$/,
        use: [
          'vue-style-loader',
          'css-loader',
          'less-loader'
        ]
      }
    ]
  }
}

好处是,此规则也适用于从 JavaScript 导入的普通 *.less 文件,您可以根据需要配置这些加载器的选项。在 v14 及更低版本中,如果您想为推断的加载器提供自定义选项,您必须在 Vue Loader 自己的 loaders 选项下复制它。在 v15 中,这不再需要。

v15 还允许使用不可序列化的加载器选项,这在以前的版本中是不可能的。

# 从依赖项导入 SFC

通常,对于应用于 .js 文件的 JS 转译规则(例如 babel-loader),我们会使用 exclude: /node_modules/。由于 v15 的推断更改,如果您在 node_modules 中导入 Vue SFC,它的 <script> 部分也将被排除在转译之外。

为了确保 JS 转译应用于 node_modules 中的 Vue SFC,您需要使用排除函数来将它们列入白名单。

{
  test: /\.js$/,
  loader: 'babel-loader',
  exclude: file => (
    /node_modules/.test(file) &&
    !/\.vue\.js/.test(file)
  )
}

# 模板预处理

v14 及更低版本使用 consolidate 来编译 <template lang="xxx">。v15 现在使用 webpack 加载器来对它们进行预处理。

请注意,一些模板加载器(如 pug-loader)导出的是编译后的模板函数,而不是纯 HTML。为了将正确的内容传递给 Vue 的模板编译器,您必须使用输出纯 HTML 的加载器。例如,要支持 <template lang="pug">,您可以使用 pug-plain-loader

{
  module: {
    rules: [
      {
        test: /\.pug$/,
        loader: 'pug-plain-loader'
      }
    ]
  }
}

如果您还打算使用它将 .pug 文件作为 HTML 字符串导入 JavaScript,则需要在预处理加载器之后链接 raw-loader。但是请注意,添加 raw-loader 会破坏 Vue 组件中的使用,因此您需要有两个规则,一个使用 resourceQuery 针对 Vue 文件,另一个(回退)针对 JavaScript 导入。

{
  module: {
    rules: [
      {
        test: /\.pug$/,
        oneOf: [
          // this applies to `<template lang="pug">` in Vue components
          {
            resourceQuery: /^\?vue/,
            use: ['pug-plain-loader']
          },
          // this applies to pug imports inside JavaScript
          {
            use: ['raw-loader', 'pug-plain-loader']
          }
        ]
      }
    ]
  }
}

# 样式注入

客户端样式注入现在会预先注入所有样式,以确保开发模式和提取模式之间的一致行为。

请注意,注入顺序仍然没有保证,因此您应该避免编写依赖于插入顺序的 CSS。

# PostCSS

Vue Loader 不再自动应用 PostCSS 变换。要使用 PostCSS,请像配置普通 CSS 文件一样配置 postcss-loader

# CSS 模块

CSS 模块现在需要通过 css-loader 选项显式配置。<style> 标签上的 module 属性仍然需要用于将本地注入到组件中。

好消息是,您现在可以在一个地方配置 localIdentName

{
  module: {
    rules: [
      {
        test: /\.css$/,
        use: [
          {
            loader: 'vue-style-loader'
          },
          {
            loader: 'css-loader',
            options: {
              modules: true,
              localIdentName: '[local]_[hash:base64:8]'
            }
          }
        ]
      }
    ]
  }
}

如果您只想在一些 Vue 组件中使用 CSS 模块,您可以使用 oneOf 规则并检查 resourceQuery 中的 module 字符串。

{
  test: /\.css$/,
  oneOf: [
    // this matches `<style module>`
    {
      resourceQuery: /module/,
      use: [
        'vue-style-loader',
        {
          loader: 'css-loader',
          options: {
            modules: true,
            localIdentName: '[local]_[hash:base64:5]'
          }
        }
      ]
    },
    // this matches plain `<style>` or `<style scoped>`
    {
      use: [
        'vue-style-loader',
        'css-loader'
      ]
    }
  ]
}

# CSS 提取

与您为普通 CSS 配置的方式相同。使用 mini-css-extract-plugin 的示例用法。

{
  module: {
    rules: [
      {
        test: /\.vue$/,
        use: 'vue-loader'
      },
      {
        test: /\.css$/,
        // or `ExtractTextWebpackPlugin.extract(...)`
        use: [
          MiniCssExtractPlugin.loader,
          'css-loader'
        ]
      }
    ]
  },
  plugins: [
    new MiniCssExtractPlugin({
      filename: 'output.css'
    })
  ]
}

# SSR 外部

在 SSR 中,我们通常使用 webpack-node-externals 将 npm 依赖项从服务器构建中排除。如果您需要从 npm 依赖项中导入 CSS,之前的解决方案是使用这样的白名单。

// webpack config
externals: nodeExternals({
  whitelist: /\.css$/
})

使用 v15,<style src="dep/foo.css"> 的导入现在在请求末尾附加了 resourceQuery 字符串,因此您需要将上述内容更新为。

externals: nodeExternals({
  whitelist: [/\.css$/, /\?vue&type=style/]
})

# 选项弃用

以下选项已弃用,应使用正常的 webpack 模块规则进行配置。

  • loader
  • preLoaders
  • postLoaders
  • postcss
  • cssSourceMap
  • buble
  • extractCSS
  • template

以下选项已弃用,应使用新的 compilerOptions 选项进行配置。

  • preserveWhitespace(使用 compilerOptions.preserveWhitespace
  • compilerModules(使用 compilerOptions.modules
  • compilerDirectives(使用 compilerOptions.directives

以下选项已重命名。

  • transformToRequire(现在重命名为 transformAssetUrls

提示

有关新选项的完整列表,请参阅 选项参考