DEV Community

Michael Isijola
Michael Isijola

Posted on

CI/CD Pipeline for Secure Java Alert System with Docker & GitHub Actions

This setup defines a CI/CD pipeline and containerization strategy for the Critical Alert System, a Java-based backend application. It is composed of three key components: 1. Dockerfile
A multi-stage Docker build:
Stage 1 (Builder Stage):
Uses a Maven image (maven:3.9.5-eclipse-temurin-17) to build the project. It compiles the Java code and packages it into a JAR file using mvn clean package -DskipTests.
Stage 2 (Runtime Stage): Uses a lightweight JDK image (eclipse-temurin:17-jdk) to run the built JAR file. This reduces the final image size for deployment.

  1. .dockerignore Optimizes the Docker context by excluding unnecessary files and folders, such as: The entire target/ directory except the final JAR. Git-related files, IDE configs (.idea/), and project metadata (*.iml, README.md, etc.).
  2. .github/workflows/critical-alert-ci.yml This GitHub Actions workflow automates the CI/CD process: Triggers: On push or pull_request to the main branch. Environment Setup: Checks out the code. Sets up Java 17 using the temurin distribution. Builds and verifies the project using Maven. Docker Integration: Logs into GitHub Container Registry (GHCR) securely. Builds the Docker image. Pushes the image to GHCR. (Optional) Deployment: A placeholder for automated deployment on merges to main. Purpose & Benefits: Ensures consistent builds, security validation, and automated deployments. Promotes DevOps best practices: Immutable Docker builds, CI/CD automation, secure token handling, and streamlined container publishing.
Dockerfile



 # First stage: build the JAR

FROM maven:3.9.5-eclipse-temurin-17 AS builder

WORKDIR /app

COPY pom.xml .

COPY src ./src

RUN mvn clean package -DskipTests



# Second stage: run the app

FROM eclipse-temurin:17-jdk

WORKDIR /app

COPY --from=builder /app/target/critical-alert-system-*.jar app.jar

ENTRYPOINT ["java", "-jar", "app.jar"].      

-------------------------------------------------------

.dockerignore



 # Ignore everything in target except the final JAR

target/*

!target/critical-alert-system-*.jar



# General exclusions

.git/

.gitignore

README.md

Dockerfile

*.iml

.idea/.   



---------------------------------------------------------------------------

.github/workflows/critical-alert-ci.yml





 name: CI/CD - Critical Alert Systems



on:

  push:

    branches: [ "main" ]

  pull_request:

    branches: [ "main" ]



env:

  IMAGE_NAME: ghcr.io/${{ github.repository }}:latest



jobs:

  build-test-docker:

    runs-on: ubuntu-latest



    steps:

      - name: Checkout code

        uses: actions/checkout@v3



      - name: Set up Java 17

        uses: actions/setup-java@v3

        with:

          java-version: '17'

          distribution: 'temurin'



      - name: Build with Maven

        run: mvn clean verify



      - name: Log in to GHCR

        run: echo "${{ secrets.GHCR_PAT }}" | docker login ghcr.io -u ${{ github.actor }} --password-stdin





      - name: Set lowercase image name

        id: vars

        run: echo "IMAGE_NAME=ghcr.io/$(echo '${{ github.repository }}' | tr '[:upper:]' '[:lower:]'):latest" >> $GITHUB_ENV



      - name: Build Docker image

        run: docker build -t $IMAGE_NAME .



      - name: Push Docker image to GHCR

        run: docker push $IMAGE_NAME



      - name: Deploy (optional)

        if: github.ref == 'refs/heads/main'

        run: echo "Deploying to production"
Enter fullscreen mode Exit fullscreen mode

Top comments (132)

Collapse
 
steve_tennyson_d0492229c1 profile image
Steve Tennyson

Fantastic.....good information

Collapse
 
linabasugit profile image
LinabasuGit

Love the CI/CD pipeline setup for the Critical Alert System! The multi-stage Docker build is genius, keeping the final image lightweight and secure. The GitHub Actions workflow is well-structured, automating the build, verification, and deployment process. Great job implementing DevOps best practices.

Collapse
 
jingbang_pou_f6ae9545525e profile image
Jingbang Pou

I like how this setup balances simplicity with best practices—it’s not just about getting a JAR into a container, but doing it in a way that feels production-ready. The multi-stage build trims the fat, and pushing straight to GHCR keeps the flow tight. What stands out is how it quietly enforces discipline: no stray files, secure token usage, and a clear path to deployment without overcomplicating things.

Collapse
 
umar_abubakar_ba89bbffe50 profile image
Umar Abubakar

This setup implements a robust CI/CD pipeline and containerization strategy for the Critical Alert System, leveraging Docker and GitHub Actions to automate builds, testing, and deployment, while ensuring consistency, security, and efficiency in the development and deployment process.

Collapse
 
kimberly_jgablar_1c2c0a profile image
Kimberly J. Gablar

The CI/CD pipeline built for the Critical Alert System is truly commendable! The multi-stage Docker build keeps the final image lightweight and secure, which is a great strategy. Also, the GitHub Actions workflow is well-organized, where the entire process of build, testing, and deployment is automated. This is a great example of following DevOps best practices.

Collapse
 
mintmuse_er profile image
Metaversal Muse

Fantastic deep dive! Your post clearly illustrates how a Java-based Critical Alert System can benefit from a secure and streamlined CI/CD workflow using Docker and GitHub Actions. The multi-stage Docker build (using Maven for compilation and a slim JDK for runtime) is a great example of minimizing image size and attack surface. And automating build, test, and secure image push to GitHub Container Registry (GHCR) ensures consistent, immutable deployments.

Collapse
 
firstchae1 profile image
firstchae1102

Really insightful article! I like how you combined Docker and GitHub Actions to create a secure CI/CD pipeline for the Java Alert System. The explanation about the multi-stage Docker build and integration steps is very clear. Do you think this setup could also be adapted for microservices architecture with multiple Java-based services?

Collapse
 
emily_kelleher_cec7905a99 profile image
Emily Kelleher

This setup showcases a clean and efficient CI/CD and containerization strategy for a Java backend. The multi-stage Dockerfile optimizes image size, the .dockerignore improves build performance, and the GitHub Actions workflow ensures automated, secure builds and deployments. A solid example of modern DevOps best practices in action.

Collapse
 
steven_williams_b2bed18e4 profile image
Steven Williams

I find it excellent how this pipeline ensures the reliability of the system right out of the box. Thanks to the use of Docker with separate stages, I feel that the application remains lightweight and optimized for deployment. Also, the fact that GitHub Actions automates testing, compilation and publishing to the registry gives me peace of mind, because it eliminates manual errors and ensures that the latest stable and secure version of the project is always used.

Collapse
 
mian_awais_e59c511ce93e43 profile image
Mian Awais

Great write-up! The multi-stage Docker build is well thought out, and using Maven for the build stage with a lightweight JDK for runtime is an efficient choice. The inclusion of a .dockerignore and GitHub Actions workflow shows a solid understanding of DevOps best practices. It’s impressive how the pipeline ensures consistent builds and secure image publishing. Curious—do you plan to add automated tests or deployment steps to the CI/CD workflow in the future?

Some comments may only be visible to logged-in visitors. Sign in to view all comments.