Spring Framework Tutorial
Running, Packaging and Troubleshooting Spring Applications
Writing the code is half the job. You also need to run the application in different ways, change its port and settings, package it into a single executable jar, and diagnose the errors that every beginner meets. This lesson covers all four, and it ends with a troubleshooting table of the most common startup problems and their fixes.
Three ways to run a Spring Boot application
Use the one that suits the moment.
- From the IDE - run the main class. Best for debugging with breakpoints.
- With the build tool -
./mvnw spring-boot:run(Maven) or./gradlew bootRun(Gradle). Best for quick runs from the terminal. - As a jar -
java -jar target/app.jar. This is how applications run in production and in Docker.
Packaging an executable jar
Running ./mvnw package compiles the code, runs the tests, and produces target/hello-0.0.1-SNAPSHOT.jar. This is a "fat jar" (also called an uber jar): it contains your classes, every dependency, and the embedded Tomcat, so it runs anywhere a JDK exists. The jar for our small web and actuator project was about 21 MB. Add -DskipTests to skip tests while experimenting, but never in your real pipeline.
Changing the port and other settings
Spring Boot reads configuration from many places, and the later sources win. The most common are: application.properties in src/main/resources, environment variables, and command-line arguments. To change the port you can do any of the following: write server.port=9090 in application.properties, set the environment variable SERVER_PORT=9090, or add --server.port=9090 after the jar name. The command-line value overrides the file. The full configuration model is covered in the Spring Boot course.
Reading errors: start at the bottom, find "Caused by"
Java stack traces are long, and beginners panic. Ignore the wall of text and look at the last "Caused by:" line. That is the root cause, and the lines above it are only the chain of callers. Boot also prints a friendly "APPLICATION FAILED TO START" box with a Description and an Action for the most common failures, such as a port already in use. Read the Action line first.
Common problems and fixes
These are the errors you are most likely to meet in your first weeks. Each one has a specific cause, so read the message rather than guessing.
- The JAVA_HOME environment variable is not defined correctly - JAVA_HOME points to the wrong folder. Point it at the JDK root (the folder containing bin), open a new terminal and retry.
- release version 21 not supported (or similar) - the pom asks for a newer Java than your JDK. Install that JDK, or lower java.version to a release you have.
- Web server failed to start. Port 8080 was already in use - another process owns the port. Stop it, or run this application on another port.
- No qualifying bean of type ... - Spring cannot find a bean to inject. The class is missing an annotation, or it sits outside the scanned packages.
- Failed to determine a suitable driver class / Failed to configure a DataSource - you added a JPA or JDBC starter but no database driver or URL. Add H2 or configure your database.
- package javax.servlet does not exist - old code. Current Spring uses jakarta.servlet; update the imports.
- 404 on every request - the controller is not being scanned, or the path in the URL does not match the mapping.
- mvn is not recognized - Maven is not installed or not on PATH. Use the wrapper (mvnw) instead.
Finding and freeing a busy port
When port 8080 is busy, find the process that owns it and stop it, or choose another port. On Windows run netstat -ano | findstr :8080 to see the process ID, then taskkill /PID <pid> /F. On macOS and Linux run lsof -i :8080 and then kill <pid>. Often the culprit is a previous run of your own application that is still open in another terminal or IDE tab.
Examples
Build, run with a different port, and stop
./mvnw -DskipTests package
java -jar target/hello-0.0.1-SNAPSHOT.jar --server.port=9090
# in another terminal
curl http://localhost:9090/hello
Hello, World!
What a missing JAVA_HOME looks like (from a real failed run)
./mvnw package
The JAVA_HOME environment variable is not defined correctly,
this environment variable is needed to run this program.
Set the port in application.properties
# src/main/resources/application.properties
spring.application.name=hello
server.port=9090
Common Mistakes
- Reading the first error line only. The root cause is at the end, after the last "Caused by".
- Fixing one error by deleting the .m2 cache or reinstalling the IDE instead of reading the message.
- Running java -jar on the small original jar. Boot produces the executable jar as the main artifact; use the file that contains BOOT-INF.
- Hard-coding secrets such as database passwords in application.properties and committing them to Git.
- Skipping tests in the real build to make errors disappear.
Key Points to Remember
- Run from the IDE while debugging, with spring-boot:run for quick starts, and as a jar in production.
- mvnw package builds a self-contained executable jar with an embedded server.
- Change settings with application.properties, environment variables or command-line arguments; the command line wins.
- Diagnose failures from the last Caused by line and the Action text in the failure box.
Practice the examples
Change an input, predict the result, then compare it with the output. Explain why the result changes.
Use your local JDK or project IDE for these examples. Codelab currently runs Python and HTML/CSS/JavaScript; framework examples may need project dependencies.