Elasticsearch는 HTTP를 통해 위와 같이 JSON에 access할 수 있는 REST API를 제공한다. Elasticsearch REST API에 대해 간단하게 살펴보고, 어떤 규약/규칙을 가지고 있는지 알아본다.
REST란?
REST(Representational State Transfer)란 자원(Resource)의 상태를 주고 받는 모든 것을 말하며, Protocol이나 표준이 아닌 Architecture 원칙을 말한다.REST 적용 방식은 다음과 같다
1) HTTP URI(Uniform Resource Identifier)를 통해 자원(Resource)를 명시하고,
2) HTTP Method를 통해 해당 자원(URI)에 대한 CRUD Operation을 적용한다.
.
HTTP Method
- POST : 데이터 생성(create)
- GET : 데이터 조회(get)
- PUT : 데이터 수정(update)
- DELETE : 데이터 삭제(delete)
REST API에 대한 자세한 내용은 아래 블로그 참조
https://khj93.tistory.com/entry/%EB%84%A4%ED%8A%B8%EC%9B%8C%ED%81%AC-REST-API%EB%9E%80-REST-RESTful%EC%9D%B4%EB%9E%80
Command Example
school
이라는 이름의 index 생성한다.
PUT school
정상 출력
{
"acknowledged" : true,
"shards_acknowledged" : true,
"index" : "school"
}
Command Example
school
이라는 index에 _doc
이란 type을 추가하고, 10
id를 가진 document를 추가한다.
POST school/_doc/10
{
"name":"Saint Paul School",
"description":"ICSE Afiliation",
"street":"Dawarka",
"city":"Delhi",
"state":"Delhi",
"zip":"110075",
"location":[28.5733056, 77.0122136],
"fees":5000,
"tags":["Good Faculty", "Great Sports"],
"rating":"4.5"
}
정상 출력
{
"_index" : "school",
"_type" : "_doc",
"_id" : "10",
"_version" : 1,
"result" : "created",
"_shards" : {
"total" : 2,
"successful" : 1,
"failed" : 0
},
"_seq_no" : 0,
"_primary_term" : 1
}
추가로 아래 데이터를 삽입한다.
POST school/_doc/16
{
"name":"Crescent School",
"description":"State Board Affiliation",
"street":"Tonk Road",
"city":"Jaipur",
"state":"RJ",
"zip":"176114",
"location":[26.8535922,75.7923988],
"fees":2500,
"tags":["Well equipped labs"],
"rating":"4.5"
}
API에서 주로 검색 및 기타 작업과 같은 대부분의 작업은 한 개 이상의 index를 위함이다. 따라서 사용자는 쿼리 한 번 실행에 여러 index나 모든 데이터를 검색할 수 있다. 여러 index를 검색하거나 모든 index를 검색하는 표기 방법은 다양하다. 그 표기 방법에 대해서는 다음과 같다.
콤마(,
)로 index 구분해서 여러 개의 index를 조회할 수 있다. 콤마(,
) 뒤에 space는 없어야 된다.
Command Exmaple
POST school,schools_gov/_search
정상 출력
{
"took" : 1,
"timed_out" : false,
"_shards" : {
"total" : 2,
"successful" : 2,
"skipped" : 0,
"failed" : 0
},
"hits" : {
"total" : {
"value" : 4,
"relation" : "eq"
},
"max_score" : 1.0,
"hits" : [
{
"_index" : "school",
"_type" : "_doc",
"_id" : "10",
"_score" : 1.0,
...
_all
키워드 사용_all
keyword를 사용하면 모든 index를 조회할 수 있다.
Command Example
POST /_all/_search
정상 출력
{
"took" : 347,
"timed_out" : false,
"_shards" : {
"total" : 60,
"successful" : 60,
"skipped" : 0,
"failed" : 0
},
"hits" : {
"total" : {
"value" : 10000,
"relation" : "gte"
},
"max_score" : 1.0,
"hits" : [
{
"_index" : ".kibana_1",
"_type" : "_doc",
...
Wildcards를 통해 여러 index를 조회할 수 있다.
Command Example
school
로 시작하는 모든 index를 조회한다.
POST /school*/_search
정상 출력
{
"took" : 0,
"timed_out" : false,
"_shards" : {
"total" : 2,
"successful" : 2,
"skipped" : 0,
"failed" : 0
},
"hits" : {
"total" : {
"value" : 4,
"relation" : "eq"
},
"max_score" : 1.0,
"hits" : [
{
"_index" : "school",
"_type" : "_doc",
"_id" : "10",
...
Command Example 2
school
로 시작하는 index를 조회하되, schools_gov
index는 검색하지 않는다.
POST /school*,-schools_gov/_search
정상 출력
위 example과 !!! 라인을 비교해보면 schools_gov
index에 대한 검색이 빠져 total 수가 줄어든 것을 확인 할 수 있다.
{
"took" : 0,
"timed_out" : false,
"_shards" : {
"total" : 1,
"successful" : 1,
"skipped" : 0,
"failed" : 0
},
"hits" : {
"total" : {
"value" : 2, !!!
"relation" : "eq"
},
"max_score" : 1.0,
"hits" : [
{
...
Elasticsearch는 <static_name{date_math_expr{date_format|time_zone}}>
포맷과 같은 날짜와 시간에 대한 index 검색 기능을 지원한다. 수학적 연산을 사용하면 특정 날짜나 날짜와 시간 범위에 대한 세부정보를 얻을 수 있도록 한다.
static_name
은 index 이름 중 변하는 부분인 날짜나 시간이 아닌 고정된 이름을 입력하는 부분이다.
예를 들면 아래와 같은 index가 있을 때 static_name
에 해당하는 부분은 accountdetail-
이다.
Expression | Resolves to
<accountdetail-{now-d}>
accountdetail-2015.12.29
<accountdetail-{now-M}>
accountdetail-2015.11.30
<accountdetail-{now{YYYY.MM}}>
accountdetail-2015.12
Comman Example
POST <covid*-{now-3d{dd.MM.YYYY|UTC}}>/_search
정상 출력
{
"took" : 5,
"timed_out" : false,
"_shards" : {
"total" : 1,
"successful" : 1,
"skipped" : 0,
"failed" : 0
},
"hits" : {
"total" : {
"value" : 10000,
"relation" : "gte"
},
"max_score" : 1.0,
"hits" : [
{
"_index" : "covid-19-all-08.06.2022",
"_type" : "_doc",
"_id" : "RT1LQoEB6GtmU4u6b-uq",
"_score" : 1.0,
"_source" : {
...
filter_path
파라미터(parameter)를 이용하면 원하는 field만 출력할 수 있다.
Command Example
school
로 시작하는 index들을 검색하되 출력 결과에서는 hits
아래의 total
field만 출력한다.
POST school*/_search?filter_path=hits.total
정상 출력
{
"hits" : {
"total" : {
"value" : 4,
"relation" : "eq"
}
}
}
API 사용시 파라미터로 줄 수 있는 유용한 옵션도 있다.
ignore_unavailable
조회한 URL 안에 현재 존재하지 않는 index가 포함되어 있을 경우 에러가 발생하거나 작동이 멈추는 것을 방지한다.
에러 Example
book_shops
라는 index는 존재하지 않는다.
POST /school*,book_shops/_search
에러 출력
book_shops
라는 index는 존재하지 않는다.
{
"error" : {
"root_cause" : [
{
"type" : "index_not_found_exception",
"reason" : "no such index [book_shops]",
"resource.type" : "index_or_alias",
"resource.id" : "book_shops",
"index_uuid" : "_na_",
"index" : "book_shops"
}
],
"type" : "index_not_found_exception",
"reason" : "no such index [book_shops]",
"resource.type" : "index_or_alias",
"resource.id" : "book_shops",
"index_uuid" : "_na_",
"index" : "book_shops"
},
"status" : 404
}
Command Example
파라미터 옵션으로 ignore_unavailable=true
를 준다.
POST /school*,book_shops/_search?ignore_unavailable=true
정상 출력
{
"took" : 0,
"timed_out" : false,
"_shards" : {
"total" : 2,
"successful" : 2,
"skipped" : 0,
"failed" : 0
},
"hits" : {
"total" : {
"value" : 4,
"relation" : "eq"
},
"max_score" : 1.0,
"hits" : [
{
"_index" : "school",
"_type" : "_doc",
"_id" : "10",
...
allow_no_indices
allow_no_indices=true
이면 Wildcards가 쓰인 URL에 해당하는 index가 없을 경우 에러를 방지한다.
Command Example
schools_pri
로 시작하는 index가 없을 때 아래와 같이 명령을 실행하면 에러가 발생하지 않는다.
POST /schools_pri*/_search?allow_no_indices=true
정상 출력
에러 대신 hits.total.value가 0이고, hits.hits에 빈 배열이 보인다.
{
"took" : 0,
"timed_out" : false,
"_shards" : {
"total" : 0,
"successful" : 0,
"skipped" : 0,
"failed" : 0
},
"hits" : {
"total" : {
"value" : 0,
"relation" : "eq"
},
"max_score" : 0.0,
"hits" : [ ]
}
}
pretty=true
로 파라미터를 주면 JSON 포맷을 보기 편하고 이쁘게 포맷팅해서 보여준다.
Command Example
POST /school/_search?pretty=true