Mapping 이란?
Mapping 이란 문서의 구조를 나타내는 정보라고 할 수 있다.
ES 에서와 RDB 에서와 사용하는 단어는 아래와 같이 대응된다고 볼 수 있다.
Elasticsearch | RDBMS |
Index | database |
mapping | schema |
document | row |
Elasticsearch를 스키마리스라고 해서 스키마가 없는 게 아니고 미리 정의하지 않아도 되는 것이다.
Mapping 은 크게 동적 매핑(Dynamic Mapping)과 정적 매핑(Static Mapping)으로 나뉘게 된다.
mapping 종류 | 정의 |
동적 매핑 (Dynamic Mapping) | 처음 색인되는 문서를 바탕으로 매핑 정보를 Elasticsearch가 동적(자동)으로 생성한다. |
정적 매핑 (Static Mapping) | RDBMS 와 비슷하게 문서의 매핑정보를 미리 정의해준다. |
동적 매핑 (Dynamic Mapping)
동적 매핑을 사용하면 어떤 문서가 색인될지 스키마를 미리 정의하지 않아도 된다.
측 처음 색인되는 문서를 바탕으로 ES가 매핑정보를 자동으로 구성한다.
ES에서는 스키마 구성 없이 아래와 같이 데이터를 바로 색인 할 수 있다.
POST movie/_doc
{
"genre": "science_fiction",
"name": "inter stellar",
"distributor": "PARAMOUNT",
"score" : 9.2
}
mapping 정보를 보려면 아래와 같은 커맨드를 실행해준다.
GET movie/_mapping
mapping 정보를 보면 ES 가 자체적으로 문자열 값이 들어오면 text type을 지정해 줬고
숫자형 타입이 들어오면 float type을 지정해 줬다.
매핑 정보가 생성된 후에는 타입이 맞지 않을 경우
파싱 에러가 발생한다.
아래와 같이 이미 score 필드에는 float 가 할당이 되었는데,
문자열 값을 넣어주면 파싱 에러가 발생한다.
POST movie/_doc
{
"genre": "science_fiction",
"name": "inter stellar2",
"distributor": "PARAMOUNT",
"score" : "test"
}
정적 매핑 (Static Mapping)
정적매핑이란 어떤 문서가 색인될지 스키마를 미리 정의하는 방식이다.
즉 index에 데이터를 색인하기 이전에
매핑정보를 미리 넣어주는 것이다.
PUT /movie
{
"index": {
"number_of_shards" : 3,
"number_of_replicas" : 1
},
"mappings": {
"properties": {
"genre": {
"type": "text"
},
"name": {
"type": "text"
},
"distributor": {
"type": "text"
},
"score": {
"type": "double"
}
}
}
}
그럼 RDBMS와 같이 이미 mapping 해둔 필드만 사용할 수 있을까?
정답은 "아니오" 다.
아래를 보자.
POST movie/_doc
{
"genre": "science_fiction",
"name": "inter stellar2",
"distributor": "PARAMOUNT",
"score" : 9.2,
"price" : 10000
}
분명 정적 매핑으로 지정해 줄 때에는 price라는 필드는 정의해주지 않았다.
하지만, 해당 값이 문제없이 색인되는 모습을 볼 수 있다.
GET /movie/_mapping
즉 새로운 price 라는 필드는 동적으로 매핑된 것이다.
이처럼 Elasticsearch는 정적매핑과 동적매핑을 동시에 수행할 수 있다.
정적 매핑 (Static Mapping)을 사용하는 이유
그럼 굳이 왜 정적매핑이 필요할까? 답은 간단하다.
위에서 동적매핑으로 색인할 때 9.2라는 숫자가 자동으로 float type 이 지정된 걸 볼 수 있다.
float type과 int type, double 타입은 모두 min, max value 가 다르다.
만약에 float type 이 허용하는 값보다 큰 값을 할당해야 하는 필드라면
동적 매핑을 적용한다면, 특정 값이 들어갈 수 없는 상황이 발생한다.
즉, 특정 필드가 임계치에 의존적이거나 서비스 성격에 의해서 특정 type을 가져야 한다면,
미리 타입을 정의해야 한다.
또한 불필요한 색인의 발생을 막기 위해 정적 매핑을 사용한다.
예를 들어 동적매핑으로 문자열필드를 생성하면
자동으로 keyword 타입이 할당되게 되는데,
이는 불필요한 색인이 발생하는 예라고 볼 수 있다.