Free tool
Spring Boot migration risk analyzer: 2.x and 3.x to 4.x
Find out what breaks before you branch. Point it at a pom.xml or a Gradle build file and it scores the upgrade across Java version, the Jakarta namespace, Hibernate, Spring Security, dependencies, tests and deployment, then gives you a sprint-sized plan.
Your build file stays in your browser. The analyzer reads versions and migration signals locally. If you ask Taapti to review the result, we send only the redacted summary shown on screen, and you can remove any line before submitting.
Every 2.x and 3.x branch is now outside open-source support. Spring Boot 3.5 was the last to go, on 30 June 2026. Only 4.0 and 4.1 receive open-source patches, and 4.0 reaches open-source end of life on 31 December 2026.
What this checks, and how
The model is deterministic. The same input always produces the same score, and every point added has a sentence next to it explaining why. Ten categories are scored, each three ways, so unanswered questions widen the range instead of being quietly guessed.
Spring Boot version gap
2.7 to 4.1 is eight minor upgrades, each with its own breaking changes. 3.1 brings the Spring Security request-matcher ambiguity, 3.2 changes path matching, 3.3 ships Flyway 10 and its per-database module split.
Java version readiness
Java 8 to 17 usually costs more than the framework upgrade. The toolchain breaks first: Lombok, compiler plugins, JaCoCo, PowerMock and any bytecode agent.
javax to jakarta
Classified by longest matching prefix, so javax.transaction counts and javax.transaction.xa does not. JDK packages are reported separately so you can see they are not work.
Hibernate and JPA
Hibernate 6 changes the Maven coordinates, rewrites the type system, removes the legacy Criteria API, and changes id allocation in a way that collides with existing rows.
Spring Security
The context is no longer saved automatically, so a custom filter can log a user in and serve the next request as anonymous, with nothing in the logs.
Dependencies and plugins
Libraries with no Jakarta path at all are scored as replacements, not version bumps. Springfox is the common one: 3.0.0 from 2020 is the end of the line.
Application server
A WAR on WebLogic or traditional WebSphere is a procurement problem, not an engineering one, and it outweighs anything in the source tree.
Test safety net
Weighted heaviest of the ten. Every dangerous change here compiles cleanly and passes unit tests, so integration coverage predicts the outcome better than codebase size.
See a full example result
Spring Boot 2.7 on Java 8, packaged as a WAR for Tomcat 9, with Spring Security, JPA and Springfox 3.0.0 still on the classpath. Scored end to end by the same code the tool runs, so you can see the shape of the output before you paste anything of your own. +
An example, not your result. The input is a plausible composite rather than anyone's real project.
Format
Maven pom.xml
Spring Boot
2.7.18
Java
8
Packaging
war
Dependencies
4 read
Readiness grade
D
High risk. Expect surprises outside the source tree.
Risk score
65/100
Plausible range 50 to 82.
Rough size
14 to 22
Two-week sprints for one team. A planning band, not a quote.
Spring Boot 2.7 stopped receiving open-source security patches on 2023-06-30. New vulnerabilities in that branch are not fixed unless you hold a commercial agreement.
Risk by category
0 to 100, higher is worseThe bar is the score. The bracket under it is the range that score could still land in, so a wide bracket means the row was estimated, not measured.
Top blockers
Most severe first.
blockerDependencies
Springfox has no Jakarta path
No Jakarta build exists and none is coming. Version 3.0.0 from 2020 is the end of the line. Replacing it with springdoc-openapi changes every Docket bean, every @Api annotation, and the swagger-ui path.
blockerDeployment
Tomcat 9 or earlier cannot run the target version
Tomcat 9 is Java EE 8. Spring Boot 3 needs Tomcat 10.1 or later, which is the Jakarta namespace switch at the container level.
blockerJava
Java 8 has to go first
Spring Boot 3 and 4 both require Java 17 as a minimum. The JDK upgrade is a prerequisite and usually costs more than the framework upgrade.
highSpring Boot version gap
Spring Boot version gap
Spring Boot 2.7 to 4.1 is 8 minor upgrades, and each one carries its own breaking changes.
mediumHibernate and JPA
Hibernate and JPA
Hibernate 5 to 6 changes the Maven coordinates as well as the version: org.hibernate becomes org.hibernate.orm.
Suggested sequence
In order. Nothing below starts until the phase above it has shipped.
1. Prove the ground
Remove the unknowns that change the plan before anyone writes migration code.
- Resolve the blockers listed above first. Each one can invalidate the rest of the plan.
- Confirm the exact deployment target and its Jakarta EE level. For a WAR this decides whether the upgrade is an engineering task or a procurement one.
- Run the build on the target JDK with no other changes and record what breaks in the toolchain.
- Inventory internal shared libraries and find out who owns each one and whether its build still works.
- Write enough integration coverage on authentication, one write path and one paginated read to catch the silent failures later.
2. JDK upgrade
Move from Java 8 to 17 or later on the current Spring Boot version, and ship it.
- Upgrade the build plugins, Lombok, JaCoCo and any bytecode agents first. They break before the application does.
- Remove or replace PowerMock and anything else built on old cglib or ASM.
- Deploy this on its own. Shipping the JDK change separately from the framework change is what makes a rollback meaningful.
3. Namespace and framework
Cross to Spring Boot 3.0 on the Jakarta namespace.
- Run the OpenRewrite Spring Boot 3 recipes for the mechanical rename, then handle what they cannot: string-typed javax names in persistence.xml, web.xml, XML namespace URIs, taglib URIs and META-INF/services.
- Replace anything with no Jakarta path rather than trying to upgrade it.
- Rewrite security configuration to SecurityFilterChain beans and check the SecurityContext is saved explicitly in any custom filter.
- Work through the Hibernate 6 type system, identifier generation and HQL changes against a copy of production data.
4. Walk the 3.x line
Move up through the 3.x minors to 3.5.
- This is not free. 3.1 brings the Spring Security 6.1 request-matcher ambiguity, 3.2 changes path matching, 3.3 ships Flyway 10 and its per-database module split.
- Take one minor at a time and run the integration suite between each.
5. Spring Boot 4
Land on 4.1, which is the current supported branch.
- The cost here is Jackson 2 to Jackson 3 across every custom serializer, mixin and module, plus Spring Security 6 to 7.
- Jakarta EE 11 API levels need Tomcat 11 or later, or Jetty 12.1 or later.
- The Spring Boot module split means some imports move between finer-grained jars.
6. Cutover
Get it into production without discovering the silent failures from user reports.
- Use a canary or a staged rollout. The failures in this upgrade appear under real traffic, not in a smoke test.
- Watch authentication success rate, 403 rates on internal dispatches, and identifier collisions on any table with a Hibernate-generated id.
- Remember-me cookies are invalidated by the hashing change, so expect a login spike at cutover.
Your own build file will score differently. Run it against the analyzer above and you get this same breakdown for your codebase, parsed in your browser with nothing uploaded.
Run it on your build fileWhere the version facts come from
Support dates come from the Spring Boot generations API and the official migration guides on the Spring Boot GitHub wiki. The Jakarta rename lists are cross-checked against the Eclipse Transformer rename table and the Java SE API package index, which is what makes the JDK exclusions above reliable. Where a widely-repeated claim conflicts with the primary source, the primary source wins: Spring Boot 4 requires Java 17, not Java 21, whatever the blog posts say.
Once you have decided to go ahead, the mechanical part of the rename is a solved problem. Use the OpenRewrite Spring Boot recipes or Spring Boot Migrator for that. This analyzer covers the step before it, which is deciding whether to start and what to budget.
Frequently asked questions
Does my build file get uploaded anywhere? +
No. The analyzer parses it in your browser with JavaScript. There is no upload, no request to a server, and no copy kept. You can disconnect from the network after the page loads and the scan still works. If you later ask Taapti to review the result, you see the exact text before it is sent and you can delete any line from it first.
Which Spring Boot version should I be migrating to in 2026? +
Spring Boot 4.1 for most teams. Every 2.x and 3.x branch is now outside open-source support: 3.5 was the last to go, on 30 June 2026, and only 4.0 and 4.1 receive open-source patches today. Spring Boot 4.0 itself reaches open-source end of life on 31 December 2026, so aiming at 4.0 puts you back in the same position within months. Spring Boot 3.5 is a defensible staging point if you hold a commercial support agreement, because that runs to June 2032.
Does Spring Boot 4 require Java 21? +
No, and this is worth getting right because several widely-read blog posts say otherwise. The official Spring Boot 4.0 migration guide states Java 17 or later, with the latest LTS encouraged. Spring Boot 4 has first-class Java 25 support while retaining Java 17 compatibility. If you are already on Java 17 the JDK is not a blocker for you.
How is this different from OpenRewrite or Spring Boot Migrator? +
They rewrite code. This estimates risk before you decide to run them. OpenRewrite recipes and Spring Boot Migrator are the right tools once you have committed, and the analyzer tells you to use them. What neither answers is whether to start now, what will break that no recipe can fix, and how many sprints to budget. That question usually gets asked one step earlier, by someone deciding where the quarter goes.
Why does the estimate show a range instead of a number? +
Because the honest answer is a range. Each category is scored three ways: optimistic, likely and pessimistic. Answering "not sure" keeps all three apart, so the band stays wide and the row comes back estimated rather than measured. Running the browser-local scan on a real build file collapses several categories to a measurement and narrows the band. A tool that returns one confident number off five dropdowns is guessing.
Is counting javax imports a good measure of Jakarta migration size? +
On its own, no, and it is the most common way these estimates go wrong. A large share of javax packages never moved: javax.sql, javax.crypto, javax.naming, javax.net.ssl, javax.management, javax.xml.parsers and the JAAS half of javax.security.auth are all still in the JDK. Two are carved out of a parent that went the other way: javax.transaction relocated but javax.transaction.xa did not, and javax.security.auth.message relocated but the rest of javax.security.auth did not. This analyzer classifies by longest matching prefix and reports the JDK hits separately so you can see they are not work.
What will this analyzer miss? +
A build file cannot see your source tree, so it misses javax references in Java and Kotlin imports, and it misses the string-typed half of the problem entirely: fully-qualified javax names in persistence.xml, web.xml, XML namespace URIs, JSP taglib URIs, SPI files under META-INF/services and reflection by name. Those fail at boot rather than at compile. It also cannot see internal shared libraries, which are usually the hidden critical path.