How to Create a Dockerfile for a Spring Boot Application with PostgreSQL

by Starling Diaz

Introduction

Docker is an essential tool for modern software development, allowing developers to build, package, and deploy applications efficiently. In this guide, we will walk you through creating a Dockerized Spring Boot application with PostgreSQL as the database. We will cover:

✅ Setting up a Spring Boot backend
✅ Configuring PostgreSQL in Docker
✅ Writing a Dockerfile for containerization
✅ Optimizing images with multi-stage builds
✅ Setting up docker-compose for seamless integration
✅ Implementing CI/CD with GitHub Actions

By the end of this guide, you’ll have a fully containerized Spring Boot application ready for deployment. Let’s get started! 🚀


Step 1: Create a Spring Boot Backend

1.1 Generate a Spring Boot Project

Go to Spring Initializr and configure the project with:

  • Project: Maven
  • Spring Boot Version: 3.0+
  • Dependencies: Spring Web, Spring Data JPA, PostgreSQL Driver

Download the project and unzip it. Navigate to the project folder and open it in your preferred IDE.

1.2 Define application.properties

Modify src/main/resources/application.properties:

spring.datasource.url=jdbc:postgresql://localhost:5432/mydatabase
spring.datasource.username=postgres
spring.datasource.password=secret
spring.jpa.hibernate.ddl-auto=update
spring.jpa.show-sql=true

1.3 Create a Simple Entity and Repository

Create a new entity in src/main/java/com/example/demo/entity/User.java:

package com.example.demo.entity;

import jakarta.persistence.*;

@Entity
@Table(name = "users")
public class User {
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Long id;
    private String name;
    private String email;
}

Create a repository in src/main/java/com/example/demo/repository/UserRepository.java:

package com.example.demo.repository;

import com.example.demo.entity.User;
import org.springframework.data.jpa.repository.JpaRepository;

public interface UserRepository extends JpaRepository<User, Long> {
}

Create a controller in src/main/java/com/example/demo/controller/UserController.java:

package com.example.demo.controller;

import com.example.demo.entity.User;
import com.example.demo.repository.UserRepository;
import org.springframework.web.bind.annotation.*;

import java.util.List;

@RestController
@RequestMapping("/users")
public class UserController {
    private final UserRepository userRepository;

    public UserController(UserRepository userRepository) {
        this.userRepository = userRepository;
    }

    @GetMapping
    public List<User> getAllUsers() {
        return userRepository.findAll();
    }
}

Run the application:

mvn spring-boot:run

Step 2: Configure PostgreSQL in Docker

Create a docker-compose.yml file in the root of your project:


services:
  app:
    image: 'docker-spring-boot-postgres:latest'
    build:
      context: .
    container_name: app
    depends_on:
      - db
    environment:
      - SPRING_DATASOURCE_URL=jdbc:postgresql://db:5432/compose-postgres
      - SPRING_DATASOURCE_USERNAME=compose-postgres
      - SPRING_DATASOURCE_PASSWORD=compose-postgres
      - SPRING_JPA_HIBERNATE_DDL_AUTO=update
    ports:
      -  "8080:8080"

  db:
    image: 'postgres:13.1-alpine'
    container_name: db
    environment:
      - POSTGRES_USER=compose-postgres
      - POSTGRES_PASSWORD=compose-postgres

Start PostgreSQL using:

docker-compose up -d

Step 3: Create a Dockerfile for Spring Boot

Create a Dockerfile in the project root:

# Use an official Java runtime as a base image
FROM eclipse-temurin:17-jdk-alpine AS build
WORKDIR /app
COPY . .
RUN ./mvnw package -DskipTests

# Use a smaller runtime image for production
FROM eclipse-temurin:17-jre-alpine
WORKDIR /app
COPY --from=build /app/target/*.jar app.jar
EXPOSE 8080
ENTRYPOINT ["java", "-jar", "app.jar"]

Build and run the container:

docker build -t spring-boot-app .
docker run -d -p 8080:8080 --name spring-boot-container spring-boot-app

Step 4: Optimize with Multi-Stage Builds

Modify Dockerfile for a smaller production image:

# First stage: Build the application
FROM maven:3.8.6-openjdk-17 AS build
WORKDIR /app
COPY . .
RUN mvn clean package -DskipTests

# Second stage: Run the application
FROM eclipse-temurin:17-jre-alpine
WORKDIR /app
COPY --from=build /app/target/*.jar app.jar
EXPOSE 8080
ENTRYPOINT ["java", "-jar", "app.jar"]

Step 5: Set Up GitHub Actions for CI/CD

Create .github/workflows/ci-cd.yml:

name: Spring Boot CI/CD

on: [push]

jobs:
  build:
    runs-on: ubuntu-latest
    steps:
      - name: Checkout Code
        uses: actions/checkout@v3

      - name: Set up JDK
        uses: actions/setup-java@v3
        with:
          java-version: '17'
          distribution: 'temurin'

      - name: Build Application
        run: mvn clean package -DskipTests

      - name: Build Docker Image
        run: docker build -t my-spring-app .

      - name: Login to Docker Hub
        run: echo "${{ secrets.DOCKER_PASSWORD }}" | docker login -u "${{ secrets.DOCKER_USERNAME }}" --password-stdin

      - name: Tag and Push Docker Image
        run: |
          docker tag my-spring-app ${{ secrets.DOCKER_USERNAME }}/spring-app:latest
          docker push ${{ secrets.DOCKER_USERNAME }}/spring-app:latest

Conclusion

In this guide, we built a Spring Boot application, containerized it with Docker, configured PostgreSQL, optimized the image with multi-stage builds, and set up GitHub Actions for CI/CD. This ensures an efficient, scalable, and automated deployment workflow.

💡 Ready to take it further? Try deploying the container to AWS, Azure, or Google Cloud! 🚀

Social Media

LinkedIn: https://www.linkedin.com/in/starling-diaz-908225181/

GitHub: https://github.com/NSTLRD

Youtube: https://www.youtube.com/@Mentorly-e3b

Mentorly Academy: https://www.mentor-ly.com/

Related Posts

About Us

We are Mentorly, your space for learning and practicing with real industry projects that will allow you to develop problem-solving skills with the best practices. Offering mentorships and real-world challenges to push you and support you in your professional development.

This website uses cookies to improve your experience. We'll assume you're ok with this, but you can opt-out if you wish. Accept Read More