vue,react 项目.env 环境变量原理解析

简介:

.env 文件扩展了 vuereact 项目的环境变量,相信大家用的比较多了,vuereactcli 里把这些配置好了,所以大家可以直接用,但是换个框架或者换个项目,这个问题就比较麻烦了。

比如说现在写 Ant Design Pro 的项目,它内部用的是 umi 来做这些配置,默认只支持.env 文件,那我想支持.env.development.env.production或者其他模式的环境变量怎么办?当然 umi@3 可以用config.dev.jsconfig.jsconfig.prod.js这些文件结合UMI_ENV来解决这些问题,可是心里很不爽。

于是你又开始写一个 nuxt 的项目,发现它里面的配置文件 nuxt.config.js 也仅仅支持 env:{} 对象扩展,那么问题来了,那我还想支持.env.development.env.production或者其他模式的环境变量怎么办?

既然项目的改变我们控制不了,那我们只能搞清楚 vue 里的 env 文件加载原理,以不变应万变了。

下面是解决思路。

1.新建一个.env.development 文件

NODE_ENV=development
VUE_APP_WEB_TITLE=test
VUE_APP_BASE_URL=http://0.0.0.0

2.核心实现,解析 env 文件

先安装依赖
dotenv
dotenv-expand

根据 vue-cli 源码
https://github.com/vuejs/vue-cli/blob/dev/packages/%40vue/cli-service/lib/Service.js

https://github.com/vuejs/vue-cli/blob/dev/packages/%40vue/cli-service/lib/util/resolveClientEnv.js
改写

parseEnv.js

const fs = require('fs')
const path = require('path')
const dotenv = require('dotenv') // 解析.env.*文件为键值对,并写入环境变量。
const variableExpansion = require('dotenv-expand') // 拿到dotenv解析的参数,扩展计算机上已经存在的环境变量(存在就赋值)。

const resolve = dir => path.join(__dirname, dir)
const prefixRE = /^VUE_APP_/

/*
这里加载的是development 模式文件,需要其他的可以根据启动参数来动态修改,或者NODE_ENV来修改

ag:根据NODE_ENV来修改
const env = variableExpansion(
  dotenv.parse(fs.readFileSync(resolve(`./.env.${process.env.NODE_ENV}`)))
)
*/
const env = variableExpansion(
  dotenv.parse(fs.readFileSync(resolve(`./.env.development`)))
)
Object.keys(env).forEach(key => {
  if (prefixRE.test(key) || key === 'NODE_ENV') {
    env[key] = JSON.stringify(env[key]) // JSON.stringify 的目的是为了给webpack.DefinePlugin 的值是 '"development"',DefinePlugin插件配置要求
  } else {
    Reflect.deleteProperty(env, key)
  }
})

module.exports = env

3.配置 webpack,注入环境变量到项目中

const webpack = require('webpack')

// 加载.env.* 环境变量
const env = require('./parseEnv')

console.log(env) // {NODE_ENV: '"development"',VUE_APP_WEB_TITLE: '"test"',VUE_APP_BASE_URL: '"http://0.0.0.0"'}

module.exports = {
  plugins: [new webpack.DefinePlugin({ 'process.env': env })]
}

4.使用

console.log(process.env.VUE_APP_BASE_URL) // 'http://0.0.0.0'

参考链接

1.https://github.com/vuejs/vue-cli/blob/dev/packages/%40vue/cli-service/lib/Service.js

2.https://github.com/vuejs/vue-cli/blob/dev/packages/%40vue/cli-service/lib/util/resolveClientEnv.js

Logo

前往低代码交流专区

更多推荐