Lombok Serialize and Deserialize @Builder Class

Learn to serialize and deserialize Lombok @Builder annotated class with Jackson library.

For demo purpose, we are using Article class have few field members. We have created this class during the Lombok @Builder tutorial.

@Builder
@Getter
@ToString
public class Article {

  private Long id;
  private String title;
  private List<String> tags;
}

1. Serializing @Builder Class

The serialization process is very simple and we do not do anything extra. It works out of the box.

1.1. Gson

Java program to serialize @Builder class using Gson.

Article article = Article.builder(1L)
  .title("Test Article")
  .tag("Test Tag")
  .build();

//With Gson
Gson gson = new Gson();
String gsonJson = gson.toJson(article);

//Prints {"id":1,"title":"Test Article","tags":["Test Tag"]}
System.out.println(gsonJson); 

1.2. Jackson

Java program to serialize @Builder class using Jackson.

Article article = Article.builder(1L)
  .title("Test Article")
  .tag("Test Tag")
  .build();

//With Jackson
ObjectMapper mapper = new ObjectMapper();
String json = mapper.writeValueAsString(article);

//Prints {"id":1,"title":"Test Article","tags":["Test Tag"]}
System.out.println(json); 

2. Deserializing @Builder Class

2.1. Gson

Gson works great for deserialization as well, without any extra configuration. We can use it directly.

String json = "{\"id\":1,\"title\":\"Test Title\",\"tags\":[\"Test Tag\"]}";

Gson gson = new Gson();
Article gsonArticle = gson.fromJson(json, Article.class);

//Prints Article(id=1, title=Test Title, tags=[Test Tag])
System.out.println(gsonArticle);

2.2. Jackson

By default, if we try to deserialize the Article class we will get the runtime exception InvalidDefinitionException. The Jackson is not able to find a way to construct the object in the absence of a default no-args constructor.

ObjectMapper mapper = new ObjectMapper();
String json = "{\"id\":1,\"title\":\"Test Title\",\"tags\":[\"Test Tag\"]}";
Article article = mapper.readValue(json, Article.class);
System.out.println(article);
Exception in thread "main" com.fasterxml.jackson.databind.exc.InvalidDefinitionException: 
Cannot construct instance of `com.howtodoinjava.demo.lombok.Article` 
(no Creators, like default constructor, exist): cannot deserialize from Object value 
(no delegate- or property-based Creator)
 at [Source: (String)"{"id":1,"title":"Test Title","tags":["Test Tag"]}"; line: 1, column: 2]

2.2.1. Lombok @Jacksonized

Using @Jacksonized annotation is the simplest solution if you are using Jackson for deserialization purposes. Just annotate the @Builder class with @Jacksonized annotation and we are good for converting the JSON string to Java object.

@Builder(toBuilder = true)
@Getter
@ToString
@Jacksonized
public class Article {
    ...
}
String json = "{\"id\":1,\"title\":\"Test Title\",\"tags\":[\"Test Tag\"]}";

ObjectMapper mapper = new ObjectMapper();
Article article = mapper.readValue(json, Article.class);

//prints Article(id=1, title=Test Title, tags=[Test Tag])
System.out.println(article);

2.2.2. Jackson @JsonDeserialize and @JsonPOJOBuilder

Keep in mind that @Jacksonized is an experimental feature and may be removed in future versions. Another approach to make @Builder work with Jackson is by adding Jackson annotation which can help Jackson to figure out how to create an instance of Article class.

The two such annotations are:

@Builder
@Getter
@ToString
@JsonDeserialize(builder = Article.ArticleBuilder.class)
public class Article {
  private Long id;
  private String title;
  private List<String> tags;

  @JsonPOJOBuilder(withPrefix="")
  public static class ArticleBuilder {
  }
}
String json = "{\"id\":1,\"title\":\"Test Title\",\"tags\":[\"Test Tag\"]}";

ObjectMapper mapper = new ObjectMapper();
Article article = mapper.readValue(json, Article.class);

//Prints Article(id=1, title=Test Title, tags=[Test Tag])
System.out.println(article);

3. Conclusion

Based on the above conversation, Google Gson works best for serialization and deserialization purposes on classes annotated with Lombok @Builder. It should be the preferred approach as it works out of the box.

If using Jackson is required, we have @Jacksonized annotation that works best with very little code. In the future, if @Jacksonized is not part of Lombok then during library upgrades we can use other Jackson annotations to make deserialization work.

Happy Learning !!

Download Sourcecode

Leave a Reply

0 Comments
Inline Feedbacks
View all comments

About Us

HowToDoInJava provides tutorials and how-to guides on Java and related technologies.

It also shares the best practices, algorithms & solutions, and frequently asked interview questions.

Our Blogs

REST API Tutorial