Partner – JPA Buddy – NPI (tag=JPA/Hibernate)
announcement - icon

The right tools can and will save a lot of time. As long as you are using Hibernate and IntelliJ IDEA you can boost your coding speed and quality with JPA Buddy. It will help in a lot of the day-to-day work:

  • Creating JPA entities that follow best practices for efficient mapping
  • Creating DTOs from entities and MapStruct mappers using convenient visual tools
  • Generating entities from the existing database or Swagger-generated POJOs
  • Visually composing methods for Spring Data JPA repositories
  • Generating differential SQL to update your schema in accordance with your changes in entities
  • Autogenerating Flyway migrations and Liquibase changelogs comparing entities with the database or two databases
  • … and a lot more

Simply put, you'll learn and use the best practices of Hibernate and surrounding technology and become a lot more!

Definitely visit the JPA Buddy site to see its features in action closer.

Persistence top

Get started with Spring Data JPA through the reference Learn Spring Data JPA course:


1. Overview

When we use Hibernate to retrieve data from the database, by default, it uses the retrieved data to construct the whole object graph for the object requested. But sometimes we might want to retrieve only part of the data, preferably in a flat structure.

In this quick tutorial, we'll see how we can achieve this in Hibernate using a custom class.

2. The Entities

First, let's look at entities we'll be using to the retrieve the data:

public class DeptEmployee {
    @GeneratedValue(strategy = GenerationType.SEQUENCE)
    private long id;

    private String employeeNumber;

    private String designation;

    private String name;

    private Department department;

    // constructor, getters and setters 

public class Department {
    @GeneratedValue(strategy = GenerationType.SEQUENCE)
    private long id;

    private String name;

    private List<DeptEmployee> employees;

    public Department(String name) { = name;
    // getters and setters 

Here, we have two entities – DeptEmployee and Department. For simplicity, let's assume that a DeptEmployee can belong to only one Department.

But, a Department can have multiple DeptEmployees.

3. A Custom Query Result Class

Let's say we want to print a list of all employees with just their name and the name of their department.

Typically, we would retrieve this data with a query like this:

Query<DeptEmployee> query = session.createQuery("from com.baeldung.hibernate.entities.DeptEmployee");
List<DeptEmployee> deptEmployees = query.list();

This will retrieve all employees, all their properties, the associated department, and all its properties.

But, in this particular case, this might be a bit expensive as we only need the name of the employee and the name of the department.

One way to only retrieve the information we need is by specifying the properties in the select clause.

But, when we do this, Hibernate returns a list of arrays instead of a list of Objects:

Query query = session.createQuery("select, from com.baeldung.hibernate.entities.DeptEmployee m");
List managers = query.list();
Object[] manager = (Object[]) managers.get(0);
assertEquals("John Smith", manager[0]);
assertEquals("Sales", manager[1]);

As we can see, the returned data is a bit cumbersome to process. But, fortunately, we can get Hibernate to populate this data into a class.

Let's look at the Result class that we'll use to populate the retrieved data into:

public class Result {
    private String employeeName;
    private String departmentName;
    public Result(String employeeName, String departmentName) {
        this.employeeName = employeeName;
        this.departmentName = departmentName;

    public Result() {

    // getters and setters 

Note that the class is not an entity but just a POJO. However, we can also use an entity as long as it has a constructor that takes all attributes that we want to populate as parameters.

We'll see why the constructor is important in the next section.

4. Using a Constructor in HQL

Now, let's look at the HQL that uses this class:

Query<Result> query = session.createQuery("select new com.baeldung.hibernate.pojo.Result(," 
  + " from com.baeldung.hibernate.entities.DeptEmployee m");
List<Result> results = query.list();
Result result = results.get(0);
assertEquals("John Smith", result.getEmployeeName());
assertEquals("Sales", result.getDepartmentName());

Here, we use the constructor we defined in the Result class along with the properties we want to retrieve. This will return a list of Result objects with the data populated from the columns.

As we can see, the returned list is easier to process than using a list of object arrays.

It's important to note that we have to use the fully qualified name of the class in the query.

5. Using a ResultTransformer

An alternative to using a constructor in the HQL query is to use a ResultTransformer:

Query query = session.createQuery("select as employeeName, as departmentName" 
  + " from com.baeldung.hibernate.entities.DeptEmployee m");
List<Result> results = query.list();
Result result = results.get(0);
assertEquals("John Smith", result.getEmployeeName());
assertEquals("Sales", result.getDepartmentName());

We use the Transformers.aliasToBean() method to use the retrieved data to populate the Result objects.

Consequently, we have to make sure the column names or their aliases in the select statement match the properties of the Result class.

Note that Query.setResultTransformer(ResultTransformerhas been deprecated since Hibernate 5.2.

6. Conclusion

In this article, we saw how a custom class can be used to retrieve data in a form that is easy to read.

The source code that accompanies this article is available over on GitHub.

Persistence bottom

Get started with Spring Data JPA through the reference Learn Spring Data JPA course:

Persistence footer banner
Inline Feedbacks
View all comments
Comments are closed on this article!