본문으로 바로가기

만약 MySQL과 같은 SQL이었다면 검색을 위해 스핑크스나 엘라스틱서치를 사용하는 것이 필수였을 것입니다. 

mongoDB도 마찬가지로 고급 검색 시스템을 적용하기 위해서는 검색엔진을 사용해야하는 것이 필수지만 간단한 기능을 구현하는 앱에서는 별다른 외부 서비스없이 text 인덱스만을 활용해서 검색 기능을 구현할 수 있습니다.

 

(오타 수정, 유의어 검색 등의 기술은 외부 서비스를 사용해야 합니다)

 

과거 인덱스를 다룬 포스트(https://darrengwon.tistory.com/671?category=870801)에서 text 인덱스를 살펴본 바가 있습니다. 

 

text 인덱스
https://docs.mongodb.com/manual/core/index-text/

문자열 검색에 최적화된 인덱스입니다. 
예를 들어 "해외 최신 영화"를 검색한다고 가정한다면, 유저는 "영화"라는 단어만 입력하지 문자열 전체를 '정확'하게 입력하는 경우는 별로 없습니다. 이러한 검색 기능을 도와주는 인덱스로 text 인덱스가 있습니다.

텍스트 인덱스는 하나의 컬렉션에 단 하나만 만들 수 있습니다.

 

text 인덱스의 독특한 점은, 검색 기능에 필요한 형태소 분석을 알아서 처리해준다는 것입니다. (검색 엔진에는 형태소 분석과 NLP가 동원됩니다. 검색 엔진만 따로 연구하기도 하니 상당히 어려운 분야임을 알 수 있습니다.)

 

일반적으로 검색 엔진은 다음과 같은 방식으로 작동한다고 합니다.

 

  1. 이용자가 넣은 키워드 혹은 문장을 읽어들인다.
  2. 문장이라면 키워드를 뽑아서 나눈다 (제일 가까운 병원 => '제일', '가까운', '병원')
  3. 데이터베이스에서 해당 키워드와 문장을 이용하여 검색을 돌린다.
  4. 해당 키워드 혹은 문장이 어디에 얼마나 포함되어 있는지에 따라 가중치를 적용하여 각 검색 결과에 점수를 메긴다.
  5. 점수에 따라 데이터를 정렬하여 결과 값을 이용자에게 보여준다.

여기에서 형태소 분석이 개입할 부분은 2번입니다. mongoDB의 경우 run을 검색하면 run 동사의 과거형 등 변형까지도 고려해 결과를 반환합니다. 아쉽게도 한국어는 이를 지원하지 않습니다. (어디서 듣기로는 유럽권 언어도 이를 지원한다고 하는데, 한국어도 지원이 되었으면 하는 바람입니다.)

 

 

섹션별로 찾은 후 contents를 검색하기 위해 다음과 같이 인덱스를 설정했습니다.

postSchema.index({ section: 1, contents: "text" });

 

shell에서 다음과 같이 인덱스를 찾아보니 등록이 되었군요

db.getCollection('posts').getIndexes()


// 인덱스 출력의 일부
        "v" : 2,
        "key" : {
            "section" : 1,
            "_fts" : "text",
            "_ftsx" : 1
        },
        "name" : "section_1_contents_text",
        "ns" : "KinoProject.posts",
        "background" : true,
        "weights" : {
            "contents" : 1
        },
        "default_language" : "english",
        "language_override" : "language",
        "textIndexVersion" : 3
    

 

 

 

이제 find 메서드로 해당하는 내용을 찾아내면 됩니다. 

 

 

 

참고한 글)

 

 

$text — MongoDB Manual

Text Score The $text operator assigns a score to each document that contains the search term in the indexed fields. The score represents the relevance of a document to a given text search query. The score can be part of a sort() method specification as wel

docs.mongodb.com

 

MongoDB 검색 기능 활용하기

어플리케이션을 만들다 보면, 검색 기능은 빠질 수 없는 기능 중 하나이다. 하지만 실제로 구글처럼 키워드나 문장을 넣어서 검색되는 기능을 구현하려면 매우 복잡해진다. 일반적으로 검색엔��

sy34.net

 


darren, dev blog
블로그 이미지 DarrenKwonDev 님의 블로그
VISITOR 오늘 / 전체