Recently we were trying to deploy a PWA application developed in react on production. We wanted to create a docker image for our application for an easy deployment. We did not want to run node process in our docker container because it will consume a lot of memory. So, we decided to compile our application as static files and serve these files using nginx to make it lightweight.
We were developing the application on a Windows machine and deploy on a Linux machine so we decided to do the compilation in a docker build. We used following code in our Dockerfile.
FROM node:12 as mynode
ARG environment
# Create app directory
WORKDIR /usr/src/app
# Copy source code to build context
COPY . .
RUN npm install
RUN npm run build:${environment}
# Start from a clean nginx image
FROM nginx
#Copy the build generated file to target image
COPY --from=mynode /usr/src/app/build/ /usr/share/nginx/html
#delete the default nginx config
RUN rm /etc/nginx/conf.d/default.conf
#copy the required nginx config file to image
COPY ui-nginx.conf /etc/nginx/conf.d
Following is the content of ui-nginx.conf file:
server {
listen 80 default_server;
server_name localhost;
location / {
root /usr/share/nginx/html;
access_log /var/log/nginx/ui-access.log;
error_log /var/log/nginx/ui-error.log;
index index.html index.htm;
try_files $uri /index.html;
}
}
Following part is used in package.json file for making the build:
"scripts": {
"start": "env-cmd -f ./environments/.env.development react-scripts start",
"build": "env-cmd -f ./environments/.env.development react-scripts build",
"start:development": "env-cmd -f ./environments/.env.development react-scripts start",
"build:development": "env-cmd -f ./environments/.env.development react-scripts build",
"start:production": "env-cmd -f ./environments/.env.production react-scripts start",
"build:production": "env-cmd -f ./environments/.env.production react-scripts build",
"test": "react-scripts test",
"eject": "react-scripts eject"
}
Following command is used for making the build. We use different environment variables for development and production environment. We pass required build as build args.
docker build --build-arg environment=production -t <imagename>:<tag> .
The above command generates the production build. Using the above method we generated a docker image which is less than 160MB in size. It can be deployed in AWS ECS container of 512MB size.
No comments:
Post a Comment