1 First piece of the puzzle


This chapter covers

  • Modularity and how it shapes a system
  • Java’s inability to enforce modularity
  • How the new module system aims to fix these issues

We’ve all been in situations where the software we’ve deployed refuses to work the way we want it to. There are myriad possible reasons, but one class of problems is so obnoxious that it earned a particularly gracious moniker: JAR hell. Classic aspects of JAR hell are misbehaving dependencies: some may be missing but, as if to make up for it, others may be present multiple times, likely in different versions. This is a surefire way to crash or, worse, subtly corrupt running applications.

The root problem underpinning JAR hell is that we see JARs as artifacts with identities and relationships to one another, whereas Java sees JARs as simple class-file containers without any meaningful properties. This difference leads to trouble.

One example is the lack of meaningful encapsulation across JARs: all public types are freely accessible by all code in the same application. This makes it easy to inadvertently depend on types in a library that its maintainers considered implementation details and never polished for public use. They likely hid the types in a package called internal or impl, but that doesn’t stop us from importing them anyway.

1.1 What is modularity all about?

1.1.1 Visualizing software as graphs

1.1.2 The impact of design principles

1.1.3 What modularity is all about

1.2 Module erasure before Java 9

1.3 Complications before Java 9

1.3.1 Unexpressed dependencies between JARs

1.3.2 Shadowing classes with the same name

1.3.3 Conflicts between different versions of the same project

1.3.4 Complex class loading

1.3.5 Weak encapsulation across JARs

1.3.6 Security checks have to be handcrafted

1.3.7 Poor startup performance

1.3.8 Rigid Java runtime

1.4 Bird’s-eye view of the module system

1.4.1 Everything is a module

1.4.2 Your first module

1.4.3 The module system in action

1.4.4 Your non-modular project will be fine—mostly

1.5 Goals of the module system

1.5.1 Reliable configuration: Leaving no JAR behind