Chapter 8: Persistence Layer with Spring Data JPA and Hibernate
In the previous chapter, we implemented request validation and exception handling for our Insurance Policy Management System (IPMS).
Our APIs can now:
- Validate requests
- Return standardized errors
- Handle exceptions gracefully
However, our data is still not stored anywhere.
In this chapter, we will introduce the persistence layer using Spring Data JPA and Hibernate.
By the end of this chapter, our APIs will be capable of storing and retrieving insurance policies from a relational database.
🎯 Learning Objectives
By the end of this chapter, you will be able to:
- Understand JPA
- Understand Hibernate
- Create Entities
- Create Repositories
- Perform CRUD operations
- Configure database connectivity
- Understand entity relationships
- Manage transactions
Why Persistence Matters
Without persistence:
Create Policy
↓
Application Restarts
↓
Data Lost
Persistence ensures data survives application restarts.
For our Insurance Policy Management System we must store:
Policy Holders
Policies
Claims
Premium Payments
Agents
Beneficiaries
JPA and Hibernate Overview
Many developers confuse JPA and Hibernate.
They are not the same.
What is JPA?
JPA stands for:
Java Persistence API
JPA is a specification.
It defines:
- Entity mapping
- Persistence operations
- Relationships
- Query mechanisms
What is Hibernate?
Hibernate is:
JPA Implementation
It provides the actual persistence engine.
JPA-Hibernate Architecture

Persistence Architecture
Our application architecture now becomes:
Controller
↓
Service
↓
Repository
↓
Hibernate
↓
Database
This follows the layered architecture introduced in Chapter05.
Database Configuration
Spring Boot simplifies database configuration.
application.yml
spring:
datasource:
url: jdbc:mysql://localhost:3306/ipms
username: root
password: password
jpa:
hibernate:
ddl-auto: update
show-sql: true
Creating Our First Entity
The first entity will be:
Policy
which we introduced in earlier chapters.
Policy Entity
@Entity
@Table(name = "policies")
public class Policy {
@Id
private String policyNumber;
private String policyType;
private String status;
private BigDecimal coverageAmount;
}
Understanding Entity Annotations
@Entity
Marks the class as a database entity.
@Entity
public class Policy {
}
@Table
Maps entity to database table.
@Table(name = "policies")
@Id
Defines the primary key.
@Id
private String policyNumber;
Entity Lifecycle
Every entity goes through a lifecycle.
Entity Lifecycle

States include:
Transient
Persistent
Detached
Removed
Understanding these states helps diagnose persistence issues.
Policy Entity Model
Our Policy entity contains:
Policy Number
Policy Type
Status
Coverage Amount
Policy Entity Model

Creating Repository Layer
Repositories abstract database access.
Without repositories:
Connection connection =
DriverManager.getConnection(...);
With Spring Data JPA:
policyRepository.save(policy);
Policy Repository
@Repository
public interface PolicyRepository
extends JpaRepository<
Policy,
String> {
}
Spring automatically generates CRUD operations.
CRUD Operations
The repository automatically provides:
save()
findById()
findAll()
deleteById()
existsById()
No implementation required.
Saving a Policy
Policy policy = new Policy();
policy.setPolicyNumber("LIFE-100001");
policyRepository.save(policy);
Hibernate generates SQL automatically.
Generated SQL
insert into policies
(
policy_number,
policy_type
)
values
(
'LIFE-100001',
'TERM'
);
Repository Flow
Repository Processing Flow

Query Methods
Spring Data JPA generates queries automatically.
Find By Status
List<Policy>
findByStatus(String status);
Spring generates SQL automatically.
Find By Policy Type
List<Policy>
findByPolicyType(String policyType);
No SQL required.
Integrating Repository into Service Layer
Service:
@Service
@RequiredArgsConstructor
public class PolicyService {
private final PolicyRepository
repository;
}
Create Policy Service
public PolicyResponse createPolicy(
PolicyRequest request) {
Policy policy = mapper.toEntity(request);
repository.save(policy);
return mapper.toResponse(policy);
}
This is our first real database operation.
Entity Relationships
Insurance systems contain relationships.
Examples:
Policy Holder
↓
Policies
Policy
↓
Claims
Policy
↓
Beneficiaries
Common Relationships
One-To-Many
@OneToMany
Example:
Policy Holder
↓
Multiple Policies
Many-To-One
@ManyToOne
Example:
Many Policies
↓
One Policy Holder
Entity Relationships

Policy Holder Entity
@Entity
public class PolicyHolder {
@Id
private Long id;
private String fullName;
}
Policy Entity Relationship
@ManyToOne
@JoinColumn(
name = "policy_holder_id")
private PolicyHolder policyHolder;
Hibernate automatically manages foreign keys.
Transactions
Database operations should be atomic.
Example:
Create Policy
↓
Create Payment Schedule
↓
Create Beneficiaries
Either:
All Succeed
or
All Fail
Transaction Management
Spring provides:
@Transactional
Transaction Example
@Transactional
public void createPolicy() {
savePolicy();
saveBeneficiary();
savePayment();
}
Transaction Processing Flow

Optimistic Locking
Multiple users may update the same policy.
Example:
User A Updates Policy
User B Updates Policy
Potential conflict.
Version Field
@Version
private Long version;
Hibernate prevents accidental overwrites.
Best Practices
✅ Use repositories for persistence
✅ Keep entities focused on data
✅ Use transactions for business operations
✅ Model relationships carefully
✅ Use optimistic locking
✅ Keep service layer responsible for orchestration
Common Mistakes
❌ Business logic inside entities
❌ Database access inside controllers
❌ Missing transactions
❌ Eager loading everywhere
❌ Exposing entities directly to APIs
Interview Questions
-
What is JPA?
-
What is Hibernate?
-
Difference between JPA and Hibernate?
-
What is an Entity?
-
What is JpaRepository?
-
What is @Transactional?
-
Difference between @OneToMany and @ManyToOne?
-
What is optimistic locking?
-
What is entity lifecycle?
-
Why use repositories?
Practice Exercises
-
Create Claim entity.
-
Create ClaimRepository.
-
Add PolicyHolder relationship.
-
Create custom query methods.
-
Add transaction management.
Key Takeaways
- JPA is a specification.
- Hibernate is a JPA implementation.
- Entities map Java objects to database tables.
- Repositories simplify database access.
- Spring Data JPA generates CRUD operations automatically.
- Relationships model business domains.
- Transactions ensure data consistency.
- Persistence is the foundation of enterprise applications.
Chapter Summary
In this chapter, you learned:
- JPA
- Hibernate
- Entity Mapping
- Repositories
- CRUD Operations
- Relationships
- Transactions
- Optimistic Locking
Our Insurance Policy Management System can now persist and retrieve data from a database. In the next chapter, we will focus on DTO Mapping, Data Transformation, and API Response Modeling.