TIL (Today I Learned)

[Spring] Spring Data JPA에서 @Repository를 사용하지 않는 이유

기만나🐸 2025. 2. 9. 17:16

spring data jpa로 프로젝트를 구현할때, Repository 클래스에 Repository 어노테이션을 사용하지 않는 이유가 궁금해져서 알아보았다.

spring jdbc로 구현할 때는 @Repository를 썼었는데, JPA에서는 Repository 클래스에 @Repository를 사용하지 않아도 되는 이유가 뭘까?

 

Spring JDBC vs Spring Data JPA

  Spring JDBC Spring Data JPA
레포지터리 `JdbcTemplate`을 이용하여 직접 SQL 작성 `JpaRepository` 또는 `CrudRepository`를 상속하여 자동으로 구현
@Repository 필요 여부 명시적으로 `@Repository`를 선언해야 스프링 빈(Bean)으로 등록됨 Spring이 자동으로 빈(Bean) 등록
(@Repository를 명시해도 문제는 없음!)
예외 변환
(AOP 적용 여부)
`@Repository`를 선언해야 Spring의 예외 변환(AOP)이 적용됨 자동으로 예외 변환 지원

 

 

Spring Data JPA의 Repository

Spring Data JPA에서 JpaRepository를 상속받는 인터페이스는 Spring Boot가 자동으로 구현체를 생성해준다.
그래서 굳이 @Repository를 명시할 필요 없이 자동으로 빈으로 등록된다.

 

예시: 일정관리 API의 Repository

import com.example.schedule.entity.Schedule;
import org.springframework.data.jpa.repository.JpaRepository;

public interface ScheduleRepository extends JpaRepository<Schedule, Long> {
}

 

 

Spring Data JPA의 예외 변환 자동화(AOP)

Spring Data JPA는 @Repository 없이도 자동으로 예외 변환을 수행한다.

JPA 구현체(Hibernate 등)에서 발생하는 기본 예외(RuntimeException) 를 Spring의 일관된 데이터 접근 계층 예외(DataAccessException) 로 변환하여 처리한다.

 

예시: 일정 조회 API의 예외 발생 orElseThrow

@Service
@RequiredArgsConstructor
public class ScheduleService {
    private final ScheduleRepository scheduleRepository;

    public Schedule getSchedule(Long id) {
        return scheduleRepository.findById(id)
                .orElseThrow(() -> new RuntimeException("존재하지 않는 아이디입니다."));
    }
}

 

Spring이 자동으로 예외를 변환하는 과정

  1. Spring이 @Repository 빈을 감싸는 프록시(proxy)를 생성
  2. Repository 메서드를 실행할 때 AOP가 적용된 프록시가 먼저 실행됨
  3. JPA 예외가 발생하면 AOP가 예외를 감지하고, Spring의 DataAccessException으로 변환
  4. 서비스(Service) 계층에서는 변환된 Spring 예외를 받아서 처리 가능

 

 

결론

1️⃣ Spring Data JPA는 JpaRepository를 상속받으면 자동으로 빈으로 등록됨
2️⃣ @Repository 없이도 Spring이 예외 변환(AOP) 기능을 자동 지원
3️⃣ Spring JDBC에서는 @Repository가 필요했지만, JPA에서는 생략 가능
4️⃣ 필요하면 @Repository를 추가해도 무방하지만 일반적으로 불필요함 🎯