Package.json: How To Switch Your Node Environment

Package.json: How To Switch Your Node Environment

Problem Statement

As developers, even while putting it all together we need to be able to test the functionality of our applications in a real-life-like environment but without actually making changes to our real data. To achieve this flexibility we as a matter of convention create separate working environments namely "development/staging" and "production".

Objective

In this article, we are going to demonstrate how to switch between our work environments.

Case study

I am going to be using a node application I am presently working on to demonstrate and achieve our objective.

Setting the "scripts" command in package.json

In a Node environment, the package.json is a file that contains the configuration for our application. It describes the dependencies and how our application will be run.

{
    "name": "article",
    "version": "1.0.0",
    "description": "how to switch your node environment",
    "main": "index.js",
    "scripts": {
      "start": "nodemon index.js",
      "test": " "
  }
}

This package.json file is generated when we create a node application by running the command npm init -y in our project root directory, then we can go ahead and fill in the fields as we want. When we also install our node packages and project dependencies, the package.json file is automatically extended and populated with a description of every package we have installed.

{
    "name": "article",
    "version": "1.0.0",
    "description": "how to switch your node environment",
    "main": "index.js",
    "scripts": {
      "start": "nodemon index.js",
      "test": " "
  },
  "dependencies": {
    "axios": "^1.2.0",
    "bcrypt": "^5.0.1",
    "chai": "^4.3.4",
    "chai-http": "^4.3.0",
    "cors": "^2.8.5",
    "dotenv": "^14.3.2",
    "express": "^4.17.2",
    "jsonwebtoken": "^8.5.1",
    "mocha": "^9.1.4",
    "mochawesome": "^7.1.3",
    "nyc": "^15.1.0",
    "pg": "^8.7.1",
    "pg-hstore": "^2.3.4",
    "reflect-metadata": "^0.1.13",
    "typeorm": "^0.3.10"
  },
}

Where our interest lay in this file is the "scripts" property, here we can set the commands that should be run for our app to function. We can have the start, test, build and other custom scripts as we will.

In this scripts property, we need to write commands that will automatically switch our environment and its variables when we decide to run the application. Now, it is necessary to let us know at this point that I have harvested the opinions of developers in the wild from credible discussion groups and their agreements, hence this method I am sharing is not an opinion I singlehandedly came up with. This is to say that it is a method you will find in abundance out there in code repositories.

Create a Node environment

{
    "name": "article",
    "version": "1.0.0",
    "description": "how to switch your node environment",
    "main": "index.js",
    "scripts": {
      "development":"env NODE_ENV=development node index.js",
      "production":"env NODE_ENV=production node index.js",
      //"start": "nodemon index.js",
      "test": " "
  },
  ...
}

Now with this update in our file, we have created an environment variable called NODE_ENV with two different values depending on which environment we would like to run our application.

We can then go into our file and conditionally load environment variables as shown in the file below. The file is a database configuration and the variables point to different database services. To switch our environment, we run the commands:

npm run production for the production environment, and

npm run development for the development environment.

import "dotenv/config"
import "reflect-metadata";
import { DataSource } from "typeorm";
import User from "./entity/users/user.entity";
import Post from "./entity/posts/post.entity";
import Topic from "./entity/topic/topic.entity";

const {
  POSTGRES_DEV_USER,
  POSTGRES_DEV_PASSWORD,
  POSTGRES_DEV_DB,
  POSTGRES_DEV_HOST,
  POSTGRES_PROD_HOST,
  POSTGRES_PROD_USER,
  POSTGRES_PROD_PWORD,
  POSTGRES_PROD_DB,
} = process.env;

const AppDataSource = new DataSource({
  type: "postgres",
  host:
    process.env.NODE_ENV === "production" ? POSTGRES_PROD_HOST :      POSTGRES_DEV_HOST,

  port: 5432,
  username:
    process.env.NODE_ENV === "production" ? POSTGRES_PROD_USER : POSTGRES_DEV_USER,
  password:
    process.env.NODE_ENV === "production"
      ? POSTGRES_PROD_PWORD
      : POSTGRES_DEV_PASSWORD,
  database:
    process.env.NODE_ENV === "production" ? POSTGRES_PROD_DB : POSTGRES_DEV_DB,
  entities: [User, Post, Topic],
  synchronize: true,
  logging: false,
});

By following this approach, we can conveniently test out our application without risking our sensitive resources.

CONCLUSION

In this article, we have been able to demonstrate how to create a testing environment for our application. This is achieved by setting an environment from the package.json file and running from the command line accordingly.

I hope we have learned a skill worthy of practice in our daily development tasks.

Comments and constructive criticisms are welcome :)