2019. 3. 20. 20:37ㆍ[개발] 기록/오늘의 고민
해결
1. 엘라스틱 서치 템플릿을 안쓰는 방향으로 하였다.
2. 엘라스틱 서치 (유사) JPA 를 안사용 하는 방향으로 하였다.
3. 엘라스틱 서치를 Rest api로 호출하기로 하였다.
=> 엘라스틱 서치는 자바에서 Rest api 로 엘라스틱 서치를 호출 할 수 있도록 2가지 형태로 지원한다.
=> 1. Low level REST Client
=> 2. High level REST Client
=> Low level REST Client 는 RestClient 로 지원하며 엘라스틱 서치에 REST API로 접근하는 방식이다.
=> High level REST Client 는 HighLevelRestClient 로 지원하며 엘라스틱 서치에 접근할 때 리퀘스트를 빌더로 만들어서 API 통신 하는 방식이다. 리스폰스도 이미 만들어진 클래스로 받아올 수 있게 지원해준다.
=> High level REST Client 는 Low level REST Client 을 이용하여 구현되어있다고 공식 문서에 나와있다.
=> 참조할만한 포스트
0. 공식문서
1. (2018.07) KWANGSIK LEE's log
=> 모듈에대한 의존성이 더 낮고 API 의 body를 직접 제어할 수 있는 Low level REST Client 를 쓰기로 하였다.
장점
1. @Document에서 자유로워지니 인덱스 생성이 자유로워졌다.
2. @Document에서 자유로워지니 데이터 삽입도 자유로워졌다.
3. 인덱스 생성 ~ 맵핑 파일 적용이 하나의 api 호출로 합쳐져서 인덱스만 성공하고 맵핑은 실패할 수도 있다는 걱정거리가 사라졌다. (Put 인덱스 할때 맵핑정보도 넘기면 되므로)
새로 나온 문제상황과 해결
- 해쉬 데이터를 엘라스틱 서치에 저장해야한다.
=> 안타깝게도 엘라스틱 서치는 해쉬라는 데이터 타입이 존재하지않는다.
=> Nested 방식으로 임의의 자료형을 맵핑하는 방식이 존재
=> 맵핑 정보를 만들 때 엔티티 멤버 변수의 타입을 알아내서 HashMap이면 nested 데이터 타입으로 지정해주자.
엘라스틱 서치에 저장하려는 엔티티
@Data public class MyData{ String myName; HashMap<String, String> myHashs; } |
엘라스틱 서치 맵핑 정보
{ "mappings" : { "_doc" : { "properties" : { "myName" : { "type" : "text" }, "myHashs" : { "type":"nested", "properties : { "key" : "text", "value" : "text" } } } } } |
Json 데이터를 insert 하려는 형식
{ "myName" : "kok202", "myHashs": [{"key":"abc", "value":"123"}, {"key":"def", "value":"456"}, {"key":"ghi", "value":"789"}] } |
=> 해쉬 데이터를 Jackson으로 그대로 파싱하면
{ "myName" : "kok202", "myHashs": [{"abc","123"}, {"def","456"}, {"ghi","789"}] } |
다음과 같이 파싱된다.
해쉬맵을 원하는 방식으로 Serialize, Deserialize 해주는 커스텀 Serializer, Deserializer 를 만들어야한다.
그리고 해쉬 데이터 필드 위에 해당 어노테이션을 달아주는 방식으로 해결하였다.
@JsonSerializer
@JsonDeserializer
* 변수 타입을 알아내기 위해 커스텀 어노테이션을 만들어서 사용했는데 이제 크게 의미 없으니 다 지우자.
* mapping 정보가 해쉬맵 때문에 어쩔수 없이 엔티티에 의존적이다 = 맵핑 파일을 만드는 것이 자동화가 불가능하다.
=> 이럴거면 그냥 스트링으로 json 파일을 만들어서 때려박을걸 그랬다.
* ElasticsearchTemplate은 Spring 쪽에서 지원하는 Spring-data-elasticsearch 에서 사용하는 것이다.
* Low, High level REST API 는 Elasticsearch 쪽에서 지원하는 공식 api 이다.
=> 아예 ElasticsearchTemplate를 사용하지 말자
=> spring-boot-starter-data-elasticsearch 디펜던시를 삭제할 수 있다.
'[개발] 기록 > 오늘의 고민' 카테고리의 다른 글
ControllerAdvice의 Response status 가 변경되지 않는 문제 (0) | 2019.06.20 |
---|---|
엘라스틱 서치 인덱스 동적 생성, 해쉬, 데이터 저장? (0) | 2019.03.19 |
엘라스틱 서치 인덱스 동적 생성? (0) | 2019.03.18 |