Spring Data JPA
Dashboard
Topic 30/30
Home › Spring Data JPA

💾 Spring Data JPA

Simplify database access with JPA entities, repositories, and Hibernate ORM.

1. ORM Concept

Relational databases represent data in tables, while Java represents data as objects. This difference causes the Object-Relational Mismatch problem. ORM (Object-Relational Mapping) frameworks bridge this gap by automatically converting data between Java objects and database tables.

Technology Description
JPA (Java Persistence API) A Java specification (interfaces and annotations) outlining how to manage relational data. It is just an API, not an implementation (package: jakarta.persistence.*).
Hibernate The most popular implementation (provider) of the JPA specification. It does the heavy lifting of translating JPA concepts to actual SQL queries.
Spring Data JPA A Spring abstraction layer built on top of JPA/Hibernate. It drastically reduces boilerplate code by automatically providing repository implementations and query generation.

2. JPA Entities

An entity is a lightweight Java class whose state is persisted to a table in a relational database. We map fields to columns using annotations.

  • @Entity: Marks the class as a JPA entity.
  • @Table(name="..."): Specifies the DB table name.
  • @Id: Defines the primary key.
  • @GeneratedValue: Specifies the primary key generation strategy (IDENTITY, SEQUENCE, AUTO).
  • @Column(name="...", nullable=false, unique=true): Customizes the column mapping.
  • @Transient: Ignores the field; it will not be persisted.
Employee.java Java

3. Entity Relationships

Databases use foreign keys to relate tables. JPA maps these relationships to object references.

  • @OneToOne: 1-to-1 relationship.
  • @OneToMany / @ManyToOne: 1-to-N relationship (e.g., Department has many Employees). The "Many" side usually holds the foreign key (@JoinColumn).
  • @ManyToMany: M-to-N relationship (e.g., Students and Courses). Requires a junction table (@JoinTable).

Fetch Types: EAGER fetches related entities immediately (can cause N+1 query performance issues). LAZY fetches them only when accessed.

OneToMany Example Java

4. Spring Data JPA Repositories

Instead of writing DAO (Data Access Object) classes with repetitive JDBC or Hibernate code, you just define an interface. Spring generates the implementation at runtime.

The hierarchy: Repository → CrudRepository → PagingAndSortingRepository → JpaRepository.

JpaRepository gives you full CRUD, pagination, and sorting capabilities out of the box.

EmployeeRepository.java Java

5. Derived Query Methods

Spring Data JPA can automatically generate queries simply by looking at the method name! It parses terms like findBy, LessThan, And, and maps them to SQL.

EmployeeRepository.java (Extended) Java

6. JPQL (Java Persistence Query Language)

For complex queries that make method names too long, use the @Query annotation. JPQL operates on Entity classes and fields, not database tables and columns. You can also use native SQL.

CustomQueries.java Java

7. Pagination and Sorting

To avoid loading thousands of rows into memory, use Pagination. Pass a Pageable object to your repository method.

PaginationDemo.java Java

8. Configuration

Configure JPA in application.properties.

application.properties Properties

9. Complete Mini Project: E-Commerce

A quick look at multiple entities working together.

EcommerceDomain.java Java

10. Auditing with Spring Data

Auditing automatically tracks who created/modified an entity and when.

  1. Add @EnableJpaAuditing to your main app class.
  2. Add @EntityListeners(AuditingEntityListener.class) to your entity.
AuditableEntity.java Java

11. Caching

Spring provides an easy caching abstraction. Enable it with @EnableCaching.

CachedEmployeeService.java Java

12. Best Practices + Common Pitfalls

Problem / Pitfall Solution / Best Practice
N+1 Query Problem (Fetching a list of parents causes N additional queries for children). Use @Query("SELECT p FROM Parent p JOIN FETCH p.children") or EntityGraphs to load related data in a single query.
Exposing Entities in APIs (Infinite recursion, leaking DB structure). Always map Entities to DTOs (Data Transfer Objects) before returning them in a @RestController. Use MapStruct or ModelMapper.
LazyInitializationException (Trying to access a lazy collection outside an open session). Ensure the database transaction spans the service layer using @Transactional. Initialize collections inside the transaction.
Using save() for updates (Can trigger unnecessary SELECTs). Within a @Transactional method, simply fetching an entity and modifying its setters will automatically issue an UPDATE when the transaction commits (Dirty Checking).