일 | 월 | 화 | 수 | 목 | 금 | 토 |
---|---|---|---|---|---|---|
1 | ||||||
2 | 3 | 4 | 5 | 6 | 7 | 8 |
9 | 10 | 11 | 12 | 13 | 14 | 15 |
16 | 17 | 18 | 19 | 20 | 21 | 22 |
23 | 24 | 25 | 26 | 27 | 28 | 29 |
30 | 31 |
- 구글
- @Entity
- 리액트오류
- post
- useEffect
- firebase
- HttpSession
- 워드프레스
- 구글애널리틱스
- 인텔리제이
- JPA
- db
- GET
- ChatGPT
- router
- Login
- mergeattributes()
- 구글알고리즘
- 플러그인
- addallattributes()
- SEO
- @Query
- set
- Thymeleaf
- GA4
- 데이터베이스
- Polylang
- @Controller
- @Repository
- linkedhastset
- Today
- Total
개발천재
[Spring Boot] JPA @Query 사용하기 +메서드 이름 기반 쿼리 본문
@Query 이해하기
@Query는 Spring Data JPA에서 사용자 정의 쿼리를 작성할 때 사용하는 어노테이션으로, JPQL(엔티티 기반 쿼리)이나 Native SQL(DB 직접 쿼리)을 사용하여 복잡한 조건의 검색, JOIN, 서브쿼리 등을 자유롭게 구현할 수 있으며, 메서드 이름으로 작성하기 어려운 쿼리를 간결하게 표현하고 최적화할 때 유용하게 사용된다.
@Query를 사용하는 이유
복잡한 쿼리나 맞춤형 쿼리가 필요할 때, JPA 메서드 이름만으로는 부족할 때 사용한다. JPQL(Java Persistence Query Language)을 사용해서 엔티티 객체를 기반으로 쿼리를 작성할 수 있고, Native Query(순수 SQL)도 지원한다.
- JPA 메서드 이름으로 만들기 어려운 경우
- SQL 최적화가 필요한 경우
- 복잡한 JOIN이나 조건이 많아질 때
- 메서드 이름이 길어질 필요 없이 간단하게 쿼리 작성 가능
- 복잡한 JOIN이나 서브쿼리도 자유롭게 작성할 수 있다.
- JPQL과 Native SQL 모두 지원
@Query 사용 방법 1, JPQL로 작성하는 방법
@Query 안에 JPQL로 작성하는 방식이다.
:name은 파라미터 바인딩(값을 전달할 자리)하고 @Param으로 메서드 매개변수와 쿼리의 파라미터를 연결한다.
public interface MemberRepository extends JpaRepository<Member, Long> {
@Query("SELECT m FROM Member m WHERE m.name = :name")
List<Member> findByName(@Param("name") String name);
}
@Query 사용 방법 2, Native Query (SQL)
nativeQuery = true를 추가하면 SQL을 그대로 사용할 수 있다.
주의할 점은 테이블 이름과 컬럼명이 DB에 실제 존재하는 이름이어야 한다.
@Query(value = "SELECT * FROM member WHERE name = :name", nativeQuery = true)
List<Member> findByNameNative(@Param("name") String name);
@Query 예시
이름에 특정 키워드가 포함된 회원 검색하는 경우
@Query("SELECT m FROM Member m WHERE m.name LIKE %:keyword%")
List<Member> searchByName(@Param("keyword") String keyword);
2개 이상의 조건을 가진 쿼리일 경우
@Query("SELECT m FROM Member m WHERE m.name = :name AND m.email = :email")
Member findByNameAndEmail(@Param("name") String name, @Param("email") String email);
메서드 이름 기반 쿼리
메서드 이름 기반 쿼리(Method Query Derivation) 방식은 JPA가 메서드명을 분석하여 자동으로 SQL을 생성하는 방식이다. 특별한 쿼리가 필요 없다면 메서드 이름 기반 쿼리를 사용하는 것이 편리할 수 있다.
엔티티
@Entity
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
public class Users {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private Long id;
@Column(length = 50)
private String name;
@Column(length = 50)
private String email;
@Column(length = 20)
@Enumerated(EnumType.STRING)
private Gender gender;
@Column(length = 50)
private String likeColor;
private LocalDateTime createdAt;
private LocalDateTime updatedAt;
}
레파지토리
@Repository
public interface UsersRepository extends JpaRepository<Users, Long> {
// 이름으로 검색하는 기능
List<Users> findByName(String name);
// 색상 값을 받아서 그 중 처음으로 발견되는 3개의 데이터를 출력
List<Users> findTop3ByLikeColor(String color);
// 남자이면서 색상이 Yellow
List<Users> findByGenderAndLikeColor(Gender gender, String color);
// 범위 검색
// 최근 7일 이내 자료를 읽어오고 싶을 때(오늘 빼고)
List<Users> findByCreatedAtBetween(LocalDateTime start, LocalDateTime end);
}
내부적으로 변환되는 JPQL (예시)
위와 같이 자동으로 SQL이 생성된다.
SELECT * FROM users WHERE name = ?
SELECT * FROM users WHERE like_color = ? LIMIT 3
SELECT * FROM users WHERE gender = ? AND like_color = ?
쿼리 방식 비교
JPQL (Java Persistence Query Language)
- 엔티티 기준으로 SQL과 비슷한 쿼리 작성
- @Query("SELECT u FROM Users u WHERE u.name = :name")
- 데이터베이스 독립적, SQL과 유사
- 복잡한 SQL은 작성이 어려울 수도 있음
Native Query
- 순수 SQL을 직접 실행
- @Query(value = "SELECT * FROM users WHERE name = :name", nativeQuery = true)
- 최적화된 SQL 사용 가능, 복잡한 쿼리 작성 가능
- DB 종속적, 유지보수 어려움
메서드 이름 기반 쿼리 (Method Query Derivation)
- 메서드명을 분석해 자동으로 SQL 생성
- findByName(String name)
- 간단한 CRUD에 적합, 유지보수 쉬움
- 복잡한 쿼리는 어려움
'개발 준비 > Spring Boot' 카테고리의 다른 글
[Spring Boot] JpaRepository 사용하기 (0) | 2025.02.21 |
---|---|
[Spring Boot] DTO와 Entity 간의 변환 (1) | 2025.02.21 |
[Spring Boot] RedirectAttributes 이해하기 (1) | 2025.02.21 |
[Spring Boot] Thymeleaf, 반복문에서 index 보여주기, stat (2) | 2025.02.21 |
[Spring Boot] HttpSession으로 로그인 구현하기 (2) | 2025.02.20 |