Hot reload your Java Spring Boot and Micronaut applications inside docker with debugging support via IntelliJIdea.
hot-reload-inside-docker.mp4
- Application built inside docker.
- Code changes are auto-compiled and updated without having to restart the app or container.
- Remote debugging using IntelliJIDEA.
- Make sure that you have Docker and Docker-Compose installed
- Windows or macOS: Install Docker Desktop
- Linux: Install Docker and then Docker Compose
Run the application first time by hitting run button in IDE. While application is running, make some
changes to the code in src
directory and save the changes. This time code changes
should be auto-compiled and updated without having to restart the application manually, and that is
what we call a Hot Reload.
Most of the frameworks support this feature locally. To have same behaviour inside
docker we have created Dockerfile
and docker-compose.yml
templates
for the java related technologies like SpringBoot and Micronaut. Additionally, you can debug the
application running inside docker through IntelliJIDEA. To know more about it
refer Remote Debugging Using IntellijIDEA.
Navigation Table
Framework | Database | Maven | Gradle |
---|---|---|---|
SpringBoot | postgres | ||
Micronaut | postgres |
Step-1: Click
on icon
based on framework and build tool used in project to navigate to specific docker files. Check
the README.md
per framework for the detailed steps.
Step-2: Now copy the Dockerfile
, docker-compose.yml
and .env
files from repository where
you have been navigated, to the working directory and make appropriate changes.
Step-3: Simply run:
cd <working-dir>
docker-compose up
- Volume Mapping
- Gradle / Maven Dependency Caching
The essential component is mounting current directory from local machine to app
(WORKDIR)
directory
inside Docker container. SpringBoot / Micronaut application by default comes with Maven / Gradle
Wrappers, this would allow us to run the application within Docker container.
Mounting current directory into Docker container helps to have source code and the build tool within Docker container, but the source code within Docker is dependent on many external libraries(dependencies) which are not present in current directory.
There are two ways to solve this issue:
- Mounting
.m2
/.gradle
from Docker Host to Docker container. - Caching all the dependencies while building the Docker image
Mounting root level directories is not an option to choose. But there are some other issue with
Gradle
caching, if you are mounting .gradle
and running the application with Gradle build tool within
Docker container, then docker acquires lock for gradle cache, that means we
can't run any application with Gradle build in local machine until Docker container is stopped.
Caching all the dependencies while building Docker image is a good option during development phase. Since we are downloading all the dependencies image size would be larger(depends on dependencies).
Table depicts the way to enable hot-reload / remote-debugging feature for the Java related technologies(SpringBoot / Micronaut) between the Maven and Gradle build tools.
Framework | Feature | Maven | Gradle |
---|---|---|---|
SpringBoot | hot-reload | Step-1: Add spring-boot-devtools dependency to pom.xml . Step-2: Run ./mvnw spring-boot:run inside working directory. |
Step-1: Add org.springframework.boot:spring-boot-devtools dependency to build.gradle . step-2: Run ./gradlew bootRun inside working directory. |
remote-debugging | Just run the command ./mvnw spring-boot:run -Dspring-boot.run.jvmArguments="-agentlib:jdwp=transport=dt_socket,server=y,suspend=n,address=*:8000" inside working directory. |
Step-1: Add task bootRun { jvmArgs=["-agentlib:jdwp=transport=dt_socket,server=y,suspend=n,address=*:8000"] } to build.gradle Step-2: Run ./gradlew bootRun inside working directory. |
|
Micronaut | hot-reload | Run ./mvnw mn:run -Dmn.watch=true inside working directory |
Run ./gradlew run -t inside working directory, Here -t enables continious build. |
remote-debugging | Just run the command ./mvnw mn:run -Dmn.debug -Dmn.debug.host=* -Dmn.debug.port=8000 inside working directory. |
Step-1: Add task run { jvmArgs=["-agentlib:jdwp=transport=dt_socket,server=y,suspend=n,address=*:8000"] } to build.gradle Step-2: Run ./gradlew run -t inside working directory. |
remote-debugging-intellij.mp4
Note: Check out Comparison between Framework, Feature and Build Tools for Hot-Reload and Remote-Debugging section if you are using different build tool or framework.