Spring Boot Application Not Starting After Java Upgrade: Causes and Solutions

updated image

You upgrade your JDK — maybe from Java 8 to 17, or 11 to 21 — and suddenly your previously rock-solid Spring Boot application refuses to start. The frustrating part isn’t that it’s broken; it’s that the error messages are often vague, indirect, or buried inside a stack trace that points to a symptom rather than the real cause.

What this typically looks like:

  • The build fails outright, or builds successfully but the app crashes on startup
  • Errors like UnsupportedClassVersionErrorNoSuchMethodError, or IllegalAccessError
  • Sometimes no error at all — the app exits immediately after printing the banner
  • Code that worked fine yesterday now fails, with zero changes made

This is a classic “it’s not your code, it’s your environment” problem — and it’s extremely common after any Java LTS upgrade (8→11, 11→17, 17→21).

Common Reasons Spring Boot Fails After a Java Upgrade

1. Java Version Mismatch Between Build and Runtime

Your IDE compiles with Java 17, but your JAVA_HOME or terminal still points to Java 11 when you run the jar. This mismatch causes UnsupportedClassVersionError immediately on startup.

2. Spring Boot Version Incompatibility

Older Spring Boot versions (2.x, particularly before 2.5) have limited or no support for newer Java versions. Spring Boot 3.x requires Java 17 as a minimum. If you upgraded your JDK but you’re still on Spring Boot 2.7, you may hit subtle incompatibilities, especially in reflection-heavy libraries like Hibernate and Jackson.

3. Maven / Gradle Compiler Plugin Still Targeting the Old Version

Even after installing a new JDK, your build configuration might still explicitly target the old Java version — creating a mismatch between what gets compiled and what the runtime expects.

4. Deprecated or Removed JVM Options

JVM flags that worked fine in Java 8 — especially PermGen/Metaspace settings or certain --add-opens module flags — are either removed or behave differently in newer runtimes and can cause immediate startup failures.

How to Fix It — Step by Step

Step 1: Update Java Version in pom.xml

Open your pom.xml and check the <properties> block:

<properties>
    <java.version>17</java.version>
    <maven.compiler.source>17</maven.compiler.source>
    <maven.compiler.target>17</maven.compiler.target>
</properties>

If you have an explicit maven-compiler-plugin entry, update that too:

<plugin>
    <groupId>org.apache.maven.plugins</groupId>
    <artifactId>maven-compiler-plugin</artifactId>
    <configuration>
        <source>17</source>
        <target>17</target>
    </configuration>
</plugin>

For Gradle (build.gradle):

java {
    sourceCompatibility = JavaVersion.VERSION_17
    targetCompatibility = JavaVersion.VERSION_17
}

Step 2: Update the Spring Boot Parent Version

If you’ve moved to Java 17+, update your Spring Boot parent to 3.x:

<parent>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-parent</artifactId>
    <version>3.2.5</version>
    <relativePath/>
</parent>

⚠️ Important — javax to jakarta namespace migration: Spring Boot 3.x migrates from javax.* to jakarta.*. Every import using the old namespace must be updated:

// Before — Spring Boot 2.x (Java 8 / 11)
import javax.persistence.Entity;
import javax.validation.constraints.NotNull;

// After — Spring Boot 3.x (Java 17+)
import jakarta.persistence.Entity;
import jakarta.validation.constraints.NotNull;

This is the single biggest source of “it builds cleanly but throws weird errors at runtime” issues during a 2.x → 3.x migration.

Step 3: Verify Build and Runtime Are on the Same JDK

In your terminal, confirm what Java version is actually being used:

java -version
javac -version

And check JAVA_HOME:

# Linux / macOS
echo $JAVA_HOME

# Windows
echo %JAVA_HOME%

If your IDE shows Java 17 but the terminal resolves to Java 11, that mismatch alone will cause UnsupportedClassVersionError. Update JAVA_HOME to point to the new JDK, then restart your terminal and IDE for the change to take effect.

Step 4: Clear the Maven or Gradle Cache

Stale compiled classes and cached dependency metadata from the old Java version can produce confusing errors completely unrelated to your actual code. Always clear the cache after a major JDK change.

Maven:

rm -rf ~/.m2/repository
mvn clean install -U

The -U flag forces Maven to re-check for updated dependency versions instead of using cached snapshots.

Gradle:

./gradlew clean build --refresh-dependencies

This single step resolves a surprising number of “it just won’t start and the error makes no sense” situations after a JDK upgrade.

Prevention: Java & Spring Boot Compatibility Reference

Java VersionMinimum Spring Boot VersionNotes
Java 82.0 – 2.7.xSpring Boot 3.x dropped support entirely
Java 112.1+ (recommended 2.5+)Widely supported across the 2.x line
Java 173.0+ (required minimum)javax → jakarta namespace migration required
Java 213.2+Virtual threads support added in 3.2

Test Checklist Before Pushing a Java Upgrade to Production

  1. Run the full test suite locally with the new JDK — don’t just check if the app starts
  2. Build a fresh jar with mvn clean package (not an incremental build) and run it standalone, outside the IDE
  3. Check startup logs for WARN messages about deprecated APIs or reflection access — these often become hard failures in later versions
  4. If you’re also upgrading Spring Boot major versions (2.x → 3.x), do it as a separate step from the Java upgrade — debugging two major changes simultaneously is significantly harder

Conclusion

A Java upgrade that “breaks” Spring Boot is almost always one of three things: a build/runtime version mismatch, a Spring Boot version that hasn’t caught up to your new JDK, or a stale cache hiding the real error. Walk through pom.xml, confirm JAVA_HOME, and clear .m2 — in that order — and you’ll usually find the culprit before you’ve finished your coffee.

Leave a Comment

Your email address will not be published. Required fields are marked *