Java 8 has been around for what seems like forever! More than 9 years after its release in 2014, it’s still the most widely used version. Why is that? Java 8 provided lots of new language features that gave Java developers a good reason to upgrade. These features included functional programming, lambda expressions, streams, and extensive API extensions. Not to mention changes to the JVM with the removal of the permanent generation and performance improvements to the G1 garbage collector. It was the Java version to use!
The vast majority of our clients still use it. Absolutely nothing wrong with that. It’s a long term support (LTS) release and will be supported till the middle of 2026. As of this writing the latest update of Java 8 is update 382, so it’s still going strong.
A Word On Versions
As we all probably know by now, there has been a six-monthly formal Java version release cycle. This started from Java 9. Every March and September, a new version of Java has been released. Obviously no-one can put a new release into production every 6 months, because that wouldn’t leave much time for new development work.
In the beginning, every third release was going to be a long term support (LTS) release, with the others being mainly short term support (STS) releases. STS means that as the next version is released, support and development on the previous version will stop, and the old version will reach its end of life (EOL).
However, not every third release has become an LTS release. Java 8 is an LTS version, as is Java 11. According to the original statements, Java 14 should have been, but isn’t. Java 17 is the latest LTS, and so far, has the longest EOL, being sometime in 2030.
Over the years, Java has introduced a number of new features in a phased manner. These features improve multiple aspects such as performance, productivity, and ease of use. Each version is essentially a stepping stone to the next release. New language features and enhancements are first previewed, possibly a few times, before becoming a final, accepted feature.
Very often you’ll see an article saying a new feature was introduced in Java 11 or Java 17, whereas in reality it was released in an earlier version. Don’t worry too much about the exact version when a feature was released. All the features essentially roll up to either Java 11 or Java 17. For example, most articles say that modularization (Project Jigsaw) was introduced in Java 11, while it actually appeared in Java 9. But because no-one should actually be using Java 9 or Java 10 for any development, the feature release is said to be in Java 11.
As already mentioned, Java 8 EOL date is May 2026. Java 11 EOL date is October 2024. Java 17 was released in October 2021, and its EOL date is 2030. So you’re better off using Java 8 or 17 than 11.
See https://javaalmanac.io/jdk/ for release and EOL dates.
When and Why Should You Upgrade?
I’m a big proponent of not upgrading to the latest and greatest version of any piece of software the moment it’s released. Yes, there’s something to be said about being on the leading edge of technology, but from bitter experience, many times it’s been more like the bleeding edge of technology.
Upgrading any application to take advantage of the latest technology is costly and time-consuming, and fraught with many pitfalls. The game must be worth the candle, otherwise why do it?
Is it a good time to move on from Java 8? What’s in Java 17? What does it bring to the party when compared to Java 8?
Let’s look at some of the advantages of upgrading from Java 8 to Java 17 (if you haven’t taken part of the plunge already by upgrading to Java 11).
Advantages to upgrading include:
- Language enhancements.
- Framework integration and support.
- Enhanced performance.
- Improved security.
Language Enhancements
There are a number of language enhancements when you look at Java 17 from a Java 8 viewpoint. Some are small, some are large, some you may never use, some might become indispensable in your project. None have to be used right away. Some might make you wonder how you ever coded in Java without them.
I’ll just mention most of them here without going into too much detail. The details will come in later posts (or even in previous posts).
-
The module system was introduced for ease of maintenance and scalability. Developers can use it to create and maintain class libraries and large JSE/JEE applications. It is also used to modularize the Java SE platform itself. The module system is a huge topic. I wrote a series of posts around this, starting with Modularity: Part 1.
-
Small amendments to the Java 7 Coin project have been made. These include allowing private methods in interfaces and no longer allowing the single underscore character (
_
) as a one-character identifier. -
The
var
reserved type name uses type inference to reduce repetitive boilerplate coding. See my previous post on local type inferences. -
The
switch
can now be used as either a statement or an expression. You can use either traditionalcase ...
labels (with fall through) or the newcase ... ->
labels (with no fall through). Switch expressions can also yield a value. See my previous post on switch expressions. -
Compact strings halve the memory usage of
String
objects if they only contain ASCII characters. See my previous post on compact strings. -
Text blocks make code more readable by avoiding unnecessary string formatting. String blocks are delimited by triple quotes, and can contain multiple double quoted strings without needing escape characters. This makes it very easy to write JSON, HTML and similar strings. See my previous post on text blocks.
-
Records are classes intended to hold pure immutable data. Creating data transfer objects (DTOs) using records is simple and reduces lots of boilerplate code. See my previous posts of records – part 1 and part 2.
-
Pattern matching is commonly needed to conditionally extract components from objects. This can now be done more concisely and safely. Two new pattern matching features have been introduced: in an enhanced
instanceOf
operator and inswitch
expressions. -
Sealed classes/interfaces can only be extended or implemented by classes that are allowed to do so. Sealed classes declaratively restrict the set of subclasses in a cleaner way than using access modifiers.
-
More useful
NullPointerException
messages allow easier debugging.
Framework Integration and Support
Java 17 integrates with a variety of frameworks such as Spring, Hibernate, Jakarta EE (formerly Java EE), Apache Kafka, Spark, and Quakus. Many of the newer versions of these frameworks require a Java 17 baseline. Which framework should you use? Every framework has its own unique features, but that’s a topic for another post.
Enhanced Performance
JIT (Just-In-Time) compilers are fast, but Java applications can get so large that it takes a long time for the JIT to warm up completely. Ahead-Of-Time (AOT) compilation reduces program startup time and improves runtime performance. jaotc
is an ahead-of-time compiler that produces native code for compiled Java methods.
Many performance improvements were made to the low-pause G1 garbage collector in Java 8 and later releases. Other garbage collectors have been added. This includes the low-latency Z Garbage Collector (ZGC) and the low-pause-time Shenandoah garbage collector.
Improved Security
It is critical that your applications are secure. In Java 17 there are upgraded security features that help protect users’ data and ensure application integrity. Many known security vulnerabilities in previous Java versions have been resolved.
Downsides to Upgrading
Lots of code changes! Lots of testing! Deprecation and removal of APIs!
All Java applications contain both the code you wrote and a number of class dependencies. If any APIs being used are deprecated or removed, this might break your code, the dependencies, or both. You must make sure the dependencies are up to date to prevent breaking issues.
Sometimes you might have to wait for a new framework version that is compatible with your chosen Java version before you can upgrade.
Marc Hoffmann and Cay Horstmann have created a very useful website where you can view the API changes for any Java version. Check out the Java Version Almanac website. They have a lot of other technical information online as well.
Conclusion
Before upgrading to Java 17 (or any other LTS version) you need to do a lot of research as part of the pre-upgrade evaluation process. You need solid knowledge of any dependencies to prevent breaking your application.
The language enhancements are always welcome, and rarely, if ever, cause breaking changes.
Was this post useful? Please share your comments, and as always, stay safe and keep learning!