Azul Statement on the eMudhra Intermediate CA Certificates Compromise

Legacy Java Application Modernization: A Jakarta EE Migration Guide

Modernizing legacy applications in the cloud era has become an imperative for business success. With customer expectations constantly rising and digital transformation becoming critical for business survival, understanding how to approach legacy application modernization has never been more important.

For enterprise Java teams, modernization often starts with a specific task: moving Java EE applications to Jakarta EE. This guide covers the business case for modernization, followed by a javax to jakarta migration checklist and tools to handle the package renaming. It draws on our comprehensive legacy application modernization white paper, which you can download for free here. 

What Exactly is a Legacy Application?

Contrary to popular belief, a legacy application isn’t just old software. According to Gartner, it’s “an information system that may be based on outdated technologies, but is critical to day-to-day operations.” Interestingly, even relatively modern applications written in Java could be considered legacy if they are built on outdated frameworks like J2EE that are no longer supported.

The True Cost of Legacy Applications

Organizations often underestimate the hidden costs of maintaining legacy systems:

  1. Hardware Dependencies: Many legacy systems require specific, often expensive-to-maintain hardware
  2. Development Bottlenecks: Simple updates can take weeks or months
  3. Security Vulnerabilities: Outdated components pose significant security risks
  4. Talent Scarcity: Finding developers for older technologies becomes increasingly difficult
  5. Compliance Challenges: Meeting modern regulatory requirements becomes more complex.

The 7 Rs of Legacy Application Modernization

Based on complexity and business impact, organizations can choose from seven modernization approaches. Here’s a comprehensive comparison.

Strategy

Description

Effort Level

Business Impact

Best For

Retain/Encapsulate

Keeps existing system while exposing functions through modern interfaces

Low

Moderate

Stable systems that still deliver value but need modern integration points

Rehost

Moves application to new infrastructure with minimal changes

Low-Moderate

Moderate

Systems limited by current infrastructure or hardware

Replatform

Updates runtime and framework versions while maintaining core functionality

Moderate

Moderate-High

Applications running on outdated but similar platforms

Refactor

Optimizes internal code structure without changing external functionality

Moderate-High

Moderate-High

Systems with significant technical debt but solid core functionality

Rearchitect

Fundamentally alters code structure to enable cloud-native capabilities

High

High

Applications that need significant architectural improvements

Rebuild

Complete rewrite while preserving core functionality and business rules

Very High

Very High

Systems where modernization costs exceed rebuilding costs

Replace

Implementation of entirely new solution based on current requirements

Highest

Highest

Outdated systems that no longer meet business needs

A Framework for Successful Modernization

Success in legacy application modernization relies on three key pillars that must work in harmony to ensure effective transformation.

Culture

Organisational culture plays a pivotal role in modernization success. It’s essential to create an environment that accepts change while maintaining stability. Start by securing buy-in from all stakeholders, from C-level executives to end-users. Set clear expectations about the modernization journey, including potential challenges and benefits. Prepare your organization for changes in workflows, tools and processes. Remember that resistance to change is natural – address concerns proactively and maintain open communication channels throughout the modernization process.

Portfolio

A strategic approach to portfolio management is crucial for modernization success. Begin by conducting a thorough assessment of your application landscape. Prioritize applications based on business value, technical debt and modernization urgency. Consider your resource constraints carefully – both in terms of budget and expertise. Create a balanced modernization roadmap that combines quick wins to build momentum with longer-term strategic initiatives. Use metrics and KPIs to track progress and demonstrate value to stakeholders.

Technology

While technology choices are important, they should be driven by business needs rather than trends. Carefully evaluate modernization approaches based on your organization’s specific context. Consider both current requirements and future scalability needs. Don’t fall into the trap of blindly following technology trends – what works for one organization may not work for another. For instance, while microservices are popular, they might not be the best choice for every application. Instead, focus on selecting technologies that align with your team’s capabilities and your organisation’s long-term technology strategy.

Modernizing Java Enterprise Applications: The Jakarta EE Advantage

A significant portion of enterprise legacy applications are built on Java EE/J2EE platforms, making Jakarta EE a natural modernization path. Jakarta EE (formerly Java EE) represents the evolution of enterprise Java, offering a powerful framework for modernizing legacy applications while maintaining enterprise-grade reliability.

The Java EE to Jakarta EE Modernization Path

The transition from Java EE to Jakarta EE provides several modernization opportunities:

  1. Incremental Updates: Move from older Java EE versions (like J2EE) to Jakarta EE 10 in stages, allowing for controlled risk management
  2. Cloud-Native Capabilities: Take advantage of Jakarta EE’s cloud-native features without completely rewriting your applications
  3. Modern Standards: Access updated specifications for REST APIs (JAX-RS or Jakarta REST), persistence (JPA or Jakarta Persistence), and dependency injection (CDI)
  4. Microservices Support: Optionally break down monoliths using Jakarta EE’s microservices capabilities when it makes business sense.

When to Choose Jakarta EE for Modernization

Jakarta EE is valuable when:

  • You have existing Java EE applications that need updating
  • Your team has Java expertise
  • You need enterprise-grade reliability and security
  • You want to modernize without completely rebuilding
  • Your application requires strong standards compliance.

The Microservices Myth

While microservices are often touted as the ultimate modernization goal, this isn’t always the best approach. Jakarta EE supports both monolithic and microservices architectures effectively. Modern monolithic applications built with Jakarta EE can be just as cloud-native and maintainable as microservices, often with less complexity. The key is choosing an architecture that aligns with your business goals and organizational capabilities.

For example, you might:

  • Keep your core application as a Jakarta EE monolith for stability
  • Expose new features as Jakarta EE microservices where needed
  • Use Jakarta EE’s REST capabilities to create modern APIs
  • Leverage Jakarta EE’s cloud specifications for container deployment.

What Changes in a Java EE to Jakarta EE Migration? 

A Java EE to Jakarta EE migration is mostly a rename, from javax package names to jakarta ones. There are three main things to know: 

  • The rename depends on your target version: Jakarta EE 8 kept the same APIs as Java EE 8, so moving to it didn’t need any code changes. The rename arrived with Jakarta EE 9 in December 2020, and every release since uses jakarta. So if you’re aiming for Jakarta EE 10 or 11, your code has to switch too. 
  • The rename applies to libraries: Every library your app loads must be compatible with the new namespace. A JAR compiled against javax.servlet won’t run on a server that only provides jakarta.servlet. 
  • Not every javax package changes: Some packages are part of Java SE itself and remain under javax. That’s why a blind find-and-replace on javax breaks the build. 

The javax to jakarta namespace checklist 

Work through this list on one application first, then roll it out to the rest of your portfolio. 

  1. Pick your target version and JDK: Jakarta EE 10 needs Java SE 11 or higher, and Jakarta EE 11 needs Java SE 17 or higher (Azul Payara 7 runs on Java SE 21 or 25). Upgrade the JDK first, so you’re only debugging one change at a time. 
  1. Swap the API dependency: Replace javax:javaee-api 8.0 with jakarta.platform:jakarta.jakartaee-api 10.0.0 or 11.0.0. Don’t use version 8.0.0 of the new artifact, because it still contains the javax packages. 
  1. Rename the specification imports: javax.servlet, javax.persistence, javax.ws.rs, javax.ejb, javax.faces, javax.inject, javax.enterprise, javax.validation, javax.jms and javax.mail all become jakarta. So javax.persistence.Entity turns into jakarta.persistence.Entity. 
  1. Leave the Java SE packages alone: javax.sql, javax.naming, javax.crypto, javax.net.ssl and javax.transaction.xa ship with the JDK, so they keep their names. Watch javax.transaction, because the package moves, but its xa subpackage stays put. 
  1. Update your deployment descriptors: web.xml, ejb-jar.xml, beans.xml, and faces-config.xml move to the https://jakarta.ee/xml/ns/jakartaee namespace, and persistence.xml moves to https://jakarta.ee/xml/ns/persistence. Bump the schema version too, like web-app 6.1 for Jakarta EE 11. 
  1. Rename configuration properties: Jakarta Persistence 3.0 swapped javax for jakarta in every property name, so javax.persistence.jdbc.url becomes jakarta.persistence.jdbc.url. 
  1. Update JSP tag library URIs: Jakarta Tags 3.0 added short URIs like jakarta.tags.core in place of ones like http://java.sun.com/jsp/jstl/core, though it still accepts the old URIs. 
  1. Search strings and resource files: Reflection calls, hard-coded class names, and META-INF/services file names can all hold javax references your compiler won’t catch. 
  1. Upgrade third-party libraries: Move to jakarta-based releases like Hibernate ORM 6 or Spring Framework 6. Spring 6 also needs Java 17, so it’ll shape your JDK choice. 
  1. Watch for changed defaults: In Jakarta EE 10, an empty beans.xml means annotated discovery, so classes without a bean-defining annotation stop being picked up. 
  1. Check for removed APIs: Jakarta EE 11 dropped XML Binding and XML Web Services from the platform, so confirm your server still provides them. 
  1. Test on a certified runtime: Run your full regression suite on a server that’s certified for your target version. 

It also helps to change servers and migrate your code separately. Azul Payara Server is a Jakarta EE 11 certified application server.  

Our supported releases include version 5, which runs Java EE 8 on javax, and version 7 on jakarta. So you can move an app off GlassFish, WebLogic, or JBoss EAP while it’s still on javax, then switch namespaces when you’re ready. 

Tools that automate the javax to jakarta rename 

You don’t need to rename thousands of imports by hand, because these three tools do the mechanical part. 

1. Eclipse Transformer 

Eclipse Transformer is an Eclipse Foundation project that rewrites javax references to jakarta. It works on class files and JAR, WAR, and EAR archives, plus text files like XML descriptors, JSPs, and Java source. You give its command-line tool an input and an output path, and it writes a converted copy using built-in Jakarta rules. 

Since it converts compiled code, it’s the best fit for code you can’t recompile, like an old third-party library that never got a jakarta release. We’ve walked through converting a third-party library with Eclipse Transformer. 

On Azul Payara Server 6, a built-in Deployment Transformer converts Jakarta EE 8 apps to the Jakarta EE 10 namespace at deployment. We don’t guarantee it in future major releases, so treat it as a bridge. 

2. OpenRewrite 

OpenRewrite changes your source code directly. Its JavaxMigrationToJakarta, JakartaEE10, and JakartaEE11 recipes update imports, dependencies, and XML descriptors, and you run them through the Maven or Gradle plugin. Check the licensing first, though, because these recipes ship under the Moderne Source Available License. 

3. IntelliJ IDEA and the Tomcat migration tool 

IntelliJ IDEA has a Java EE to Jakarta EE migration map under Refactor, then Migrate Packages and Classes. It renames packages in your source, but you’ll still update dependencies and persistence.xml yourself. 

Apache’s Tomcat Migration Tool for Jakarta EE converts WAR files, folders, or single files from the command line. Add -profile=EE to convert every Java EE API, since the default only covers the APIs Tomcat itself provides.  

Practical Example: Modernizing a J2EE Application

Let’s look at a practical example of modernizing a J2EE application using different strategies:

  1. Retain/Encapsulate Approach:
    • Keep the core J2EE application running
    • Create Jakarta EE REST facades for new functionality
    • Gradually migrate components as needed
  2. Replatform Approach:
    • Upgrade from J2EE to Jakarta EE 11
    • Update deprecated APIs to their modern equivalents
    • Maintain existing architecture while gaining modern capabilities
  3. Rearchitect Approach:
    • Break down the monolith into Jakarta EE components
    • Implement cloud-native patterns
    • Use Jakarta EE’s microservices features where appropriate.

Getting Started 

Before starting on a modernization journey:

  1. Assess Current State: Evaluate your application portfolio comprehensively
  2. Define Clear Goals: Understand what you want to achieve beyond just “modernization”
  3. Start Small: Choose a pilot project with manageable scope
  4. Measure Success: Define KPIs to track progress and ROI
  5. Plan for Change: Prepare your team for new processes and technologies.

Conclusions

Legacy application modernization is not just about updating technology – it’s about transforming your business for the digital age. While the process can be complex, taking a structured approach focused on culture, portfolio and technology can help ensure success. The key is to start with a clear understanding of your goals and choose modernization strategies that align with your organization’s capabilities and resources.

Remember, modernization is a journey, not a destination. As technology continues to evolve, maintaining modern, adaptable applications will become increasingly crucial for business success.

Want to learn more about legacy application modernization? Download a copy of “A Business Guide to Legacy Application Modernization For The Cloud Era” and feel free to reach out to discuss your modernization challenges as well as opportunities.