DZone
Thanks for visiting DZone today,
Edit Profile
  • Manage Email Subscriptions
  • How to Post to DZone
  • Article Submission Guidelines
Sign Out View Profile
  • Post an Article
  • Manage My Drafts
Over 2 million developers have joined DZone.
Log In / Join
Refcards Trend Reports Events Over 2 million developers have joined DZone. Join Today! Thanks for visiting DZone today,
Edit Profile Manage Email Subscriptions Moderation Admin Console How to Post to DZone Article Submission Guidelines
View Profile
Sign Out
Refcards
Trend Reports
Events
Zones
Culture and Methodologies Agile Career Development Methodologies Team Management
Data Engineering AI/ML Big Data Data Databases IoT
Software Design and Architecture Cloud Architecture Containers Integration Microservices Performance Security
Coding Frameworks Java JavaScript Languages Tools
Testing, Deployment, and Maintenance Deployment DevOps and CI/CD Maintenance Monitoring and Observability Testing, Tools, and Frameworks
Partner Zones AWS Cloud
by AWS Developer Relations
Culture and Methodologies
Agile Career Development Methodologies Team Management
Data Engineering
AI/ML Big Data Data Databases IoT
Software Design and Architecture
Cloud Architecture Containers Integration Microservices Performance Security
Coding
Frameworks Java JavaScript Languages Tools
Testing, Deployment, and Maintenance
Deployment DevOps and CI/CD Maintenance Monitoring and Observability Testing, Tools, and Frameworks
Partner Zones
AWS Cloud
by AWS Developer Relations
11 Monitoring and Observability Tools for 2023
Learn more
  1. DZone
  2. Data Engineering
  3. Databases
  4. Create an API Builder Multi-Container Application Using Docker: Part 2

Create an API Builder Multi-Container Application Using Docker: Part 2

Use Docker Compose to easily stand up a multi-container application based on two API Builder microservices, a MongoDB database, and an Nginx based load balancer.

Leor Brenman user avatar by
Leor Brenman
·
May. 03, 19 · Tutorial
Like (2)
Save
Tweet
Share
16.66K Views

Join the DZone community and get the full member experience.

Join For Free

In Part 1 of this series, we discussed how to stand up a multi-container application using Docker, API Builder, and MongoDB.

In this post, we're going to add another API Builder instance to handle an increased load. We'll also add a load balancer based on nginx as described in this excellent post, Scaling Out With Docker and Nginx.

We'll do this using Docker Compose only and won't bother with any manual setup as we did in Part 1.

Here is a block diagram of our application:

Let's get started.

Prerequisites

You'll need Docker Compose installed on your machine. Refer to the online docs for installation instructions.

docker-compose.yaml

Since we covered a lot of the basics in Part 1, this post is mainly concerned with creating a docker-compose.yaml file.

My docker-container YAML is shown below:

version: '3.2'
services:
  apibmongodb1:
    image: lbrenman/apibmongodb:1.0.0
    container_name: "apibmongodb1"
    environment:
      - MONGO_URL=mongodb://admin:admin@mymongodb:27017/mydata?authSource=admin
    depends_on:
      - mymongodb

  apibmongodb2:
    image: lbrenman/apibmongodb:1.0.0
    container_name: "apibmongodb2"
    environment:
      - MONGO_URL=mongodb://admin:admin@mymongodb:27017/mydata?authSource=admin
    depends_on:
      - mymongodb

  loadbalancer:
      build: ./load-balancer
      tty: true
      links:
          - apibmongodb1
          - apibmongodb2
          - mymongodb
      ports:
          - '80:8080'

  mymongodb:
    image: mongo:latest
    container_name: "mymongodb"
    ports:
      - "27017:27017"
    volumes:
      - ~/mongodata:/data/db
    command: mongod --auth

Create a file called docker-container.yaml and paste the YAML above into it and save it.

Let's dissect the YAML as follows:

  • apibmongodb1 and apibmongodb2 are the two API Builder containers. This section is basically identical to what we saw in Part 1 except that we have two services instead of one. Both depend on mymongodb and both connect to the same MongoDB instance.
  • mymongodb is the MongoDB container and is the same as in Part 1
  • loadbalancer is new and has the following configuration options:
    • build tells Compose where to look for a Dockerfile to build the image for the service. In this example, the Dockerfile for the load balancer is in the /load-balancer subfolder
    • tty tells the container to keep running even when there's no daemon specified via CMD in the Dockerfile
    • links does two things: makes sure the loadbalancer service doesn't start unless the API Builder and MongoDB services have started. And it allows apibmongodb1 , apibmongodb2 and mymongodb to be used as references within loadbalancer, which we did in our nginx.conf (more on this shortly)
    • ports specifies a mapping between a host port and a container port. 8080 of the container will receive client requests made to localhost:80 on the host

The tricky part here is the Nginx load balancer. As we see in the YAML file above, there is a subfolder called /load-balancer that contains assets related to building the load balancer service (container).

Let's review this in the next section.

Nginx Load Balancer

In the /load-balancer subfolder, we have a Dockerfile that is used to build the loadbalancer service. This is implicitly referenced in the docker-compose.yaml above in the build configuration option. The /load-balancer subfolder also contains an Nginx configuration file, nginx.conf, which is referenced in the Dockerfile file below.

Dockerfile

The Dockerfile is shown below and is pretty simple. It basically creates an Nginx container and copies the configuration file, nginx.conf, which we'll discuss next.

# Use the standard Nginx image from Docker Hub
FROM nginx

# Copy custom configuration file from the current directory
COPY nginx.conf /etc/nginx/nginx.conf

EXPOSE 8080

# Start Nginx when the container has provisioned.
CMD ["nginx", "-g", "daemon off;"]

Create a subfolder called load-balancer, and in it, create a file called Dockerfile and paste the Dockerfile contents above into it and save it.

nginx.conf

The Nginx configuration file is shown below. It basically listens to requests on port 8080 and forwards to apibmongodb1 and apibmongodb2 (in a round robin fashion).

events { worker_connections 1024; }

http {

 upstream localhost {
    server apibmongodb1:8080;
    server apibmongodb2:8080;
 }

 server {
    listen 8080;
    server_name localhost;

    location / {
       proxy_pass http://localhost;
       proxy_set_header Host $host;
    }
  }
}

In the /load-balancer folder, create a file called nginx.conf and paste the above into it and save.

Run the Application

Now that we have our docker-compose.yaml and a subfolder called /load-balancer with our Nginx Dockerfile and configuration file, we can use docker-compose to run our app as follows:

  • Keep running ‘docker-compose up –build -d’ until you have two API Builder containers, a MongoDB Container and an NGINX (load balancer) up and running. Remember that we do this because the MongoDB service takes time before it can respond to incoming requests (from API Builder) and API Builder tries to connect to MongoDB at startup. Once all services are running, the ‘docker ps’ command should return something similar to this:

results of docker ps command

  • Then run ‘curl ‘http://localhost:80/api/mongo/dog” (or whatever is appropriate for the collection you have in your MongoDB database) to make an API call and see the results. Repeat.

Results of curl

  • Use the ‘docker logs ‘ command to see that each API Builder container received one API request each due to the round robin load balancing performed by our NGINX container
  • Use the ‘docker stop ‘ command to stop one of the API Builder services and see that even though there’s an initial brief pause (until the load balancer recognizes that one of the services is down), your API request still works
  • Use the ‘docker stop ‘ command to stop the other API Builder service and see that even though there’s an initial brief pause, your API request stops working
  • Use ‘docker container ls -a’ and get the container ID of one of the API Builder stopped containers and then use the ‘docker start ‘ command and then call your API to see that the API is working again
  • Optionally, bring up the other API Builder service as well
  • You can shut everything down using ‘docker-compose down’

Summary

In this blog post, we used Docker Compose to easily stand up a multi-container application based on two API Builder microservices, a MongoDB database and an Nginx based load balancer.

API Docker (software) application Load balancing (computing) microservice MongoDB

Published at DZone with permission of Leor Brenman, DZone MVB. See the original article here.

Opinions expressed by DZone contributors are their own.

Popular on DZone

  • Running Databases on Kubernetes
  • A Beginner's Guide to Infrastructure as Code
  • Real-Time Analytics for IoT
  • GitLab vs Jenkins: Which Is the Best CI/CD Tool?

Comments

Partner Resources

X

ABOUT US

  • About DZone
  • Send feedback
  • Careers
  • Sitemap

ADVERTISE

  • Advertise with DZone

CONTRIBUTE ON DZONE

  • Article Submission Guidelines
  • Become a Contributor
  • Visit the Writers' Zone

LEGAL

  • Terms of Service
  • Privacy Policy

CONTACT US

  • 600 Park Offices Drive
  • Suite 300
  • Durham, NC 27709
  • support@dzone.com
  • +1 (919) 678-0300

Let's be friends: