前段工程 - require.context

244 阅读1分钟

require.context是什么

一个webpack的api,通过执行require.context函数获取一个特定的上下文,主要用来实现自动化导入模块,在前端工程中,如果遇到从一个文件夹引入很多模块的情况,可以使用这个api,它会遍历文件夹中的指定文件,然后自动导入,使得不需要每次显式的调用import导入模块

分析require.context

require.context函数接受三个参数

  1. directory {String} -读取文件的路径
  2. useSubdirectories {Boolean} -是否遍历文件的子目录
  3. regExp {RegExp} -匹配文件的正则

require.context(directoryPath, useSubdirectories = false, regExp = /.vue$/);

借用webpakc官网的例子

require.context('./test', false, /.test.js$/); 上面的代码遍历当前目录下的test文件夹的所有.test.js结尾的文件,不遍历子目录

大概用图片来表示的话就是这样子的

image.png

在index.js中调用 require.context('./test', false, /.test.js$/); 会得到test文件下3个文件的执行环境

值得注意的是require.context函数执行后返回的是一个函数,并且这个函数有3个属性

  1. resolve {Function} -接受一个参数request,request为test文件夹下面匹配文件的相对路径,返回这个匹配文件相对于整个工程的相对路径
  2. keys {Function} -返回匹配成功模块的名字组成的数组
  3. id {String} -执行环境的id,返回的是一个字符串,主要用在module.hot.accept,应该是热加载?

这三个都是作为函数的属性(注意是作为函数的属性,函数也是对象,有对应的属性)

案例: 组件全局注册 Demo

代码目录 image.png

在 main.js 中 引入

import './globalComponents'

在 globalComponents/index.js 中全局注册

import Vue from 'vue'

const requireComponent = require.context(
    // 其组件目录的相对路径
    './components',
    // 是否查询其子目录
    false,
    // 匹配基础组件文件名的正则表达式
    /.vue$/
)

requireComponent.keys().forEach(fileName => {
    // 获取组件配置
    const componentConfig = requireComponent(fileName)
    fileName = fileName.split('/').pop().replace(/.\w+$/, '')
    const componentName = `global-${fileName}`
    // 全局注册组件
    Vue.component(
        componentName,
        // 如果这个组件选项是通过 `export default` 导出的,
        // 那么就会优先使用 `.default`,
        // 否则回退到使用模块的根。
        componentConfig.default || componentConfig
    )
})

在 app.vue 中直接使用

<global-module1></global-module1>
<global-module2></global-module2>
<global-module3></global-module3>

关于 ERROR: index.js?6912:5 Uncaught TypeError: webpack_require(...).context is not a function

require.context的参数只能使用字面值,不能使用变量代替

const plugins = require.context("./items", false, /.js$/);