jOOQ & Immutables & Jackson: Great together

I really like Java. But only the plain one. I hate all the enterprise frameworks like Spring, Java EE or Hibernate. I consider them enormous and verbose. It my eyes usage of them leads to corporate applications:

  • Application so complex that it is hard to avoid duplicity in code because everone is afraid to change anything.
  • Applications that does not adapt to company needs so company needs to adapt to applications.
  • Applications that is not possible to maintain and improve any more.

Feels like hell for me :-) I prefer small, single purpose libraries. For that reason is Navigo3 using multiple libraries for data.

For building access classes to the database we are using jOOQ. You just point it to database and it will generate code for handling it. We are doing that during every Gradle build. If you then use generated code for data access it is automatically verified by compiler. Compiler will complain if anything is wrong - data type was changed, column removed, etc. Because objects read from database can be basically plain POJOs, they may be directly serialized into JSON and used in REST API. I don’t need to say how easy is to find references to certain object, for example column when compared to SQL strings in code…mainly for fields like ‘createdAt’ which is in all tables.

For effortless data structures (POJOs) we are using Immutables. It is matter of seconds to prepare data class with all necessary access methods or builder. No need to write any getter/setter anymore! This is handy mainly for programmers who like functional programming principles. Data are data and they are shaped by functions. Also since I am using Immutables I use static methods much more than before. The reason is that can create methods that returns complex output easily. Formerly I preferred to keep much richer internal state of objects and methods on that object were modifying it instead returning value. This leads to much easier refactoring - static method is so much easier to move that instance method!

For JSON (de)serialization we are using Jackson. Both jOOQ and Immutables have embedded great support for it. It is even possible to serialize combination of both.

Consider this example: I have REST API method that should return information about person - GET /person-info/12345. But not only that, I would like to return also information about company assigned to person - for example to avoid second request during rendering person detail in React.js.

So task is to compose DbPerson and DbCompany classes (generated by jOOQ) into single class that can be (de)serialized. Easy done as nested interface of REST handler:

class Handler { 
  @Value.Immutable 
  @JsonSerialize(as = ImmutablePersonAndCompany.class) 
  @JsonDeserialize(as = ImmutablePersonAndCompany.class) 
  public interface PersonAndCompany { 
    DbPerson getPerson(); 
    DbCompany getCompany(); 
  } 

  ... 
}

So you get generated ImmutablePersonAndCompanyBuilder, fill it with both objects loaded by jOOQ and serialize it using Jackson. Task accomplished.

Using this technique it is easy to add fields into data. For example adding information about address can be done by adding single line.

We also utilize POJO nature of this libraries for documentation. It is quite easy to traverse definition of such classes using reflection and automatically generate documentation from it. Such documentation is always up-to-date without any manual actions.

meta.png