Zero to Hero
Published 2021. 5. 5. 14:47
Spring Study 03 Programming

온라인 강의를 듣고 배운 점들을 기록한다.

 

Custom ResponseResult

- HTTP 헤더를 이용해서 정보를 표현하는 것은 굉장히 제한적이다.

- 그래서 억지로 HTTP 헤더를 이용해 결과를 표현하는 것보단, Body에 따로 헤더 역할을 하는 객체를 사용해서 정보를 표현하는 방법이 좋다.

- 그러니깐 Body에 내가 만든 헤더를 넣고 그 안에 정보(성공, 실패, 기타 로그 등)를 넣고, 반환해야 할 정보는 따로 바디 객체 안에 넣어서 반환한다.

- 실제로 공공 데이터 API를 보면 반환 정보 스펙이 비슷하다.

<response>
	<header>
		<resultCode>00</resultCode>
		<resultMsg>NORMAL SERVICE.</resultMsg>
	</header>
	<body>
	<items>
		<item>
		</item>
        ...
        <item>
        </item>
	</body>
</response>

- 이런 식으로 Body에 모두 표현한다.

- 클라이언트 입장에서도 이런 방법이 괜찮다고 보는 게, 무조건 서버에서 HTTP 상태 에러를 보내지 않고 200 OK로 보낼 수 있고, 클라이언트단에선 그냥 반환된 객체의 헤더를 보고 상태를 파악할 수 있다.

- 즉 클라이언트 코드가 400 에러, 500 에러 같은 예외 처리 코드를 만들 필요가 없다. (정답은 아님)

 

JPA Magic

List<User> findByEmailContainsAndPhoneContainsAndUserNameContains
(String email, String phone, String username);
// 아래 쿼리와 같음
select *
from user
where email like '%입력한이메일%'
and phone like '%입력한전화번호%'
and username like '%입력한사용자이름%'
(대충 이런 쿼리에서 예상할 수 있는 결과를 반환한다는 뜻)

- JPA는 JpaRepository를 상속받아서 Interface를 구현하고 그 안에 규칙에 맞는 메서드를 만들면 적합한 쿼리를 자동으로 만든다.

- 다양한 키워드로 복잡하지 않은 쿼리를 Java 코드로 만들 수 있다는 건 큰 장점이다.

- 위 메서드는 "email 칼럼에 입력된 이메일 문자열을 포함하고(contains) phone 칼럼에 입력된 전화번호 문자열을 포함하고, username 칼럼에 입력된 사용자 이름 문자열을 포함하는 User 데이터 목록을 반환해라"라는 기능을 한다.

 

JPQL, @Query

- 객체 지향 쿼리

- SQL과 비슷하지만 대상이 Entity라는 점이 다르다.

- 기본적으로 SQL 테이블에 해당하는 위치는 반드시 ALIAS 식으로 들어가야 하는 것 같다.

- JPA 메서드와 마찬가지로 JpaRepository를 상속받은 인터페이스에 구현하고, 구현 시에는 @Query 어노테이션을 사용해서 JPQL 쿼리를 작성한다.

 

Native Query

- SQL의 그것.

- JPA, JPQL로 구현하기 까다롭거나, 기존 시스템의 DAO 구조를 JPA로 퍼팅하는 것이 어려울 때 사용한다.

- EntityManager.createNativeQuery()로 사용한다.

- 쿼리를 정말 DB에서 쓰는 것처럼 해야 한다. 즉 JOIN 하는 경우는 실제로 JOIN 되었을 때 table을 상상하면서 그려야 한다.

- JPA, JPQL과 가장 큰 차이점은 반환되는 결과가 List <Object []>라는 점이다.

- 다시 말해서 우리가 DB에서 SQL을 사용해서 얻는 그 row 값을 Object 배열 형태로 받아온다.

- 그래서 일반적으로 객체를 Body에 반환할 때 결과가 key:value 인 json형태가 아닌 그냥 value만 내려간다.

- 기존처럼 보내려면 크게 2가지 방법이 있다. 추후 기술.

 

@SqlResultSetMapping

- 위의 Native Query 결과를 받을 객체에 대한 spec을 설정하고 값을 바인딩한다.

- MyBatis의 ResultSet과 비슷하게 JOIN 결과에 대해서 담을 객체 정보를 어노테이션 안에 기술하고 받는다.

- 이렇게 하면 기존처럼 key-value의 model을 반환할 수 있다.

- 하지만 이것이 좋은가에 대해서는 약간 의문이 드는데, 우선 가독성이 그렇게 좋지 못한 것 같다.

- 컨벤션 룰에 따라 다르겠지만 그냥 Model을 하나 선언하고 생성자로 Native Query 결과를 파라미터로 받는 식으로 구현하는 방법이 더 예쁜 것 같다.(개인 생각)

 

 

 

 

'Programming' 카테고리의 다른 글

DB 예약어(MySQL, MariaDB)  (0) 2021.05.14
Spring Study 04  (0) 2021.05.05
Docker 03  (0) 2021.04.30
M1 맥북에서 Linux Ubuntu 사용하기 with AWS EC2  (0) 2021.04.29
Spring Study 02  (0) 2021.04.28
profile

Zero to Hero

@Doljae

포스팅이 좋았다면 "좋아요❤️" 또는 "구독👍🏻" 해주세요!