PUBLISHED APRIL 24, 2024
Reading Environment Variables in NodeJS
Learn how to efficiently manage environment variables in nodeJS applications. Explore various methods and best practices for security and portability
Prerequisite
Before diving into environment variable management in nodeJS, it's helpful to have a basic understanding of JavaScript and NodeJS fundamentals.
Familiarity with terminal commands and package management tools like npm is also recommended.
Additionally, it's recommended to start from the beginning of this chapter although it's not required.
Environment variables play a crucial role in configuring nodeJS applications across different deployment environments. They allow developers to manage sensitive information, such as API keys, API Tokens or database URLs, without hardcoding them into the source code.
In this part, we'll explore how to read environment variables in Node.js and best practices for handling them
What are Environment Variables?
Environment variables are dynamic values that are set outside of the application and are accessible by all processes running on the system.
They are commonly used to store configuration settings such as API keys, database URLs, and other sensitive information. They provide a convenient way to manage configuration without hardcoding values into the application code.
Accessing Environment Variables in Node.js
NodeJS provides access to environment variables through the process.env
object. This object contains key-value pairs of environment variable names and their corresponding values, that were set at the moment the node process was started.
Here's a basic example of how to access an environment in node:
// Accessing the value of the PORT environment variable
const port = process.env.PORT || 3000;
In this example, we're accessing the value of the `PORT` environment variable. If the `PORT` variable is not set, the application will default to using port 3000.
In the same way you can access any number of custom environment variable you set.
Setting Environment Variables
Environment variables can be set in various ways depending on the deployment environment. Let's explore some common methods:
1. Command Line:
Environment variables can be set directly in the terminal before running the node application.
The following example runs index.js and sets PORT
, PAGE_SIZE
, UNIVERSAL_TOKEN
.
$ PORT=8080 PAGE_SIZE=50 UNIVERSAL_TOKEN=xxpro000111 node app.js
That will pass the user PORT
as 8080, the PAGE_SIZE
as 50 and the UNIVERSAL_TOKEN
as xxpro000111.
This is suitable for development, testing, however for production, you will probably be configuring some bash scripts to export variables.
Her's how you can access the above set environment varibles:
const PORT = process.env.PORT ;
const PAGE_SIZE = process.env.PAGE_SIZE ;
const UNIVERSAL_TOKEN = process.env.UNIVERSAL_TOKEN ;
// or you can use destructuring
//const {PORT, PAGE_SIZE, UNIVERSAL_TOKEN} = process.env ;
2. Environment Configuration Files
Environment variables can be stored in configuration files specific to each environment (e.g., development, staging and production).
Tools like `dotenv` (dotenv npm package) can be used to load these variables from a .env
file into process.env
.
- Start by installing the package in your project.
npm i dotenv
- Then create a .env
file and add the following to it.
PORT=8080
PAGE_SIZE=50
UNIVERSAL_TOKEN=xxpro000111
- Finally, in your codebase, most often in app entry file (server.js, index.js or app.js), you can read the variable as below:
// app.js or server.js, or index.js
require('dotenv').config();
// some more imports
const PORT = process.env.PORT ;
const PAGE_SIZE = process.env.PAGE_SIZE ;
const UNIVERSAL_TOKEN = process.env.UNIVERSAL_TOKEN ;
// or you can use destructuring
//const {PORT, PAGE_SIZE, UNIVERSAL_TOKEN} = process.env ;
// rest of the code
Using environment configuration files enhances portability and ensures consistency across different environments. However, be cautious not to expose sensitive information in these files.
3. Deployment Platforms
Many cloud platforms and hosting services allow you to set environment variables through their dashboards or command-line interfaces.
For example, on Heroku, you can use the Heroku CLI to set environment variables as shown in the command below:
$ heroku config:set PORT=8080
Similarly, AWS Elastic Beanstalk provides a web interface for configuring environment variables.
Personally, I think the prefered option is to use the dashboard rather than the CLI for setting your environment variable whenever applicable.
EXTRA: Built-in .env
file support
Starting from Node.js v20.6.0, node supports .env
files for configuring environment variables by specifying an environment file using the --env-file
argument.
This feature allows you to load environment variables from a file directly without using a third-party library like dotenv
.
Depending on the usecase, you can run the command as follows:
$ node --env-file .env.production app.js
Reading Multiple Environment Files
Sometimes, it's necessary to load environment variables from multiple files, such as separate files for different deployment stages (e.g., development, production).
You can achieve this by chaining multiple dotenv
configurations in your node application.
require('dotenv').config(); // Load default .env file
// Load additional environment files
require('dotenv').config({ path: '.env.development' });
require('dotenv').config({ path: '.env.production' });
require('dotenv').config({ path: '.env.staging' });
This approach allows you to specify different environment variables for each deployment stage while maintaining the simplicity and consistency of using environment configuration files.
Precedence and Collision Resolution
When multiple methods are used to set environment variables, precedence rules determine which value takes effect:
- 1.Command Line Arguments: Environment variables passed as command-line arguments take the highest precedence. They override values from all other sources.
- 2.Environment Configuration Files: Values from
.env
files are typically used during development. They take precedence over values set in the system environment but are overridden by command-line arguments. - 3.System Environment Variables: Environment variables set directly in the system environment have lower precedence. They are overridden by values from command-line arguments,
.env
files, and--env-file
arguments.
Conclusion
In modeJS applications, managing environment variables effectively is crucial for maintaining security and portability.
By understanding the various methods for setting and reading environment variables, along with their precedence rules, developers can configure their applications reliably across different deployment environments.
Whether it's through command-line arguments, environment configuration files, deployment platforms, or experimental features like --env-file
, choosing the right method depends on the specific requirements and constraints of your project.
By following best practices and understanding precedence rules, you can ensure that your node applications are well-configured and ready for deployment.
In the next part, we'll explore writing out to the command line.
PAGE CONTENT
Chapter 1 , Part 1 : Introduction to NodeJS
In this series part, I introduce nodeJS and some technical concepts associated with it. I also show how easy it is to setup and start a simple nodeJS web server.
Chapter 1 , Part 2 : How to Install and Setup NodeJS
In this series part, I run you through the various ways to install nodeJS. I also discuss how to install nvm and use it to switch between different node versions.
Chapter 1 , Part 3 : How much JavaScript do you need to learn NodeJS
In this series part, we explore the nuanced relationship between JavaScript and NodeJS, highlighting some subtle distinctions between the two environments.
Chapter 1 , Part 4 : The v8 Engine and the difference Between NodeJS and the browser
In this series part, we explore the V8 engine and how it interacts with nodeJS. We also discuss node’s event loop and uncover the mystery behinds node’s ability to handle concurrent operations.
Chapter 1 , Part 5 : NPM, the NodeJS package manager
Discover the essentials of npm, the powerful package manager for Node.js. Learn installation, management, publishing, and best practices
Chapter 1 , Part 6 : NodeJS in Development Vs Production
Explore how Node.js behaves differently in development and production environments. Learn key considerations for deploying Node.js applications effectively.
Chapter 2 , Part 1 : Asynchronous Flow Control
In this series part, we'll explore various aspects of asynchronous flow control in Node.js, from basic concepts to advanced techniques.
Chapter 2 , Part 2 : Blocking vs Non-blocking I/O
Explore the differences between blocking and non-blocking I/O in Node.js, and learn how to optimize performance and scalability.
Chapter 2 , Part 3 : Understanding NodeJS Event loop
Exploring the Node.js event loop by understanding its phases, kernel integration, and processes enabling seamless handling of asynchronous operations in your applications.
Chapter 2 , Part 4 : The NodeJS EventEmitter
Explore the power of Node.js EventEmitter: an essential tool for building scalable and event-driven applications. Learn how to utilize it effectively!
Chapter 3 , Part 1 : Working with files in NodeJS
Gain comprehensive insights into file management in Node.js, covering file stats, paths, and descriptors, to streamline and enhance file operations in your applications.
Chapter 3 , Part 2 : Reading and Writing Files in NodeJS
Uncover the fundamentals of reading and writing files in nodeJS with comprehensive examples and use cases for some widely used methods.
Chapter 3 , Part 3 : Working with Folders in NodeJS
Unlock the secrets of folder manipulation in Node.js! Explore essential techniques and methods for working with directories efficiently
Chapter 4 , Part 1 : Running NodeJS Scripts
Master the command line interface for executing nodeJS scripts efficiently. Learn common options and best practices for seamless script execution
Chapter 4 , Part 2 : Reading Environment Variables in NodeJS
Learn how to efficiently manage environment variables in nodeJS applications. Explore various methods and best practices for security and portability
Chapter 4 , Part 3 : Writing Outputs to the Command Line in NodeJS
Learn essential techniques for writing outputs in nodeJS CLI. From basic logging to formatting and understanding stdout/stderr.
Chapter 4 , Part 4 : Reading Inputs from the Command Line in NodeJS
Learn the various ways and strategies to efficiently read command line inputs in nodeJS, making your program more interactive and flexible.
Chapter 4 , Part 5 : The NodeJS Read, Evaluate, Print, and Loop (REPL)
Explore the power of nodeJS's Read, Evaluate, Print, and Loop (REPL). Learn how to use this interactive environment for rapid prototyping, debugging, and experimentation.
Chapter 5 , Part 1 : Introduction to Testing in NodeJS
Discover the fundamentals of testing in nodeJS! Learn about testing types, frameworks, and best practices for building reliable applications.
Chapter 5 , Part 2 : Debugging Tools and Techniques in NodeJS
Explore essential debugging tools and techniques in Node.js development. From built-in options to advanced strategies, and best practices for effective debugging.
Chapter 6 , Part 1 : Project Planning and Setup
Discuss the planning and design process for building our interactive file explorer in Node.js, focusing on core features, UI/UX design, and implementation approach and initial setup.
Chapter 6 , Part 2 : Implementing Basic functionalities
In this guide, we'll implement the basic functionalities of our app which will cover initial welcome and action prompts.
Chapter 6 , Part 3 : Implementating Core Features and Conclusion
In this guide, we'll complete the rest of the more advanced functionalities of our app including, create, search, sort, delete, rename and navigate file directories.