DEV Community

Cover image for Deploy Simple Java Application using Docker Compose.
divine kenechukwu
divine kenechukwu

Posted on • Edited on

Deploy Simple Java Application using Docker Compose.

Goal
The goal of this project is to create Docker Compose Stack to deploy a simple Java application running in Containers 3-Tier Architecture.

Pre-Requisites

  1. Create AWS EC2 (Amazon Linux) Instance in Public Subnet with any desired Instance Type
  2. Allow Port 80 in Security Group
  3. Apache Maven Build Artifact (.war)
  4. Install docker and run docker service
  5. Install docker-compose
  6. Application Source Code Java

Step 1: Set Up the Environment:

1. Create an Amazon Linux EC2 Instance:

  • Launch an EC2 instance in a public subnet.
  • Choose any instance type, such as t2.micro for testing.
  • Allow port 80 (HTTP) in the security group.

2. Install Docker and Docker Compose on the EC2 Instance:

- Docker:

sudo yum update -y

sudo yum install -y docker

sudo service docker start

sudo usermod -a -G docker ec2-user
Enter fullscreen mode Exit fullscreen mode

- docker-compose:

sudo curl -L https://github.com/docker/compose/releases/latest/download/docker-compose-$(uname -s)-$(uname -m) -o /usr/local/bin/docker-compose

sudo chmod +x /usr/local/bin/docker-compose

docker-compose version
Enter fullscreen mode Exit fullscreen mode

3. Install Java and Apache Maven (for building the Java application):

curl -LO https://corretto.aws/downloads/latest/amazon-corretto-11-x64-linux-jdk.tar.gz

sudo tar -xvzf amazon-corretto-11-x64-linux-jdk.tar.gz -C /usr/java/

cd /usr/java/amazon-corretto-*-linux-x64/bin

for i in java javac jfr; do path=$(find `pwd`/$i -type f); echo $path; sudo alternatives --install /usr/bin/$i $i $path 20000 ; sudo update-alternatives --config $i ; done

java -version
Enter fullscreen mode Exit fullscreen mode

Step 2: Clone the Java Source Code:

  • To deploy this application, clone the source code into the Amazon Linux instance created using git clone command.
git clone https://github.com/Divine4212/java-login-app
Enter fullscreen mode Exit fullscreen mode

Step 3: Write Dockerfiles:
Dockerfiles are the blueprints for creating Docker images. In a Docker Compose project, they define the environment for each service. Docker Compose uses these Dockerfiles to build the images and then run them as containers.

- Dockerfile-sql:
The Dockerfile-sql will create custom MySQL container image by taking docker.io/mysql:8.0 as reference image from Docker Hub registry.

FROM mysql:8.0

ENV MYSQL_ROOT_PASSWORD=rootpassword
ENV MYSQL_DATABASE=UserDB
ENV MYSQL_USER=admin
ENV MYSQL_PASSWORD=Admin123

COPY init.sql /docker-entrypoint-initdb.d/
Enter fullscreen mode Exit fullscreen mode

- init.sql:

init.sql:
CREATE TABLE Employee (
  id int unsigned auto_increment not null,
  first_name varchar(250),
  last_name varchar(250),
  email varchar(250),
  username varchar(250),
  password varchar(250),
  regdate timestamp,
  primary key (id)
);
Enter fullscreen mode Exit fullscreen mode

- Dockerfile-app:
The Dockerfile-app is a simplified and optimized version for your Java Login App that takes docker.io/openjdk:11-jre-slim as base image from Docker Hub registry.. It installs unzip, vim, telnet and mysql-client and copy .war artifact to /app.war and start the application.

# Use OpenJDK 11 as the base image
FROM openjdk:11-jre-slim

# Install necessary packages (unzip, vim, telnet, mysql-client)
RUN apt-get update && \
    apt-get install -y unzip vim telnet mysql-client && \
    rm -rf /var/lib/apt/lists/*

# Set volume for temporary files
VOLUME /tmp

# Copy the WAR file to the container
COPY target/dptweb-1.0.war /app.war

# Expose the port Tomcat will run on
EXPOSE 8080

# Run the application using the JAR command
ENTRYPOINT ["java", "-jar", "/app.war"]
Enter fullscreen mode Exit fullscreen mode

- Dockerfile-nginx:
The Dockerfile creates a custom Nginx container image by taking docker.io/amazonlinux as reference image from Docker Hub registry. Will installs Nginx server, telnet and also copy the custom nginx.conf file with proxy_pass rule to forward the traffic to the app container.

FROM amazonlinux:2

RUN yum update -y && \
    amazon-linux-extras install nginx1 -y && \
    yum install -y telnet

COPY nginx.conf /etc/nginx/nginx.conf

EXPOSE 80
CMD ["nginx", "-g", "daemon off;"]
Enter fullscreen mode Exit fullscreen mode

- nginx.conf:

events {
    worker_connections 1024;
}

http {
    upstream app {
        server app:8080;
    }

    server {
        listen 80;
        location / {
            proxy_pass http://app;
            proxy_set_header Host $host;
            proxy_set_header X-Real-IP $remote_addr;
        }
    }
}
Enter fullscreen mode Exit fullscreen mode

Step 4: Write the Docker Compose File (docker-compose.yml):

- docker-compose.yml:
Docker Compose Stack Builds and Runs the Nginx, MySQL, App containers.

services:
  db:
    build:
      context: .
      dockerfile: Dockerfile-mysql
    environment:
      MYSQL_ROOT_PASSWORD: rootpassword
      MYSQL_DATABASE: UserDB
      MYSQL_USER: admin
      MYSQL_PASSWORD: Admin123
    networks:
      - app-network

  app:
    build:
      context: .
      dockerfile: Dockerfile-app
    depends_on:
      - db
    networks:
      - app-network
    ports:
      - "8080:8080"  # Expose port 8080

  nginx:
    build:
      context: .
      dockerfile: Dockerfile-nginx
    ports:
      - "80:80"
    depends_on:
      - app
    networks:
      - app-network

networks:
  app-network:
    driver: bridge
Enter fullscreen mode Exit fullscreen mode

After creating these files in your cloned application folder, run mvn clean package command to build your application with Maven, run docker-compose build command to verify if container images are getting created and the run Run docker-compose up -d command to verify if all containers are running.

Validation

  • Login to Nginx container shell and check App port is reachable.
docker exec -it 'container-id-nginx' /bin/sh

curl http://app:8080
Enter fullscreen mode Exit fullscreen mode
  • Login to App container shell and check MySQL port is reachable.
docker exec -it 'container-id-app' /bin/sh

telnet db 3306
Enter fullscreen mode Exit fullscreen mode

or

docker exec -it 'container-id-app' /bin/sh

mysql -h db -u admin -p
Enter fullscreen mode Exit fullscreen mode
  • Browse the application from public internet browser to verify the application is accessible.

Conclusion

Once the project setup has been completed, do not forget to clean up resources to avoid the billing for your test environment. Run docker-compose down command to stop and remove the containers and finally, terminate the instance from AWS Console.

Top comments (0)