Webpack 操练场 ③:使用 Webpack 构建 Vue 开发环境

使用 Webpack 构建 Vue 开发环境

对应代码:github.com/EsunR/webpa...

本章节示例的 Vue 环境为 Vue3,基于 TypeScript 构建

调整 Eslint 规则

如果我们想要 Eslint 支持 Vue 的语法校验,可以通过安装如下几个包来实现:

sh 复制代码
pnpm install eslint-plugin-vue eslint-plugin-prettier-vue -D
  • eslint-plugin-vue:使 eslint 支持 Vue 语法校验的插件
  • eslint-plugin-prettier-vue:在 Vue 项目中使用该插件替代 eslint-plugin-prettier,以支持 Vue 语法校验

调整 eslint 配置为:

js 复制代码
module.exports = {
  extends: [
    '../../.eslintrc.cjs',
    // 使用 eslint 推荐规则集
    'eslint:recommended',
    // 使用 typescript eslint 配置和推荐规则集
    'plugin:@typescript-eslint/recommended',
    // 使用 vue3 配置和推推荐规则集
    'plugin:vue/vue3-recommended',
    // 替代 eslint-plugin-prettier,支持 vue 文件中的 prettier 的校验
    'plugin:prettier-vue/recommended',
  ],
  parserOptions: {
    /**
     * 在使用了 eslint-plugin-vue 后 parser 选项就会被修改为 vue 的 parser 导致无法解析 ts 文件
     * 为了不影响 ts 文件的解析,需要在此指定一个自定义的解析器来解析 ts 文件
     */
    parser: '@typescript-eslint/parser',
  },
  rules: {
    // 自定义规则集
    '@typescript-eslint/no-var-requires': 'off',
    '@typescript-eslint/no-explicit-any': 'off',
    'vue/multi-word-component-names': 'off',
  },
};

如果 extends 的配置太多,搞不清最终的配置长啥样,可以使用 pnpm exec eslint --print-config .eslintrc.cjs 可以查看最终的 eslint 配置。

准备 Vue 环境

安装 vue 相关的依赖:

sh 复制代码
pnpm install vue -S
pnpm install vue-loader vue-style-loader vue-template-compiler -D
  • vue:Vue 核心库
  • vue-loader:Vue 的 webpack loader
  • vue-style-loader:Vue 的样式 loader,替代 style-loader,该 loader 是 style-loader 的代码库 fork,添加了对 scoped 样式与 SSR 相关的支持
  • vue-template-compiler:Vue 模板编译器,会被 vue-loader 调用,需要独立安装

修改 main.ts 引入一个 Vue 组件:

ts 复制代码
import { createApp } from 'vue';
import '@/styles/global.css';
import App from './App.vue';

const app = createApp(App);

app.mount('#app');

修改 public/index.html,为 body 下插入 #app 节点:

diff 复制代码
<!doctype html>
<html lang="en">
  <head>
    <meta charset="UTF-8" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <title>vue template</title>
  </head>
  <body>
+   <div id="app"></div>
  </body>
</html>

使 Webpack 支持编译 Vue

修改 webpack.config.ts,添加对 Vue 的支持:

ts 复制代码
import { VueLoaderPlugin } from 'vue-loader';
import { DefinePlugin, Configuration as WebpackConfiguration } from 'webpack';
// ... ...

const config: WebpackConfiguration = {
  // ... ...
  module: {
    rules: [
      // 处理 Vue
      {
        test: /\.vue$/,
        exclude: /node_modules/,
        use: ['vue-loader'],
      },
      // 处理 ts
      {
        test: /\.tsx?$/,
        exclude: /node_modules/,
        use: [
          'babel-loader',
          {
            loader: 'ts-loader',
            options: {
              // 需要让 ts-loader 识别 vue SFC 中的 ts 代码
              appendTsSuffixTo: ['\\.vue$'],
            },
          },
        ],
      },
      // 加载样式
      {
        test: /\.css$/i,
        use: [
          // 使用 vue-style-loader 替换掉 style-loader
          isDev ? 'vue-style-loader' : MiniCssExtractPlugin.loader,
          'css-loader',
          'postcss-loader',
        ],
      },
      // ... ... 其他的 Loader
    ],
  },
  plugins: [
    // ... ...
    new VueLoaderPlugin(),
    /**
     * 使用 webpack 自带的 DefinePlugin 定义全局变量
     * __VUE_OPTIONS_API__、__VUE_PROD_DEVTOOLS__ 为 true 时候可以使用 Chrome 的 Vue Devtools 插件
     */
    new DefinePlugin({
      __VUE_OPTIONS_API__: isDev,
      __VUE_PROD_DEVTOOLS__: isDev,
    }),
  ],
};

关于 DefinePlugin 再多讲一点,这个插件是用于定义全局变量的,我们可以直接在代码中使用 console.log(__VUE_OPTIONS_API__) 来查看它的值(它并非挂载于 window 上,而是全局对象上)。但是如果你想要定义更多的全局变量,为了让 ts 和 eslint 不报错,你需要进行一系列的设置。

假如我们定义了全局变量:

ts 复制代码
new DefinePlugin({
  // ... ...
  IS_DEV: isDev,
});

我们需要在全局声明该变量的类型,可以在 types 目录下新建 global.d.ts

ts 复制代码
declare const IS_DEV: boolean;

这样 ts 就不会报错了,但是如果我们使用了 eslint,它会报 no-undef 的错误,我们需要在 .eslintrc.cjs 中添加 globals

js 复制代码
module.exports = {
  // ... ...
  globals: {
    IS_DEV: 'readonly',
  },
};

此外,为了不让 ts 引入 Vue 组件时报没有类型定义的错误,我们需要在 types 目录下新建 vue-shim.d.ts

ts 复制代码
/* eslint-disable @typescript-eslint/ban-types */

declare module '*.vue' {
  import type { DefineComponent } from 'vue';

  const component: DefineComponent<{}, {}, any>;
  export default component;
}

此外,我们要调整以下 browserslist 的配置,之前的配置我们考虑到了 IE 浏览器,但是 Vue3 不支持 IE 浏览器,因此我们可以调整浏览器适配的范围,这样可以减少一些 polyfill 的代码。修改 .browserlistrc 文件:

markdown 复制代码
> 0.2% and not dead

表示适配市场份额大于 0.2% 的浏览器,不包括已经停止维护的浏览器。

相关推荐
方才coding43 分钟前
1小时构建Vue3知识体系之vue的生命周期函数
前端·javascript·vue.js
man20171 小时前
【2024最新】基于springboot+vue的闲一品交易平台lw+ppt
vue.js·spring boot·后端
阿征学IT1 小时前
vue过滤器初步使用
前端·javascript·vue.js
王哲晓1 小时前
第四十五章 Vue之Vuex模块化创建(module)
前端·javascript·vue.js
发现你走远了1 小时前
『VUE』25. 组件事件与v-model(详细图文注释)
前端·javascript·vue.js
前端小超超1 小时前
vue3 ts项目结合vant4 复选框+气泡弹框实现一个类似Select样式的下拉选择功能
前端·javascript·vue.js
大叔是90后大叔1 小时前
vue3中查找字典列表中某个元素的值
前端·javascript·vue.js
幸运小圣1 小时前
Vue3 -- 项目配置之prettier【企业级项目配置保姆级教程2】
前端·vue.js·vue
ZJ_.1 小时前
Electron 沙盒模式与预加载脚本:保障桌面应用安全的关键机制
开发语言·前端·javascript·vue.js·安全·electron·node.js
竹秋…2 小时前
element-plus <el-date-picker>日期选择器踩坑!!!!
javascript·vue.js·elementui