Webpack中使用环境变量的各种正确姿势

目录
  • 写在前边
  • 业务代码使用环境变量
    • 使用webpack.DefinePlugin插件在业务代码中注入环境变量
    • webpack.DefinePlugin引发的思考
    • definePlugin所谓的”环境变量“实现方式
    • JSON.stringify()处理环境变量
  • 构建过程中使用环境变量
  • 传统环境变量方法使用webpack构建过程环境变量。
  • 总结

写在前边

你还在为Webpack中各种打包配置而烦恼吗?

今天我们来聊聊webpack中注入环境变量的各种姿势,或者你会觉得注入环境变量通过命令行注入不就可以了吗?

如果你有这种想法,耐心看下去我相信你会有不一样的收获的~

毕竟所谓成长就是一点一滴积累的过程!让我们来聊聊Webpack 5中使用环境变量的各种正确姿势。

文章中从三个方面来讲解Webpack流程中的环境变量:

  • 业务代码中注入使用webpack环境变量。
  • 官方提供构建过程使用webpack环境变量。
  • 传统环境变量方法使用webpack构建过程环境变量。

业务代码使用环境变量

使用webpack.DefinePlugin插件在业务代码中注入环境变量

相信不少同学已经应用过这种场景,我们需要在打包过程中通过webpack注入一些全局变量在业务代码中使用。
比如我们业务入口文件有这样一段代码:

// src/main.js
console.log('hello, Environment variable', __WEPBACK__ENV)

我们希望的是业务代码中碰到这个__WEBPACK__ENV这个变量时,代码中会认识这个变量并且输出正确字符串值pacakges。

想一想我们应该怎么做?

熟悉webpack的同学其实已经想到了,我们可以通过webpack中的definePlugins这个插件进行注入:

const wepback = require('webpack')
// webpack.config.js
...
new webpack.DefinePlugin({
  __WEBPACK__ENV: JSON.stringify('packages'),
  TWO: '1+1',
});

我们通过在webpack的plugins中加入这段配置后当我们运行打包命令后,此时我们业务代码中如果出现__WEBPACK__ENV这个变量的话他就会帮我们替换成为'packages'这个字符串,从而达到类似环境变量注入的效果。

webpack.DefinePlugin引发的思考

或许你已经很熟悉webpack.definePlugins这个插件的使用了,别着急让我们耐心往下看看,由这段代码我们引发出一下的几个思考:

  1. 'packages'已经是string类型了,为什么我们还要使用JSON.stringify()进行处理。
  2. 此时的环境变量真的就是所谓的环境变量吗?

我们先来探讨一下这两个问题:

definePlugin所谓的”环境变量“实现方式

webpack官方文档中这样讲到

(Note that because the plugin does a direct text replacement, the value given to it must include actual quotes inside of the string itself. Typically, this is done either with alternate quotes, such as '"production"', or by using JSON.stringify('production').)

其实他也就是再说webpack.definePlugins本质上是打包过程中的字符串替换,比如我们刚才定义的__WEBPACK__ENV:JSON.stringify('packages')。

在打包过程中,如果我们代码中使用到了__WEPBACK__ENV,webpack会将它的值替换成为对应definePlugins中定义的值,本质上就是匹配字符串替换,并不是传统意义上的环境变量process注入。

这也就回答了我们第二个问题。

JSON.stringify()处理环境变量

接下来我们来看看第一个问题,正所谓实践出真知。我们来试试对比配置两次不同的definePlugin来看看结果:

// webpack.config.js
new webpack.DefinePlugin({
  __WEBPACK__ENV: JSON.stringify('packages'),
  TWO: '1+1',
});

// 打包后的代码 这里我们关闭了devtools 罗列出打包后打包后的代码
console.log('hello, Environment variable', 'packages')
// webpack.config.js
new webpack.DefinePlugin({
  __WEBPACK__ENV: 'packages',
  TWO: '1+1',
});

// 打包后的代码 这里我们关闭了devtools 罗列出打包后打包后的代码
console.log('hello, Environment variable', packages)

仔细对比这两段代码第一个问题的答案其实已经很明了了,针对definePlugin这个插件我们使用它定义key:value全局变量时,他会将value进行会直接替换文本。所以我们通常使用JSON.stringify('pacakges')或者"'packages'"。

对于DefinePlugin的流程以及需要额外注意的细节我们差不多已经说清除了,但是此时我们定义所谓的全局变量是在业务代码中进行使用的。但此时如果我们对于打包构建过程中想使用环境变量的话需要另一种方式来注入。

构建过程中使用环境变量

通常我们在使用webpack过程中需要根据自己独特的需求去使用环境变量进行动态打包,比如一些通过动态读取项目中的文件夹从而在控制台动态和用户交互打包对应不同的bundle。

此时在构建过程中使用环境变量就显得非常重要了,所谓构建过程中使用环境变量简单来说就是在非业务代码中,比如webpack.config.js配置文件中注入环境变量。

我们来看看在项目中输入这行代码:

npx webpack --env goal=local --env production --progress --config ./webpack.config.js

此时这行代码我们相当于运行webpack读取当前目录中的webpack.config.js配置文件进行打包,同时注入两个环境变量goal和progress他们的值分别为local和true。

这样我们就可以在配置文件中使用注入的环境变量了:

const path = require('path');

module.exports = (env) => {
  // Use env.<YOUR VARIABLE> here:
  console.log('Goal: ', env.goal); // 'local'
  console.log('Production: ', env.production); // true

  return {
    entry: './src/index.js',
    output: {
      filename: 'bundle.js',
      path: path.resolve(__dirname, 'dist'),
    },
  };
};

细心的你可以已经发现了,这里我们的module.exports导出的是一个包含env的函数,而并不是传统的对象了。

通常,module.exports 指向配置对象。要使用 env 变量,你必须将 module.exports 转换成一个函数的方式进行使用。
我们来看看如果不使用函数的话:

const path = require('path');

// Use env.<YOUR VARIABLE> here:
console.log('Goal: ', process.env.goal); // undefined
console.log('Production: ', process.env.production); // undefined

module.exports = {
  entry: './src/index.js',
  output: {
    filename: 'bundle.js',
    path: path.resolve(__dirname, 'dist'),
  },
};

我们可以看到我们读取node进程process中的env.goal/production发现两个分别都是undefined。

也就是说通常我们使用--env在命令行中为webpack构建过程注入环境变量时,需要将配置文件的module.exports导出一个函数的形式,从而在函数第一个参数中获取对应的key拿到对应的环境变量value。

那么问题又来了,诶?假如我就是想在node的process中获得对应的环境变量呢?我应该怎么办,我就是不想写一个函数。

传统环境变量方法使用webpack构建过程环境变量。

应该怎么办呢?其实webpack对应打包的原理就是通过shell命令去执行我们的配置文件(nodejs配置文件)。

假如我们在运行命令webpack时注入真正传统意义上的环境变量而非通过--env是不是就可以了呢?接下来我们来试一试~

这里我们借助了一个非常好用的环境变量插件cross-env,它的使用方式很简单可以帮助我们在不同环境下linux/windows...中以相同的方式去注入运行时环境变量,接下来我们来使用一下它:

不要忘记安装npm install --save-dev cross-env。

// package.json
 "build": "cross-env NAME_W=aaa webpack --config ./webpack.config.js"

我们通过cross-env NAME_W=aaa注入了一个环境变量。

// webpack.config.js
console.log(process.env.NAME_W, 'env'); // 'aaa'

module.exports = {
  entry: './src/a.js',
};

在我们的尝试下,发现其实通过命令行传统方式注入环境变量的形式也是可以的!这样我们就逃离了导出必须是一个函数的限制可以"为所欲为了"。

总结

在webpack构建以及业务代码中,环境变量的注入对于我们的帮助是非常大的。当需要一定体系的前端工程化代码时,环境变量无论是在构建过程还是业务代码中都起到了至关重要的作用。

看到这里我们想说到的其实都已经讲到了,我们来进行一个简单的总结吧:

在webpack打包业务代码时,我们需要使用类似环境变量的方式使用一些全局变量时,可以通过webpack.DefinePlugin去定义一些变量从而在业务代码中使用。(但是需要注意上边讲到的JSON.stringify())。

同时在构建过程中,我们可以通过webpack官方提供的--env参数以及在配置文件中通过module.exports函数的方式使用--env定义的环境变量。

同时也可以在构建过程中通过我们日常使用的方式注入环境变量而“逃脱”webpack的限制,直接使用命令行中定义的环境变量然后通过process.env.xxx去获取。

到此这篇关于Webpack中使用环境变量的文章就介绍到这了,更多相关Webpack使用环境变量内容请搜索我们以前的文章或继续浏览下面的相关文章希望大家以后多多支持我们!

(0)

相关推荐

  • Webpack设置环境变量的一些误区详解

    一.前言 日常的前端开发工作中,至少会有两套构建环境 一套开发时使用,构建结果用于本地开发调试,不进行代码压缩.打印 debug 信息.包含 sourcemap 文件等 一套发布时使用,构建结果用于线上,即代码都是压缩过的.运行时不打印 debug 信息.静态文件不包括 sourcemap 等 webpack 4.0 版本开始引入了 mode 的概念 选项 描述 development 会将 process.env.NODE_ENV 的值设为 development.启用 NamedChunks

  • Webpack中使用环境变量的各种正确姿势

    目录 写在前边 业务代码使用环境变量 使用webpack.DefinePlugin插件在业务代码中注入环境变量 webpack.DefinePlugin引发的思考 definePlugin所谓的"环境变量"实现方式 JSON.stringify()处理环境变量 构建过程中使用环境变量 传统环境变量方法使用webpack构建过程环境变量. 总结 写在前边 你还在为Webpack中各种打包配置而烦恼吗? 今天我们来聊聊webpack中注入环境变量的各种姿势,或者你会觉得注入环境变量通过命令

  • docker中的环境变量使用与常见问题解决方案

    前言 docker可以为容器配置环境变量.配置的途径有两种: 在制作镜像时,通过ENV命令为镜像增加环境变量.在容器启动时使用该环境变量. 在容器启动时候,通过参数配置环境变量,如果与镜像中有重复的环境变量,会覆盖镜像的环境变量. 使用docker exec {containerID} env即可查看容器中生效的环境变量. [root@localhost ~]# docker exec 984 env PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/

  • Linux中修改环境变量及生效方法

    在/etc/profile文件中添加变量[对所有用户生效(永久的)] 用VI在文件/etc/profile文件中增加变量,该变量将会对Linux下所有用户有效,并且是"永久的". 要让刚才的修改马上生效,需要执行以下代码 source /etc/profile 以上这篇Linux中修改环境变量及生效方法就是小编分享给大家的全部内容了,希望能给大家一个参考,也希望大家多多支持我们.

  • 在Linux操作系统中修改环境变量的方法

    方法一:在/etc/profile文件中添加变量[对所有用户生效(永久的)] 用VI在文件/etc/profile文件中增加变量,该变量将会对Linux下所有用户有效,并且是"永久的". 要让刚才的修改马上生效,需要执行以下代码 复制代码 代码如下: # source /etc/profile 方法二:在用户目录下的.bash_profile文件中增加变量[对单一用户生效(永久的)] 用VI在用户目录下的.bash_profile文件中增加变量,改变量仅会对当前用户有效,并且是&quo

  • Linux中Bash环境变量的配置方法

    Shell 是一个用 C 语言编写的程序,它是用户使用 Linux 的桥梁.Shell 既是一种命令语言,又是一种程序设计语言. 以下是几种shell版本,bash是默认的: sh(全称 Bourne Shell): 是UNIX最初使用的 shell,而且在每种 UNIX 上都可以使用. Bourne Shell 在 shell 编程方面相当优秀,但在处理与用户的交互方面做得不如其他几种 shell. bash(全称 Bourne Again Shell): LinuxOS 默认的,它是 Bou

  • Mac Book中Java环境变量设置的方法

    Mac 启动加载文件位置(可设置环境变量) -------------------------------------------------------  (1)首先要知道你使用的Mac OS X是什么样的Shell,使用命令 echo $SHELL 如果输出的是:csh或者是tcsh,那么你用的就是C Shell. 如果输出的是:bash,sh,zsh,那么你的用的可能就是Bourne Shell的一个变种. Mac OS X 10.2之前默认的是C Shell. Mac OS X 10.3

  • window中oracle环境变量设置方法分享

    window server中Oracle的环境变量设置 1.右击"我的电脑"->选择"属性"->选择"高级"->单击"环境变量"2.选择"Path"这一行,单击"编辑",在"Path"的变量值文本框的最后面先加入一个分号":",然后再分号后面加入sqlplus文件的目录路径,如"C:\Program Files\orac

  • 如何在mac中修改环境变量path

    (1)首先要知道使用的Mac OS X是什么样的Shell,使用命令 echo $SHELL 如果输出的是:csh或者是tcsh,那么用的就是C Shell. 如果输出的是:bash,sh,zsh,那么用的可能就是Bourne Shell的一个变种. Mac OS X 10.2之前默认的是C Shell. Mac OS X 10.3之后默认的是Bourne Shell. (2)如果是Bourne Shell. 那么可以把要添加的环境变量添加到主目录下面的.profile或者.bash_profi

  • 在python代码中加入环境变量的语句操作

    以GraphViz为例: 下载安装好的路径名字为C:/Program Files (x86)/Graphviz2.38 import os os.environ["PATH"] += os.pathsep + 'C:/Program Files (x86)/Graphviz2.38/bin/' #注意修改你的路径 os.environ['path']返回的是所有环境变量的所在的位置,我们这里是为了添加,所以再重新造一个. os.pathsep返回的是分隔符";" 补

  • golang 在windows中设置环境变量的操作

    安装完成后需要在系统环境变量中设置 GOPATH为项目目录 GOROOT为安装目录 path中设置好安装目录到bin目录 打开cmd,输入go env,出现如下配置生效 补充:Golang 环境变量须知 1.前言 无论你是使用 Windows.Linux 还是 Mac 操作系统来开发 Go 应用程序,在安装好 Go 安装语言开发工具之后,都必须配置好 Go 语言开发所要求的 环境变量,才算初步完成 Go 开发环境的搭建. 但对于一些初学者来说,可能不太明白 Go 语言中常用的环境变量的作用以及如

随机推荐