온 코딩

[Spring Boot](Spring Data JPA) memoTest - IntelliJ2 본문

복습 ARCHIVE/모델별 프로젝트

[Spring Boot](Spring Data JPA) memoTest - IntelliJ2

SummerON 2021. 7. 8. 14:16

쿼리메서드

주로 finally~~deleteBy~~getBy와 같은 이름으로 시작하고, 필요한 필드 조건이나 AND,OR와 같은 키워드를 조합하여 메서드의 이름만으로도 쿼리조건을 만들어 낼 수 있다.

 

메서드의 파라미터는 키워드에 따라서 갯수 결정 (Between 등)

 

메서드의 리턴 타입 

select를 하는 작업일 경우 List 또는 배열을 이용할 수 있다.

파라미터에 Pageable타입을 전달하는 경우에는 반드시 Page<T> 타입으로 지정

 

* IntelliJ는 쿼리 메서드 작성 기능을 제공 

 

쿼리메서드 직접 작성 

Spring Data JPA

인터페이스

package com.hhw.ex2.repository;

import com.hhw.ex2.entity.Memo;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.Pageable;
import org.springframework.data.jpa.repository.JpaRepository;

import java.util.List;

public interface MemoRepository extends JpaRepository<Memo, Long> {

    //Memo의 mno값이 70-80사이의 객체들을 조회하고 mno의 역순으로 정렬 할 수 있는 쿼리 메서드
    List<Memo> findByMnoBetweenOrderByMnoDesc(Long from, Long to);

    //쿼리메서드와 Pageable을 결합하는 쿼리 메서드
    Page<Memo> findByMnoBetween(Long from, Long to, Pageable pageable);

    //특정조건에 맞는 엔티티 객체를 삭제하는 쿼리 메서드
    //Memo의 mno가 10보다 작은 엔티티 객체를 삭제하는 메서드
    void deleteMemoByMnoLessThan(Long num);
}

레포지토리 테스트

    //70~80사이의 메모 출
    @Test
    public void testQueryMethods(){
        List<Memo> list = memoRepository.findByMnoBetweenOrderByMnoDesc(70L,80L);
        for(Memo memo : list) {
            System.out.println(memo);
        }
    }

    //쿼리메서드와 Pageable 결합
    //Memo의 mno값이 10~50 사이의 객체를 조회하고, 그 중에 첫 페이지에 해당하는 10개의 객체를 mno 기준으로 역순 정렬
   @Test
    public void testQueryMethodWithPageable(){
        Pageable pageable = PageRequest.of(0,10,Sort.by("mno").descending());
        Page<Memo> result = memoRepository.findByMnoBetween(10L,50L,pageable);

        result.get().forEach(memo -> {
            System.out.println(memo);
        });

    }

    //memo의 mno가 10보다 작은 엔티티 객체 삭제
    @Test
    @Commit
    @Transactional
    public void testDeleteQueryMethods(){
        memoRepository.deleteMemoByMnoLessThan(10L);
    }

deleteBy를 이용하여 조건에 맞는 객체를 삭제하는 쿼리메서드

실제 사용할 때는 해당 메서드에  @Commit @Transactional을 사용해야 함

-> 1. 엔티티 객체 선택하고   2. 하나씩 지우기 / 커밋없으면 롤백 , 트랜젝셔널 없으면 예외발생

 

쿼리메서드 참고 사이트

https://docs.spring.io/spring-data/jpa/docs/current/reference/html/#jpa.query-methods.query-creation

 

Spring Data JPA - Reference Documentation

Example 109. Using @Transactional at query methods @Transactional(readOnly = true) interface UserRepository extends JpaRepository { List findByLastname(String lastname); @Modifying @Transactional @Query("delete from User u where u.active = false") void del

docs.spring.io

 

@Query 어노테이션 : 기존 SQL을 이용하여 메서드 생성 가능 

간단한 쿼리 -> Spring Data JPA가 제공하는 쿼리메서드

복잡한 조건일 경우 -> @Query 사용

 

@Query("SQL 구문")

메서드 이름과 무관하게 메서드에 추가한 어노테이션을 통하여 원하는 작업을 처리

(메서드명은 개발자가 임의로 명명할 수 있다)

value값은 객체지향쿼리로 작성 

객체지향쿼리 :  테이블대신 엔티티 클래스를 이용, 컬럼 대신 엔티티 클래스 멤버변수(필드)를 이용하여 작성

Table기준 - select * from tbl_memo m order by m.mno desc

Entity기준 - select m from Memo m order by m.mno desc

 

1. 필요한 데이터만 선별적으로 추출 가능

2. 데이터베이스에 맞는 순수한 SQL을 사용가능

3. insert, update, delete와 같이 select가 아닌 DML 등을 처리 가능. 단, @Modifying과 함께 사용 

 

실제 SQL에서 사용되는 함수들도 동일하게 사용 가능

JPA는 기존 SQL과 JPQL을 맵핑하는 역할! 

 

@Query의 파라미터 바인딩 방법 

1. 파라미터명을 활용하는 방식

2. 여러 개의 파라미터를 전달할때는 객체 이요 -> :#{ }

+update/delete 등 데이터가 수정이 되는 경우에는 @Transctional 사용 /update @Modifing도 

 

인터페이스

    //mno 역순으로 정렬하는 @Query를 이용한 메서드
    @Query("select m from Memo  m order by m.mno desc")
    List<Memo> getListDesc();
    //JPQL : Entity class 기준
    //SQL : Table기준 - select * from tbl_memo  m order by m.mno desc

    //업데이트 메서드
    @Transactional
    @Modifying
    @Query("update Memo m set m.memoText = :memoText where m.mno = :mno")
    int updateMemoText(@Param("mno") Long mno, @Param("memoText") String memoText);

    //업데이트메서드 (단, 객체로 전달)
    @Transactional
    @Modifying
    @Query("update Memo m set m.memoText = :#{#param.memoText} where m.mno = :#{#param.mno}")
    int updateMemoText(@Param("param") Memo memo);

레포지토리 테스트

    //memo의 mno가 10보다 작은 엔티티 객체 삭제
    @Test
    @Commit
    @Transactional
    public void testDeleteQueryMethods(){
        memoRepository.deleteMemoByMnoLessThan(10L);
    }

    //selectall 메서드
    @Test
    public void testSelectAll(){
        List<Memo> list = memoRepository.getListDesc();
        for(Memo memo:list){
            System.out.println(memo);
        }
    }

    //업데이트 메서드
    @Test
    public void testUpdateMethod(){
        int n = memoRepository.updateMemoText(11L, "update done");
    }

    //업데이트 메서드 -객체
    @Test
    public void testUpdateMethod2(){
        Memo memo = Memo.builder().mno(10L).memoText("update").build();
        int n = memoRepository.updateMemoText(memo);
    }
Comments