Connecting Services w/Docker Containers

Continued from Docker Containers

It's generally a good idea to frontend node.js apps with nginx so that we can offload tasks like compression and delivery of static assets leaving the webapp can concentrate on more complex things.

Typical nginx request processing flow:

  • If the request is for static content deliver it directly
  • Otherwise ask the backend node process to handle the request and pipe the result back up to the client compressing it if needed.

In this example we will set up nginx as a Docker container that contains the static content and a network connection to the webapp running in its own container.

The nginx config is pretty simple:

The Important aspects of this are to define where the backend is (in this case it is a container named 'webapp') and which locations to deliver static content without bothering the webapp backend

docker-assets/nginx/nginx.conf

location / {  
  proxy_pass  http://webapp:3000;
  ....
}
...
location /images/ {  
    alias /var/app/current/client/images/;
}

location /dist/ {  
    alias /var/app/current/client/dist/;
}

location /digitopia/ {  
    alias /var/app/current/client/digitopia/;
}

The container is defined in its own Docker file

Dockerfile-nginx

# install packages
FROM ubuntu  
RUN apt-get update  
RUN apt-get install -y supervisor  
RUN apt-get install -y nginx

# set up supervisord
ADD docker-assets/nginx/supervisord.conf /etc/supervisor/conf.d/supervisord.conf

# set up nginx
ADD docker-assets/nginx/nginx.conf /etc/nginx/conf.d/container.conf

ADD client /var/app/current/client

# expose nginx port
EXPOSE 8080

WORKDIR "/var/app/current"

CMD ["/usr/bin/supervisord"]

Docker Compose

Docker allows for creating multiple containers using a single file to define where the container Dockerfiles are and how they are connected. In this case we define a network called frontend and put the webapp and nginx containers in the network.

docker-compose.yml

version: '2'  
services:  
  webapp:
    build: .
    ports:
      - "3000:3000"
    env_file:
      - ./localdev.env
    networks:
      - frontend

  nginx:
    restart: always
    build:
      context: .
      dockerfile: Dockerfile-nginx
    ports:
      - "8080:8080"
    networks:
      - frontend

networks:  
  frontend:

To spin up these containers:

docker-compose up -d  

That's it. Now you have the backend webapp and the frontend nginx containers running, connected and ready for requests:

curl $(docker-machine ip):8080  

To spin it all down:

docker-compose down  
docker-compose kill