When developing web applications by using Create React App, developers get NODE_ENV=development
on their local environment and NODE_ENV=production
on the production build by default. And, modifying NODE_ENV
is forbidden. According to the Create React App, this is an intentional setting to protect the production
environment from a mistake/accident deploying.
You will be able to see scripts like below in package.json
after creating your web app.
// package.json
scripts: {
"start": "react-scripts start", // `NODE_ENV` is equal to `development`.
"build": "react-scripts build", // `NODE_ENV` is equal to `production`.
...
}
If you create or already have .env.development
and .env.production
in the root of your project, these files will be used for running each script. npm start
will pick up .env.development
, and npm build
will use environment variables in .env.production
.
-
What if you want to setup .env.staging
?
This article will show you how to manage environment variables for provisional builds.
Let's dive into that! Oh, if you do not have any experiences of CRA, please Getting started
-
Story
Imagine that your project will have three separated provisional environments; development
, staging
, and production
. Each environment is using different API endpoints. In addition to that, the project may require a REACT_APP_CUSTOM_NODE_ENV
. This is because NODE_ENV
will always be production
for the build regardless.
-
Goal
- Create
.env.development
,.env.staging
, and.env.production
. - Configure environment viriables for each build.
- Modify scripts in
package.json
-
Getting started
Step 1.
Thankfully, dotenv
comes out of box. Let's create .env
files under the root folder to manage environment variables. The files are .env
, .env.development
, .env.staging
, and .env.production
.
-
.env
- Keep all common/shared environment variable -
.env.development
- Variables are used for the local development -
.env.staging
- Variables are used for the staging build -
.env.production
- Variables are used for the production build
For example;
#.env
REACT_APP_DOC_TITLE = "Document title"
//.env.developement
REACT_APP_API_ENDPOINT = "https://development-api.endpoint.com/"
#.env.staging
# NODE_ENV will always be set to "production" for a build
# more details at https://create-react-app.dev/docs/deployment/#customizing-environment-variables-for-arbitrary-build-environments
REACT_APP_CUSTOM_NODE_ENV = "staging"
REACT_APP_API_ENDPOINT = "https://staging-api.endpoint.com/"
#.env.production
REACT_APP_API_ENDPOINT = "https://api.endpoint.com/"
NOTE: The prefix REACT_APP_
is required when creating custom environment variables.
.env.development
and .env.production
As a default behavior, those files will be served with no configuration. You do not even have to update scripts in package.json
.env.staging
Here is the main focus of this post. To target .env.staging
file for the staging build, we need a library to achieve this.
1- Let's install env-cmd
. This library will will help us on using/executing a selected environment file. See more detail
// execute command below at the root of project
$ npm install env-cmd --save
or
$ yarn add env-cmd
2- Add a script in package.json
like below.
// package.json
scripts: {
"start": "react-scripts start", // `NODE_ENV` is equal to `development`.
"build": "react-scripts build", // `NODE_ENV` is equal to `production`.
"build:staging": "env-cmd -f .env.staging react-scripts build", // `NODE_ENV` is equal to `production`.
...
}
3- Finally, test your build:staging
script.
-
Conclusion
The intention of this technique is to use different custom environment variables for many provisional environments without ejecting the default CRA configs.
-
Top comments (22)
How to run it?
i make env.local
it contains
this run script in npm
when i run
it fails and load to .env
@consciousnessdev Thanks for your comment.
You should add
REACT_APP_
prefix to your all custom env variables. eg,REACT_APP_CUSTOM_NODE_ENV
.the command is
npm run start:local
according to your scripts, just missing:
.Sorry for making this mistake, and I will update the article.
Again, thanks for your patient.
Best,
Donghyuk (Jacob) Jang
[Update] But when i run it with your suggestion, it still have an error
I have tried in the example repository, and it seems to be working fine. You may have some conflicts.
The example repository is github.com/DonghyukJacobJang/cra-e...
You will be able to find
.env.local
andstart:local
inpackage.json
.Since I cannot see all your config and settings, providing you the example repo is the best thing I can do at the moment.
Please let me know if you have questions.
Best,
Donghyuk (Jacob) Jang
Pardon Me, i'd typo on 'react-script', which is true 'react-scripts', with 's' in the end of script it, thanks a lot! :O
Thanks Donghyuk. One thing to note here is that, while my
.env.staging
is loaded,process.env.NODE_ENV
is set toproduction
despite theNODE_ENV=staging
setting in.env.staging
Is this consistent with your experience?
Seems so based on create-react-app.dev/docs:
Assuming true, what's the value in adding
NODE_ENV=staging
to.env.staging
?I will test this out ASAP, but I remember that I had to create a custom var to distinguish environments in javascript code.
Nice post, Jacob! thanks!
It's a great post! Thank you. I needed this.
I am very glad that it helps you :) Thank you so much for your message.
I think, env-cmd should be installed by
$ yarn add -D env-cmd
Thank you for the article!
I was initially confused as I was not aware that "start" and "build" scripts use ".env.development" and ".env.production", respectively, by default.
I am using visual studio 2017 with React template
in which I followed above steps but its not working for staging
can you add working source code also
There was
env-cmd
version update and it required a parameter to point a customenv
file, As @foxbit19 discovered.CRA template with
env-cmd
example is available at github.com/DonghyukJacobJang/cra-e... .Thank you so much @sushantraje2000
Thanks for your article! I think
env-cmd
needs-f
argument to load the custom file correctly. Otherwise it fails and load.env
file by default.Thanks for this information. When this article was written, it was using
env-cmd
version 8.0.2. It was not required-f
option. I also just tested the latest version which is 9.0.3 without the parameter and caused an issue. As a result, when pointing a customenv
file, it is required. Thank you so much @foxbit19 .By far the simplest solution. Good stuff!
Much thanks, it works.