본문 바로가기

춤추는 프로그래머/Big Data

ElasticSearch로 검색 Paging하기... (scan type)


일단 아래 링크를 읽어보자. 


http://www.elasticsearch.org/guide/en/elasticsearch/reference/current/search-request-search-type.html#scan



스크롤에 왜 시간값을 주는지는 잘 모르겠다.. 인자로 넘겨주는 시간 이후에는 죽는건가? 

뭐... 테스트도 안해봤따...... 뭔지... 잘........






1. 자바 함수로 구현

2. 함수를 실행시킬 때 마다 다음 페이지가 검색되도록..

3. 인자는 쿼리와 기타 검색조건들, 페이지 사이즈..


같은 함수를 실행시키는데 이게 최초 검색인지 다음페이지를 요청하는 것인지 알기 위해서 전역변수를 썼따!!!!

아니 이게 잘하는 짓인지는 모르겠지만 코딩초딩인 나는.... 플래그또는캐싱 같은 개념을 가지고... 전역변수를 씀.


전역변수

>> 쿼리와 기타 검색 조건들... 사이즈는 걍 뺌 쿼리나 기타 검색조건이 같으면 사이즈 다르게 넘어와도 

걍 첨 했던 대루 가는거다...;;;;; 지금 적어둘려고 다시 보니 그렇게 해 놨는데... 왜 그랬는지는... 잘... ㅠㅠ


그리구 함수를 두개로 나눴다.

scan search는 SearchRequestBuilder에 searchType을 SCAN으로 주고 -> 이걸 실행시킨 ListenableActionFuture를 통해 반복 실행시키면서 다음 페이지를 가져오는 방식이다. 

그래서 검색 조건들 세팅해주고 페이지 사이즈 세팅해주며 새 scroll ID를 주는 부분을 한개의 함수로 빼고 

본 함수에서는 prepareSearchScroll에 스크롤 아이디를 받아와서 새로 스크롤을 주고 정해진 개수 만큼만 딱 가져온다. 


세팅해주는_함수()

1
2
3
4
5
6
7
8
9
10
SearchRequestBuilder requestBuilder = buildSearchQuery(queries, from, to);
        
requestBuilder.setSearchType(SearchType.SCAN);
requestBuilder.setScroll(TimeValue.timeValueSeconds(1));
if(size > 0)
    requestBuilder.setSize(size/설정해_놓은_샤드의_수);
ListenableActionFuture<SearchResponse> actionFuture = requestBuilder.execute();
response= actionFuture.actionGet();
 
return response;


뭐 이런 식으로... 

여기서 사이즈를 샤드 수로 나눠주는 이유는 엘라스틱 서치가 검색을 요청할 때 각 샤드에 각각 요청을 하기 때문이다! 

원하는 양 만큼만 받을라믄 그걸 샤드 수로 나눠주고 요청 보내야 함. 딱 떨어지지 않는 사이즈에 대해서는 생각 안함 그냥. 그냥 안함. 사실 하긴 했는데 귀찮다... 어쩌라고! 참고로 설치할 때 디폴트 샤드 수가 5개인데... 뭐 난 한페이지에 44개씩 보고싶다고 하면 그냥 답없는거다. 40개씩 봐!!! ..................................는 내가 미쳤나봄. 저거 언능 수정해야긋다...^^;;;;;;;;; 나중에....


위에서 말한 전역변수 관련된 부분!!


1
2
3
4
5
6
7
8
9
            if((queries!=null && (this.queries == null || !this.queries.equals(queries)))
                || (from!=null && !from.equals(this.from)) || (to!=null && !to.equals(this.to)))    {
            response = 세팅해주는_함수(queries, from, to, size); //위의 그..;
            this.queries = new HashMap<StringString[]>();
            this.queries.putAll(queries);
            this.from = from; 
            this.to = to;
        }        
 


사람이 살면서 이런 미친짓도 한번 해 줘야한다...

전역변수가 null이면 최초검색이라고 판단한다... 전역변수와 새로 들어온 인자가 같으면 다음 페이지라고 판단한다....

(아주 귀찮아서 전역변수와 인자의 변수명을 같게 줬따...^^ this가 더 안헷갈리자너.... ㅋㅋㅋㅋㅋ ㅠㅠ 다시 말하지만 난 코딩초딩이다... 여러분... 배우는 중입니다 넘 모라 하지 마셈 확 마 내가 알아서 할라니까잉. )

최초 검색이면 세팅해주는 함수 실행시켜주고 전역변수를 인자값으로 세팅해준다. 하하하. 


그다음엔


1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
        SearchScrollRequestBuilder builder = client.prepareSearchScroll(response.getScrollId());
        builder.setScroll(TimeValue.timeValueSeconds(1));
        ListenableActionFuture<SearchResponse> future = builder.execute();
        Thread.sleep(1 * 1000);
        response = future.actionGet();
        
        SearchHits hits = response.getHits();
    
        long totalHits = hits.getHits().length;
        
        for (int i = 0; i < totalHits; i++) {
            Map<String, Object> hit = hits.getAt(i).getSource();
                result만들어주기;
        }
        return result;



앗 이런 너무 상세하다. 예제수준. 

7번째 라인까지 보면 된다. 

검색된 내용들이 다 죠깅네.


자, 저 셋스크롤에 1초를 줬는데 1초 후에 죽는다는 건지 잘 모르겠다!!!!!!!!!!!!!! 누가 답을 알려나? 알려주시면 감사 ㅋㅋ



문제점 >> DATA LOSS....


전체 검색 되어야 하는 데이터 수와 페이징해서 끝페이지까지 넘겨보며 세어본 데이터 수가 일치하지  않는 경우가 있음 ㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋ 왜그런지 몰르겠음 ㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋ 어쩔!!! 왜 누락되고 난리얔ㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋ난 그냥 멘붕 ㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋ 어쩌라고 노에스큐엘앜ㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋ 몽고디비도 누락이 심하다고 하던데 ㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋ어쩌라고 몰라 난 ㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋ 어차피 빅데이터니까 나온것만 봐 ㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋ 무결성따위 개나줰ㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋㅋ는 나미침2








천성이 메모도 못하고 정리도 못하는데

블로그 글 쓰기로 결심하고 만 3년이 흐른 이 시점.........................

처음 놀리는 손꼬락질... 갠춘하네... ms키보드 버리고 기계식 살까봐 호호호 블로그 하려면 30만원 정도는 써 줘야죠 호호호

는 나 또 미침....3............


재밌어서 다행이네 ㅎㅎ

이제 에러 해결법도 조금씩 포스팅 하고.. 새로 알게 된 개념들도 차곡차곡 정리 해 보아야 겠다.

야근도 자동으로 되고 좋네 ^^

할일 없는데 웹서핑 하는거 싫어서 맨날 칼퇴해서 좀 눈치보였었는데 ㅎㅎㅎㅎㅎㅎㅎㅎㅎㅎㅎㅎㅎㅎㅎㅎㅎㅎㅎㅎㅎ

나님 나이스샷~~