dotenv源码解读从.env文件中读取环境变量

yizhihongxing
  1. 简介

dotenv是一个读取.env文件的工具库,能够将.env文件中的环境变量读取到process.env中,使得在程序中可以方便地访问环境变量。本篇文章将从源码角度简要介绍dotenv的实现机制。

  1. 源码解读

dotenv库的主要代码存放在dotenv-webpack和dotenv两个仓库中,可从github上进行下载,下面是dotenv的主要源码解读:

首先,我们需要了解一些dotenv的用法。

require('dotenv').config()

这个命令会从当前目录中的.env文件中读取环境变量,并把这些变量存储到process.env中。我们可以在代码中使用process.env来访问这些变量。

dotenv库的实现很简单,它顺序执行以下步骤:

(1) 指定.env文件所在的路径
(2) 读取.env中的所有环境变量
(3) 将环境变量存储到process.env中

下面我们逐步分析这些步骤。

首先,我们可以看到dotenv库中的config操作,它是dotenv库最为核心的方法,文件实现代码如下:

function config(options: DotenvConfigOptions = {}): DotenvParseOutput {
  if (options.path) {
    const envConfig = parse(fs.readFileSync(options.path, { encoding: 'utf8' }))
    for (const k in envConfig) {
      if (!Object.prototype.hasOwnProperty.call(process.env, k)) {
        process.env[k] = envConfig[k]
      }
    }
    return envConfig
  }

  if (options.encoding) {
    console.warn('config() `options.encoding` is deprecated. Use `options.encoding` instead.')
  }
  const path = findUpSync('.env', { cwd: options.cwd ?? process.cwd() })
  if (path === null) {
    return {}
  }
  return config({ ...options, path })
}

从上面的代码片段中,我们可以看到doten库主要的实现逻辑:

  1. options.path指定.env文件的路径。
  2. 通过fs.readFileSync同步读取.env文件内容。
  3. 将.env文件中的所有key-value对进行解析。
  4. 将解析结果写入到process.env中。

实现步骤非常简单,主要是使用了一些node.js固有的库,具体实现请看下面的代码,其中parse方法实现很简单,直接把字符串按照换行符和等于号进行切割,生成一个键值对,如下:

export function parse(src: string, options?: DotenvParseOptions): DotenvParseOutput {
  const debug = createDebug('dotenv:parse')
  const debugKey = createDebug('dotenv:key')
  const vars = {}
  const newline = /\r\n|[\n\r\u2028\u2029]/g
  // 先用\n分割字符串,然后用=分割key-value,去掉空格
  src.split(newline).forEach((line, idx) => {
    // matching "KEY' and 'VAL' in 'KEY=VAL'
    const keyValueArr = line.match(/^\s*([\w.-]+)\s*=\s*(.*)?\s*$/)
    if (keyValueArr != null && keyValueArr.length > 1) {
      const key = keyValueArr[1]
      let val = (keyValueArr[2] || '')
      const end = val.length - 1
      const isDoubleQuoted = val[0] === '"' && val[end] === '"'
      const isSingleQuoted = val[0] === "'" && val[end] === "'"

      if (isSingleQuoted || isDoubleQuoted) {
        // remove quotes
        val = val.substring(1, end)

        if (isDoubleQuoted) {
          // handle escaped characters
          val = val.replace(/\\([\s\S])|(")/g, '$1')
        }
      } else {
        // interpret variables
        val = expandVariables(val, vars)
      }

      debugKey('%s=%s', key, val)
      vars[key] = val
    } else {
      const lineNumber = idx + 1
      if (line.trim() && !options?.ignoreProcessEnv) {
        console.warn(`dotenv: Invalid line ${lineNumber} in file ${options?.path ?? '.env' }: ${line}`)
      }
    }
  })

  return vars
}
  1. 示例说明

(1) 读取.env文件中的环境变量

首先,创建一个.env文件,内容如下:

TEST=hello world
DB_HOST=localhost
DB_USER=root
DB_PASSWORD=123456
DB_PORT=3306

然后,我们在我们的项目中创建一个main.js文件,代码如下:

require('dotenv').config()

console.log(process.env.TEST) // 输出 hello world
console.log(process.env.DB_HOST) // 输出 localhost
console.log(process.env.DB_USER) // 输出 root
console.log(process.env.DB_PASSWORD) // 输出 123456
console.log(process.env.DB_PORT) // 输出 3306

在项目根目录执行 node main.js 命令即可查看结果。

(2) 指定.env文件的路径

有时候项目根目录并不是.env文件的目录,我们可以使用path配置项指定.env文件的目录:

require('dotenv').config({ path: '/custom/path/to/.env' })

这样dotenv在加载.env文件时,就会使用指定的路径。

本站文章如无特殊说明,均为本站原创,如若转载,请注明出处:dotenv源码解读从.env文件中读取环境变量 - Python技术站

(0)
上一篇 2023年6月27日
下一篇 2023年6月27日

相关文章

  • vue项目中使用TDesign的方法

    下面是使用 TDesign 在 Vue 项目中的具体步骤: 步骤一:安装 TDesign 可以使用 npm 命令行工具进行安装: npm install tdesign-ui 步骤二:配置 TDesign 在 Vue 项目中,可以通过 main.js 或者 App.vue 组件进行全局配置。 1. main.js 方式 在 main.js 文件中导入 TDe…

    other 2023年6月26日
    00
  • C/C++ 双链表之逆序的实例详解

    C/C++ 双链表之逆序的实例详解 本文将详细讲解如何使用 C/C++ 实现双链表的逆序操作,以及具体实现代码的细节。在这篇文章中,我们将会介绍双链表的概念以及如何实现双链表的逆序操作。 双链表的概念 双链表是一种链式存储数据的结构,它类似于单向链表,但每个节点有两个指针分别指向该节点的前驱节点和后继节点。由于它的链式存储结构,双链表灵活、高效,在许多应用场…

    other 2023年6月27日
    00
  • Win 7系统调节音条没声音怎么办?Win 7系统调节音条没声音的解决方法

    Win 7系统调节音条没声音怎么办? 当我们在Win 7系统中调节音量的时候,有时候会发现音条虽然有变化,但是却没有声音输出,这种情况很让人头疼。接下来,我们将为您详细讲解Win 7系统调节音条没声音的本质原因和具体的解决方法。 本质原因 Win 7系统调节音条没声音的本质原因很可能是音频驱动或者软件的问题。因此,解决问题的方法也与之相关。 解决方法 方法1…

    other 2023年6月27日
    00
  • jemeter安装步骤

    Jmeter安装步骤 Apache JMeter是一款功能强大的负载测试工具,它能够模拟大量不同类型的负载,可以测试Web应用程序、数据库、FTP服务器等等。下面是Jmeter安装的步骤。 第一步:下载Jmeter 打开Jmeter官网(http://jmeter.apache.org/),在右侧菜单栏中找到“Downloads”,点击进入下载页面。在下载页…

    其他 2023年3月28日
    00
  • 教你如何正确了解java三大特性!!!!

    教你如何正确了解Java三大特性 Java是一种非常流行的编程语言,它有三大特性:封装、继承和多态。这些特性的理解对于Java的正确使用至关重要。本文将详细讲解如何正确了解Java三大特性。 1. 封装 封装是Java的一种基本特性,它指的是将数据和函数包装在一个对象中,防止外部的程序直接访问和修改对象的内部状态。封装有助于保护对象状态,提高安全性,并且使得…

    other 2023年6月26日
    00
  • 我所理解的ECMAScript、DOM、BOM—写给新手们

    我所理解的ECMAScript、DOM、BOM—写给新手们 作为网站开发者,ECMAScript、DOM、BOM是我们必须熟悉的概念。但是对于初学者来说,这三个概念可能令人困惑。在本文中,我们将介绍这三种概念,并说明它们如何工作和如何互相关联。 ECMAScript ECMAScript是一种由Ecma国际组织标准化的脚本语言,它是JavaScript的…

    其他 2023年3月28日
    00
  • Mysql存储过程循环内嵌套使用游标示例代码

    当在MySQL中使用存储过程时,有时候需要在循环内嵌套使用游标来处理数据。下面是一个完整的攻略,详细讲解了如何在MySQL存储过程中嵌套使用游标,并提供了两个示例说明。 准备工作 在开始之前,确保你已经创建了一个包含需要处理的数据的表。在这个示例中,我们将使用一个名为employees的表,其中包含id和name两个列。 示例1:使用游标遍历数据 首先,我们…

    other 2023年7月28日
    00
  • vxlan协议详解

    VXLAN协议详解 VXLAN(Virtual Extensible LAN)是一种网络虚拟化技术,用于在数据中心网络中扩展虚拟局域网(VLAN)数量。它通过在现有网络基础设施上创建一个逻辑网络层,将虚拟机(VM)和容器连接到虚拟网络中。本攻略中,我们将介绍VXLAN协议的细节,并提供两个示例。 VXLAN协议 VXLAN协议是一种基于UDP的封协议,用于在…

    other 2023年5月7日
    00
合作推广
合作推广
分享本页
返回顶部