What is a POJO Class?

1. Overview

In this short tutorial, we’ll investigate the definition of “Plain Old Java Object” or POJO for short.

We’ll look at how a POJO compares to a JavaBean, and how turning our POJOs into JavaBeans can be helpful.

2. Plain Old Java Objects

2.1. What Is a POJO?

When we talk about a POJO, what we’re describing is a straightforward type with no references to any particular frameworks. A POJO has no naming convention for our properties and methods.

Let’s create a basic employee POJO. It’ll have three properties; first name, last name, and start date:

public class EmployeePojo {

    public String firstName;
    public String lastName;
    private LocalDate startDate;

    public EmployeePojo(String firstName, String lastName, LocalDate startDate) {
        this.firstName = firstName;
        this.lastName = lastName;
        this.startDate = startDate;
    }

    public String name() {
        return this.firstName + " " + this.lastName;
    }

    public LocalDate getStart() {
        return this.startDate;
    }
}

This class can be used by any Java program as it’s not tied to any framework.

But, we aren’t following any real convention for constructing, accessing, or modifying the class’s state.

This lack of convention causes two problems:

First, it increases the learning curve for coders trying to understand how to use it.

Second, it may limit a framework’s ability to favor convention over configuration, understand how to use the class, and augment its functionality.

To explore this second point, let’s work with EmployeePojo using reflection. Thus, we’ll start to find some of its limitations.

2.2. Reflection with a POJO

Let’s add the commons-beanutils dependency to our project:

<dependency>
    <groupId>commons-beanutils</groupId>
    <artifactId>commons-beanutils</artifactId>
    <version>1.9.4</version>
</dependency>

And now, let’s inspect the properties of our POJO:

List<String> propertyNames =
  PropertyUtils.getPropertyDescriptors(EmployeePojo.class).stream()
    .map(PropertyDescriptor::getDisplayName)
    .collect(Collectors.toList());

If we were to print out propertyNames to the console, we’d only see:

[start]

Here, we see that we only get start as a property of the class. PropertyUtils failed to find the other two.

We’d see the same kind of outcome were we to use other libraries like Jackson to process EmployeePojo.

Ideally, we’d see all our properties: firstNamelastName, and startDate. And the good news is that many Java libraries support by default something called the JavaBean naming convention.

3. JavaBeans

3.1. What Is a JavaBean?

A JavaBean is still a POJO but introduces a strict set of rules around how we implement it:

  • Access levels – our properties are private and we expose getters and setters
  • Method names – our getters and setters follow the getX and setX convention (in the case of a boolean, isX can be used for a getter)
  • Default Constructor – a no-argument constructor must be present so an instance can be created without providing arguments, for example during deserialization
  • Serializable – implementing the Serializable interface allows us to store the state

3.2. EmployeePojo as a JavaBean

So, let’s try converting EmployeePojo into a JavaBean:

public class EmployeeBean implements Serializable {

    private static final long serialVersionUID = -3760445487636086034L;
    private String firstName;
    private String lastName;
    private LocalDate startDate;

    public EmployeeBean() {
    }

    public EmployeeBean(String firstName, String lastName, LocalDate startDate) {
        this.firstName = firstName;
        this.lastName = lastName;
        this.startDate = startDate;
    }

    public String getFirstName() {
        return firstName;
    }

    public void setFirstName(String firstName) {
        this.firstName = firstName;
    }

    //  additional getters/setters

}

3.3. Reflection with a JavaBean

When we inspect our bean with reflection, now we get the full list of the properties:

[firstName, lastName, startDate]

4. Tradeoffs When Using JavaBeans

So, we’ve shown a way in which JavaBeans are helpful. Keep in mind that every design choice comes with tradeoffs.

When we use JavaBeans we should also be mindful of some potential disadvantages:

  • Mutability – our JavaBeans are mutable due to their setter methods – this could lead to concurrency or consistency issues
  • Boilerplate – we must introduce getters for all properties and setters for most, much of this might be unnecessary
  • Zero-argument Constructor – we often need arguments in our constructors to ensure the object gets instantiated in a valid state, but the JavaBean standard requires us to provide a zero-argument constructor

Given these tradeoffs, frameworks have also adapted to other bean conventions over the years.

5. Conclusion

In this tutorial, we compared POJOs with JavaBeans.

First, we learned a POJO is a Java object that is bound to no specific framework, and that a JavaBean is a special type of POJO with a strict set of conventions.

Then, we saw how some frameworks and libraries harness the JavaBean naming convention to discover a class’s properties.

As usual, the examples are available over on GitHub.

Related posts:

Lấy ngày giờ hiện tại trong Java
Java Program to Implement Network Flow Problem
Java Program to find the maximum subarray sum O(n^2) time(naive method)
Java Program to Find Maximum Element in an Array using Binary Search
Compact Strings in Java 9
Jackson – Decide What Fields Get Serialized/Deserialized
MyBatis with Spring
Hướng dẫn sử dụng lớp Console trong java
Debug a HttpURLConnection problem
Câu lệnh điều khiển vòng lặp trong Java (break, continue)
Java Program to Implement the Alexander Bogomolny’s UnOrdered Permutation Algorithm for Elements Fro...
Login For a Spring Web App – Error Handling and Localization
Guide to the Synchronized Keyword in Java
How to Set TLS Version in Apache HttpClient
Java Program to Implement Caesar Cypher
Hướng dẫn Java Design Pattern – Memento
Java Program to Implement Hash Tables with Linear Probing
Java Program to Implement Levenshtein Distance Computing Algorithm
Java Program to Find Whether a Path Exists Between 2 Given Nodes
Java Program to Check if a Matrix is Invertible
Lập trình đa luồng với Callable và Future trong Java
Java Program to Use Boruvka’s Algorithm to Find the Minimum Spanning Tree
A Guide to Java SynchronousQueue
Spring Boot Change Context Path
Java Program to Solve Knapsack Problem Using Dynamic Programming
Hướng dẫn Java Design Pattern – Command
More Jackson Annotations
So sánh HashSet, LinkedHashSet và TreeSet trong Java
CyclicBarrier in Java
Spring Boot - Tracing Micro Service Logs
Java Program to Implement Euler Circuit Problem
Java Program to Implement Splay Tree