Hibernate SessionFactory Spring Boot CRUD Example

This tutorial will guide you through setting up and using Hibernate SessionFactory with Spring Boot and a MySQL database. We will demonstrate how to configure Hibernate, create an entity class (User), and perform basic CRUD operations.

Introduction

What is Hibernate SessionFactory?

The SessionFactory is a factory for Session objects in Hibernate. It is a thread-safe, immutable object representing a single data source or database. The SessionFactory is responsible for creating and managing Session objects, which are the primary interfaces for performing CRUD operations in Hibernate.

Why Use SessionFactory?

  • Performance: It is an efficient way to manage database connections, as it uses a connection pool.
  • Thread Safety: SessionFactory is thread-safe, ensuring multiple threads can access it without causing concurrency issues.
  • Configuration: It holds the configuration details and mappings, making it easy to manage and reuse configurations.

Integration with Spring Boot

Spring Boot simplifies the integration of Hibernate by providing auto-configuration and dependency management. By using Spring Boot, you can focus on building your application without worrying about the boilerplate setup code.

In this tutorial, we will:

  1. Set up a Spring Boot project with necessary dependencies.
  2. Configure Hibernate to connect to MySQL.
  3. Create an entity class (User).
  4. Create a repository for CRUD operations.
  5. Demonstrate CRUD operations using Hibernate and Spring Boot.

Step 1: Set Up Your Project

1.1 Create a Spring Boot Project

Open your IDE and create a new Spring Boot project.

1.2 Add Dependencies

Update your pom.xml file to include dependencies for Spring Boot, Hibernate, and MySQL.

<project xmlns="http://maven.apache.org/POM/4.0.0"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
    <modelVersion>4.0.0</modelVersion>

    <groupId>com.example</groupId>
    <artifactId>hibernate-sessionfactory-example</artifactId>
    <version>1.0-SNAPSHOT</version>

    <parent>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-parent</artifactId>
        <version>3.0.0</version>
        <relativePath/> <!-- lookup parent from repository -->
    </parent>

    <dependencies>
        <!-- Spring Boot Starter Data JPA -->
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-data-jpa</artifactId>
        </dependency>

        <!-- MySQL Connector -->
        <dependency>
            <groupId>mysql</groupId>
            <artifactId>mysql-connector-java</artifactId>
            <version>8.0.29</version>
        </dependency>

        <!-- Hibernate Core -->
        <dependency>
            <groupId>org.hibernate.orm</groupId>
            <artifactId>hibernate-core</artifactId>
            <version>6.4.0.Final</version>
        </dependency>

        <!-- Spring Boot Starter Web -->
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
        </dependency>

        <!-- Spring Boot Starter Test -->
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-test</artifactId>
            <scope>test</scope>
        </dependency>
    </dependencies>

    <build>
        <plugins>
            <plugin>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-maven-plugin</artifactId>
            </plugin>
        </plugins>
    </build>
</project>

Step 2: Configure Hibernate with SessionFactory

2.1 Create application.properties

Create an application.properties file in the src/main/resources directory to configure database connection settings and Hibernate properties.

spring.datasource.url=jdbc:mysql://localhost:3306/hibernate_db
spring.datasource.username=root
spring.datasource.password=password
spring.datasource.driver-class-name=com.mysql.cj.jdbc.Driver

spring.jpa.show-sql=true
spring.jpa.properties.hibernate.dialect=org.hibernate.dialect.MySQLDialect
spring.jpa.hibernate.ddl-auto=update

Replace hibernate_db, root, and password with your MySQL database name and credentials.

2.2 Create HibernateConfig Class

Create a HibernateConfig class to configure the SessionFactory bean.

package com.example.config;

import org.hibernate.SessionFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.orm.hibernate5.LocalSessionFactoryBean;
import org.springframework.orm.hibernate5.HibernateTransactionManager;
import org.springframework.transaction.PlatformTransactionManager;
import org.springframework.transaction.annotation.EnableTransactionManagement;

import javax.sql.DataSource;
import java.util.Properties;

@Configuration
@EnableTransactionManagement
public class HibernateConfig {

    @Autowired
    private DataSource dataSource;

    @Bean
    public LocalSessionFactoryBean sessionFactory() {
        LocalSessionFactoryBean sessionFactory = new LocalSessionFactoryBean();
        sessionFactory.setDataSource(dataSource);
        sessionFactory.setPackagesToScan("com.example.entity");
        sessionFactory.setHibernateProperties(hibernateProperties());

        return sessionFactory;
    }

    @Bean
    public PlatformTransactionManager hibernateTransactionManager(SessionFactory sessionFactory) {
        HibernateTransactionManager transactionManager = new HibernateTransactionManager();
        transactionManager.setSessionFactory(sessionFactory);
        return transactionManager;
    }

    private Properties hibernateProperties() {
        Properties hibernateProperties = new Properties();
        hibernateProperties.setProperty("hibernate.dialect", "org.hibernate.dialect.MySQLDialect");
        hibernateProperties.setProperty("hibernate.show_sql", "true");
        hibernateProperties.setProperty("hibernate.format_sql", "true");
        hibernateProperties.setProperty("hibernate.hbm2ddl.auto", "update");
        return hibernateProperties;
    }
}

Explanation:

  • The @Configuration annotation indicates that the class is a Spring configuration class.
  • The @EnableTransactionManagement annotation enables Spring's annotation-driven transaction management.
  • The sessionFactory method creates a LocalSessionFactoryBean bean, configuring the Hibernate SessionFactory.
  • The hibernateTransactionManager method creates a HibernateTransactionManager bean for managing transactions.
  • The hibernateProperties method sets Hibernate properties.

Step 3: Create the Entity Class

Create an entity class User that will be mapped to a table in the database. This class uses annotations to define the entity and its fields.

3.1 Create User Entity

package com.example.entity;

import jakarta.persistence.Entity;
import jakarta.persistence.GeneratedValue;
import jakarta.persistence.GenerationType;
import jakarta.persistence.Id;

@Entity
public class User {
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Long id;
    private String name;
    private String email;

    // Getters and setters
    public Long getId() {
        return id;
    }

    public void setId(Long id) {
        this.id = id;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public String getEmail() {
        return email;
    }

    public void setEmail(String email) {
        this.email = email;
    }
}

Explanation:

  • The @Entity annotation specifies that the class is an entity and is mapped to a database table.
  • The @Id annotation specifies the primary key of the entity.
  • The @GeneratedValue(strategy = GenerationType.IDENTITY) annotation specifies that the primary key is auto-incremented.

Step 4: Create the DAO Class

Create a DAO class to manage database operations using Hibernate.

4.1 Create UserDAO

package com.example.dao;

import com.example.entity.User;
import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Repository;
import org.springframework.transaction.annotation.Transactional;

import java.util.List;

@Repository
public class UserDAO {

    @Autowired
    private SessionFactory sessionFactory;

    @Transactional
    public void saveUser(User user) {
        Session session = sessionFactory.getCurrentSession();
        session.saveOrUpdate(user);
    }

    @Transactional
    public User getUserById(Long id) {
        Session session = sessionFactory.getCurrentSession();
        return session.get(User.class, id);
    }

    @Transactional
    public List<User> getAllUsers() {
        Session session = sessionFactory.getCurrentSession();
        return session.createQuery("from User", User.class).list();
    }

    @Transactional
    public void deleteUser(Long id) {
        Session session = sessionFactory.getCurrentSession();
        User user = session.byId(User.class).load(id);
        session.delete(user);
    }
}

Explanation:

  • The UserDAO class contains methods to interact with the database using Hibernate.
  • The @Repository annotation indicates that the class is a Spring repository component.
  • The @Transactional annotation is used to manage transactions for each method.
  • The saveUser, getUserById, getAllUsers, and deleteUser methods perform CRUD operations using the SessionFactory.

Step 5: Create the Service Class

Create a service class to encapsulate the business logic for managing users.

5.1 Create UserService

package com.example.service;

import com.example.dao.UserDAO;
import com.example.entity.User;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.List;

@Service
public class UserService {

    @Autowired
    private UserDAO userDAO;

    public void saveUser(User user) {
        userDAO.saveUser(user);
    }

    public User getUserById(Long id) {
        return userDAO.getUserById(id);
    }

    public List<User> getAllUsers() {
        return userDAO.getAllUsers();
    }

    public void deleteUser(Long id) {
        userDAO.deleteUser(id);
    }
}

Explanation:

  • The UserService class contains methods to perform CRUD operations using the UserDAO.
  • The @Service annotation indicates that the class is a Spring service component.
  • The @Autowired annotation is used to inject the UserDAO dependency.

Step 6: Create the Controller Class

Create a controller class to handle HTTP requests for user operations.

6.1 Create UserController

package com.example.controller;

import com.example.entity.User;
import com.example.service.UserService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.*;

import java.util.List;

@RestController
@RequestMapping("/users")
public class UserController {

    @Autowired
    private UserService userService;

    @PostMapping
    public ResponseEntity<User> createUser(@RequestBody User user) {
        userService.saveUser(user);
        return ResponseEntity.ok(user);
    }

    @PutMapping
    public ResponseEntity<User> updateUser(@RequestBody User user) {
        userService.saveUser(user);
        return ResponseEntity.ok(user);
    }

    @GetMapping("/{id}")
    public ResponseEntity<User> getUserById(@PathVariable Long id) {
        User user = userService.getUserById(id);
        if (user == null) {
            return ResponseEntity.notFound().build();
        }
        return ResponseEntity.ok(user);
    }

    @GetMapping
    public ResponseEntity<List<User>> getAllUsers() {
        List<User> users = userService.getAllUsers();
        return ResponseEntity.ok(users);
    }

    @DeleteMapping("/{id}")
    public ResponseEntity<Void> deleteUser(@PathVariable Long id) {
        userService.deleteUser(id);
        return ResponseEntity.noContent().build();
    }
}

Explanation:

  • The UserController class handles HTTP requests for user operations.
  • The @RestController annotation indicates that the class is a Spring REST controller.
  • The @RequestMapping("/users") annotation maps the controller to the /users URL path.
  • The @Autowired annotation is used to inject the UserService dependency.

Step 7: Run the Application

  1. Ensure your MySQL database is running and the connection details in application.properties are correct.
  2. Run the Spring Boot application using your IDE or the command line.

7.1 Main Application Class

package com.example;

import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;

@SpringBootApplication
public class HibernateSessionFactoryExampleApplication {
    public static void main(String[] args) {
        SpringApplication.run(HibernateSessionFactoryExampleApplication.class, args);
    }
}

Conclusion

In this tutorial, we have successfully demonstrated how to integrate Hibernate SessionFactory with Spring Boot, configure it to connect to a MySQL database, create an entity class, and perform basic CRUD operations using Hibernate and Spring Boot. This guide provides a solid foundation for using Hibernate with Spring Boot in your applications.

Comments