by BehindJava

What is difference between CrudRepository and JpaRepository interfaces in Spring Data JPA

Home » springboot » What is difference between CrudRepository and JpaRepository interfaces in Spring Data JPA

In this tutorial we are going to learn about the difference between CrudRepository and JpaRepository interfaces in Spring Data JPA.

JpaRepository extends PagingAndSortingRepository which in turn extends CrudRepository.

Their main functions are:

  • CrudRepository mainly provides CRUD functions.
  • PagingAndSortingRepository provides methods to do pagination and sorting records.
  • JpaRepository provides some JPA-related methods such as flushing the persistence context and deleting records in a batch.

Because of the inheritance mentioned above, JpaRepository will have all the functions of CrudRepository and PagingAndSortingRepository. We can use CrudRepository to exclude the functions provided by the JpaRepository and PagingAndSortingRepository.

The common interfaces:

The Spring Data core library ships with two base interfaces that expose a dedicated set of functionalities:

  • CrudRepository - CRUD methods
  • PagingAndSortingRepository - methods for pagination and sorting (extends CrudRepository)

Store-specific interfaces

The individual store modules (e.g. for JPA or MongoDB) expose store-specific extensions of these base interfaces to allow access to store-specific functionality like flushing or dedicated batching that take some store specifics into account. Here is the example for this i.e., deleteInBatch(…) of JpaRepository and it is diiferent from the delete(…) since it uses query to delete the records which increases the performance along with the side effects for not triggering the JPA-defined cascades as per the defined spec.

We generally recommend not to use these base interfaces as they expose the underlying persistence technology to the clients and thus tighten the coupling between them and the repository. You can stay with the PagingAndSortingRepository to get the original defination of the repository which means collection of records or entities.

Custom repository base interfaces

The downside of directly depending on one of the provided base interfaces is two-fold. Both of them might be considered as theoretical but I think they’re important to be aware of:

Depending on a Spring Data repository interface couples your repository interface to the library. I don’t think this is a particular issue as you’ll probably use abstractions like Page or Pageable in your code anyway. Spring Data is not any different from any other general purpose library like commons-lang or Guava.

To gain more fine-grained control over the methods expose, e.g. to create a ReadOnlyRepository that doesn’t include the save(…) and delete(…) methods of CrudRepository.

The solution to both of these downsides is to craft your own base repository interface or even a set of them. In a lot of applications I have seen something like this:

interface ApplicationRepository<T> extends PagingAndSortingRepository<T, Long> { }

interface ReadOnlyRepository<T> extends Repository<T, Long> {

  // Al finder methods go here
}

The first repository interface is some general purpose base interface that actually only fixes point 1 but also ties the ID type to be Long for consistency. The second interface usually has all the find…(…) methods copied from CrudRepository and PagingAndSortingRepository but does not expose the manipulating ones.