Matt Lewis
Posted on July 9, 2024
Introduction
An exciting feature of Amazon Q
is the concept of agents that autonomously perform a complex, multistep task from a single prompt. One of these agents is the "Developer Agent for Code Transformation" which automates the process of upgrading and transforming Java applications from Java 8
or Java 11
to Java 17
, with more language support on the way.
I have previously demonstrated this capability using a simple Java 8
example. However, when I stumbled upon an old Java 11
Spring Boot application with thousands of lines of code, the build failed to compile on Java 17
with various upgrade issues, and it meant a time-consuming process to manually step through all of the problems.
Now, a few months on, I wanted to see whether any step change improvements had been made to the agent, so dug out the old codebase.
Setting up the Java 11 Bicycle Licence Application
In March 2020, I presented at an online AWS Tech Talk on new features of Amazon QLDB
. To bring this to life, we built a quick demo using Java 11 and Spring Boot. You can find the code repository on GitHub here. The repository does require a QLDB Ledger and table to be set up in the eu-west-2
region, with more details provided in associated README.md
file.
First create a new QLDB ledger in the eu-west-2
region:
And once created, open up the PartiQL editor
and run a command to create a new table:
Then we create a new directory by cloning the repository using the following command:
git clone https://github.com/mlewis7127/bicycle-licence-ui-master.git
We will use the JetBrains Intellij IDEA for this transformation, and choose to open a new project and select the folder created in the previous step.
If a pop-up appears, enable annotation processing for Lombok. Make sure to set the project to use version 11 of the Java SDK
. I am using Amazon Corretto
for my distribution of the Open Java Development Kit (OpenJDK).
This is set for the project by selected File --> Project Structure
, and select Project
under Project Settings
. Clicking on the SDK dropdown box, allows you to select Download SDK
where you can specify the version and vendor of the JDK to download.
From here, run a Maven clean
and then a Maven compile
. In the screenshot below I am doing this from the Maven plugin, or you can run from the command line. This will compile all of the code successfully as shown below.
Now launch the application by running the BicycleLicenceApplication
class in a new configuration.
This will start the application, which can be accessed in a browser window on http://localhost:8080/
. I have put together a short video below showing the application running as a Java 11
application.
Using Amazon Q to automatically upgrade to Java 17
Now we have the application successfully running using Java 11
, we want to upgrade to Java 17
. We tell Amazon Q
that we want to use the Code Transformation agent by opening a chat window and typing /transform
and selecting the agent.
This launches the Developer Agent for Code Transformation
. The bicycle-licence-ui
module is automatically selected, and we press confirm to let the agent know we want to upgrade to Java 17
.
Once we select transform, the agent takes over. It starts by building the Java module. Then it uploads the project artefacts that it has just built. Once these files have been uploaded, the code transformation job has been accepted, and the agent begins building the code in a secure build environment. Once built, Amazon Q
begins analysing the code in order to generate a transformation plan.
Once created, you can see a summary of the transformation plan. In this case, we have an application with almost 2500 lines of code, in which we need to replace 2 dependencies, with changes made to 5 files.
A summary is also provided of the planned transformation changes.
The transformation plan generated follows a 3 step process:
- Update JDK version, dependencies and related code
- Upgrade deprecated code
- Finalise code changes and generate transformation summary
This is where the massive improvements in code transformation shone. A few months ago, when the build of the application to Java 17
failed, the automated process abruptly ended. Now, the agent takes the compilation errors, and looks to make changes to fix the errors, before attempting to build the code again. You can see below it took several attempts, making changes each time, before the code could successfully build on Java 17
. The key point is this was all automated, with no manual input required.
After just 16 minutes, the code transformation was complete and had succeeded.
Amazon Q
lets us know about the planned dependency that it updated, with the other identified dependency having been removed.
As well as a number of additional dependencies that were updated during the upgrade
A pop up box allows you to see which files have been changed, and you can select each file individually and run a side by sided comparison to evaluate the changes.
As an example, I can see that all all references to javax.servlet.http.HttpServletRequest
have been replaced by jakarta.servlet.http.HttpServletRequest
as Spring Boot 3.0
has migrated from Java EE
to Jakarta EE
APIs for all dependencies. The agent had also implemented a new interface that was present in the latest Spring Framework version, that had not previously existed.
After this, we accept the automated updates, and run a Maven clean
and a Maven compile
before making sure we click on the top left button in the screenshot to reload the latest version of the dependencies:
We can launch and test the application which is now running on Java 17
.
Final Observations
There has been a massive improvement in the capability of the “Developer Agent for Code Transformation” over the past few months. If you had tried and discounted the agent, you should definitely look to give it another go. As the underlying models improve, I think we will see further step change improvements happen in very short timescales on an ongoing basis.
Two areas to call out for me are:
Unit Testing
In the video above, the call to verify the digest failed with a java.lang.NoSuchFieldError
in the logs. This is an example where despite having no compilation errors, we can still experience runtime errors. I have updated the GitHub repository with some unit tests as an example, which demonstrates how Amazon Q executes these tests as part of the code transformation.
We were able to fix the error by correcting a version mismatch between AWS SDK modules. This may not be found by unit tests, unless we were able to interact directly with AWS endpoints as part of these tests, and this is something being worked on. Nevertheless, ensuring there are sufficient unit tests to provide coverage of the core functionality will help to reduce examples of code compiling correctly but failing at runtime.
AWS SDK Upgrades
Although a number of libraries and frameworks were upgraded such as Spring and Log4j, the AWS SDK itself remained on Java 1.x. A big reason for this is the upgrade to AWS SDK for Java 2.x is a major rewrite that will typically require custom development to make work.
Watch the video below to see the agent in action and the steps it takes as described throughout this post
Posted on July 9, 2024
Join Our Newsletter. No Spam, Only the good stuff.
Sign up to receive the latest update from our blog.