question-mark
Stuck on an issue?

Lightrun Answers was designed to reduce the constant googling that comes with debugging 3rd party libraries. It collects links to all the places you might be looking at while hunting down a tough bug.

And, if you’re still stuck at the end, we’re happy to hop on a call to see how we can help out.

How to run React app inside Docker with env vars

See original GitHub issue

Already set the env vars in my Docker on AWS, but the app is not using it when running.

Does anyone know how I can do it?

For development, I’m using the .env file. For the build, I’m putting the .env file in .dockerignore so this development file doesn’t go into the build version. My intention is to use the default Env Vars configuration in AWS ECS.

I’m not using docker-compose. I’m just using the Dockerfile.

Issue Analytics

  • State:closed
  • Created 7 years ago
  • Reactions:2
  • Comments:46 (6 by maintainers)

github_iconTop GitHub Comments

28reactions
baxfordcommented, Feb 6, 2017

thanks for all the tips on this page, I’ve been able to get CRA running in docker. I found a few other handy things:

  • if you link port 35729 on your container to 35729 on your system, hot reloading works
  • you can watch/run all tests within docker as well with a ‘test’ config in docker-compose.
  • I’ve also created a multi-purpose docker container that will build the production version and serve it with nginx. I’m not sure if this is necessarily what I’d use in production (as the files could just be served statically via s3/CDN, but it allows me to quickly look at a production version of my app, or let me run it in a CI enviroment).

Here’s my setup: Dockerfile

FROM node:6.3.1

RUN apt-get update && \
    apt-get install -y nginx

WORKDIR /src

COPY . /src

RUN npm install

CMD /bin/bash ./run.sh

run.sh (executed by the docker container)

#!/usr/bin/env bash
set -e
set -x

export NODE_ENV="${NODE_ENV:-development}"

if [ $NODE_ENV == "development" ]; then
  # this runs webpack-dev-server with hot reloading
  npm start
else
  # build the app and serve it via nginx
  npm run build
  mkdir -p $ROOT/logs/nginx
  nginx -g 'daemon off;' -c $ROOT/src/nginx.conf
  nginx -c $ROOT/src/nginx.conf
fi

NOTES: If NODE_ENV=development this will run the webpack-development-server, otherwise it will build the app and serve it via nginx. (I got this from a great blog post which I can’t for the life of me find anymore)

nginx.conf

worker_processes 1;

events {
  worker_connections 1024;
}

http {
  access_log /var/log/nginx/access.log;
  error_log  /var/log/nginx/error.log;

  server {
    gzip on;
    listen 8000;
    server_name localhost;
    root /src/build;

    include /etc/nginx/mime.types;

    location /nginx_status {
      stub_status on;
      access_log off;
    }

    location / {
      try_files $uri $uri/ /index.html;
    }
  }
}

docker-compose.yml

version: '2'
services:
  dev:
    build:
      context: .
      dockerfile: Dockerfile
    image: ui-dev
    container_name: webpack-container
    environment:
      - NODE_ENV=development
    ports:
      - "8080:3000"
      - "35729:35729"
    volumes:
      - .:/src
      - /src/node_modules
  test:
    build:
      context: .
      dockerfile: Dockerfile
    image: ui-test
    container_name: webpack-test-container
    environment:
      - NODE_ENV=test
    volumes:
      - .:/src
      - /src/node_modules
    command: npm test
  prod:
    build:
      context: .
      dockerfile: Dockerfile
    image: guest-ui-prod
    container_name: prod-container
    environment:
      - NODE_ENV=production
    ports:
      - "8000:8000"
    volumes:
      - /src/node_modules

For my development with hot reloading, I run one terminal window and execute the following: docker-compose up -d dev

To watch and run tests, I then open another terminal windown and execute: docker-compose up test (I don’t use the -d flag as I want to see the output)

And for a production sanity check, I can run docker-compose up prod NOTE: - this will serve the react app at the time the docker image was created, so if you’ve been making changes since the docker build, these won’t appear. However, if this is used as part of a CI system which checks out the code and builds it, the image built will be the latest.

On an unrelated note, I also found it useful to set the NODE_PATH in my package.json to allow relative imports:

  "scripts": {
    "start": "NODE_PATH=./src/ react-scripts start",
    "build": "NODE_PATH=./src/ react-scripts build",
   ...
  }
21reactions
haluvibecommented, Jan 17, 2017

@gearon Docker is amazing, I can run create-react-app without installing node on my local, hence avoiding having to use node/npm version managers such as nvm. Plus, it just works! I would even go so far to say at the very least you should add a how to integrate with docker section to the readme.

If anyone is interested I got it to work with the following (for all steps below, replace the string boilerplate with you apps name) - if there are any improvements I can make, please let me know.

Step 1) After creating your react app with create-react-app -> cd into your newly created apps directory and run this command

docker network create boilerplate

Step 2) Add a dockerfile to the root of your app directory

Dockerfile

FROM node:6.9.4

# Prepare app directory
RUN mkdir -p /usr/src/app
WORKDIR /usr/src/app/

# Install dependencies
COPY package.json /usr/src/app/
RUN npm install --silent

ADD . /usr/src/app/

EXPOSE 3000
CMD [ "npm", "start" ]

Step 3) create a docker-compose.yml in your root directory

docker-compose.yml

version: "2"

services:
  frontend:
    container_name: "boilerplate"
    build: .
    environment:
      env_file: .env
      NODE_ENV: development
    ports:
      - '3000:3000'
    volumes:
      - .:/usr/src/app

networks:
  default:
    external:
      name: boilerplate

You can now access your app as normal at http://localhost:3000

and you can even interact with your new docker container via the following command

docker-compose run --rm boilerplate /bin/bash

Yes, this isn’t following some of the nodejs docker recommend best practices, but I use the above only for the dev environment configuration so I’m unaware if those recommendations are needed. I’m open minded to improving this though.

Obviously you need to configure the build docker differently than above.

Read more comments on GitHub >

github_iconTop Results From Across the Web

How to implement runtime environment variables with create ...
We should be able to configure our React application using -e flag (environment variables) when using Docker run command.
Read more >
Reading an environment variable in react which was set by ...
First in GH action file I use run: docker build ... --build-arg REACT_APP_APIURL=${{ secrets.REACT_APP_APIURL }} . Then I use them in Dockerfile ......
Read more >
Making environment variables accessible in front-end containers
Learn how to inject environment variables directly into your React, Angular, or Vue.js codebase during the front-end container build ...
Read more >
ReactJS + Docker - Environment Variables - Jason Campos
Injecting environment variables into client-side rendered ReactJS applications built with Docker and Compose.
Read more >
How to use react environment variables: The complete guide
Learn how to use react environment variables in development and production environments with Kubernetes and docker compose examples.
Read more >

github_iconTop Related Medium Post

No results found

github_iconTroubleshoot Live Code

Lightrun enables developers to add logs, metrics and snapshots to live code - no restarts or redeploys required.
Start Free

github_iconTop Related Reddit Thread

No results found

github_iconTop Related Hackernoon Post

No results found

github_iconTop Related Tweet

No results found

github_iconTop Related Dev.to Post

No results found

github_iconTop Related Hashnode Post

No results found