Blog

2014.08.19 - 번역 - Optimizing Elasticsearch Searches ...

drscg 2019. 1. 6. 17:00

UPDATE: This article refers to our hosted Elasticsearch offering by an older name, Found. Please note that Found is now known as Elastic Cloud.

이 게시물은 기존에 Found라는 이름으로 제공된 Elasticsearch 서비스에 관한 것이다. Found은 이제 Elasticsearch Cloud로 알려져 있다.

Simple Suggestions for Speedier Searches

Elasticsearch can query, filter and aggregate in many ways. Often there are several ways to solve the same problem – and possibly with very different performance characteristics. This article will cover some important optimizations that can buy you a lot of performance.

Elasticsearch는 다양한 방식으로 query, filter, aggregation이 가능하다. 동일한 문제를 해결하는 방법에는 다양한 방법이 있고 성능 특성이 매우 다를 수 있다. 이 게시물에서는 성능을 크게 향상시킬수 있는 몇 가지 중요한 최적화 방법을 설명한다.

Find a Friend in Filters

Understanding how filters work is essential to making searches faster. A lot of search optimization is really about how to use filters, where to place them and when to (not) cache them.

filter가 동작하는 방식을 이해하면 검색이 더 빨라진다. 많은 검색 최적화는 실제로 filter를 사용하는 방법과 filter의 위치 그리고 filter를 언제 cache하는가이다.

Take this search, for example:

다음 검색 예제를 보자

query:
    bool:
        must:
            - term:
                tag: "elasticsearch"
            - multi_match:
                query: "query tuning"
                fields: ["title^5", "body"]

Elasticsearch will search for documents that are tagged with elasticsearch and that contain query tuning, preferably in the title. However, as all resulting documents are required to contain elasticsearch, the tag query has no impact on the scoring – the tag query acts as a filter.

Elasticsearch는 elasticsearch로 tag가 지정되고,  query tunnung이 포함된 document를 검색한다. (title이 선호된다). 그러나 모든 결과 document가 elasticsearch를 포함해야 하므로, tag query는 score에 영향을 미치지 않는다. tag query는 filter로 동작한다.

This is the key property of filters: the result will be the same for all searches, hence the result of a filter can be cached and reused for subsequent searches. Caching them is quite cheap, as you can store them as a compact bitmap. When you search with filters that have been cached, you are essentially manipulating in-memory bitmaps - which is just about as fast as it can possibly get.

이것이 filter의 주요 속성이다. 모든 검색에 대해 결과가 동일하기 때문에, 이후 검색에 대해 filter의 결과를 cache하고 재사용할 수 있다. 작은 bitmap으로 저장할 수 있으므로, caching은 매우 저렴하다. cache된 filter를 가지고 검색할 경우, 본질적으로 가능한 한 빠른 속도로 memory 내 bitmap을 조작하는 것이 된다.

A rule of thumb is to use filters when you can and queries when you must: when you need the actual scoring from the queries.

일반적으로, 가능한 한 filter를 사용하고, query를 통해 실제 score가 필요한 경우, 즉 필요한 경우에만 query를 사용한다.

Filter First

Having realized that we want to use a filter instead of a query, a common rewrite is something like this:

query 대신 filter를 사용하려는 경우, 일반적으로 다음과 같이 재작성한다.

query:
    multi_match:
       query: "query tuning"
      fields: ["title^5", "body"]
# Make it a filter, because filters are faaast. 
filter: # renamed to post_filter in 1.0
    - term:
       tag: "elasticsearch"
# But wait. This is wrong! Explanation follows.

This is one of the most common errors I see, and probably the reason why the top-level filter was renamed to post_filter in version 1.0, to emphasize that it is a filter that happens after (post) the query phase. To understand why this change may actually be for the worse, we’ll first have a look at the various places you can place a filter in a search.

이것은 가장 일반적인 오류 중 하나인데, 아마도 query 절 이후에 발생하는 filter라는 것을 강조하기 위해, 버전 1.0에서, 최상위 수준 filterpost_filter로 이름이 변경된 이유이다. 이러한 변경이 더 나쁜 경우에 적용되는 이유를 이해하기 위해, 먼저 검색에서 filter를 배치할 수 있는 다양한 위치에 대해 살펴보겠다.

High Level View of Filter Locations

Filters can appear in a filtered query, in filter aggregations, and in post filters. Filters are also useful for e.g. scoring in function score queries, but in that context they do not reduce the document set.

filter는 filtered query, filter aggregations, post filters에 나타날 수 있다. 또한 filter는, 예를 들어, function score query에서 score 계산에 유용하다. 그러나, 해당 context에서는 document 집합을 줄이지는 않는다.

The filtering that happens in the filtered query – in the top of the figure – is applied to everything. Aggregations as well as hits are affected by the filtering. This is not true of filtering that happens in the post_filter. Its entire purpose is to have a filter that does not affect aggregations.

그림 상단의 filtered query에서 발생하는 filtering은 모든 것에 적용된다. aggregation 및 hit는 filtering의 영향을 받는다. 이것은 post_filter에서 일어나는 filtering에는 해당되지 않는다. 그것의 완전한 목적은 aggregation에 영향을 미치지 않는 filter를 갖는 것이다.

In the (suboptimal) rewrite that we did above, we moved the tag query component into a post_filter. The outcome of this is that all documents matching the "query-tuning" query will be scored, and then the filter is applied. While we have gained cacheability of the tag filter, we have potentially increased the cost of scoring significantly. Post filters are useful when you need aggregations to be unfiltered, but hits to be filtered. You should not be using post_filter (or its deprecated top-level synonym filter) if you do not have facets or aggregations.

위에서 수행한 (차선의) 재작성에서, tag query 요소를 post_filter로 옮겼다. 이 결과는 "query tuning" query와 일치하는 모든 document에 대해 score를 계산하고, 그 다음에 filter가 적용된다는 것이다. tag filter가 cache될 수 있지만, 잠재적으로 score 계산 비용이 크게 증가되었다.post filter는 filtering되지 않은 aggregation이 필요하지만, hit는 filtering될 경우 유용하다. facet나 aggregation이 없는 경우에는, post_filter(또는 deprecate된 최상위 동의어 filter)를 사용하지 않아야 한다.

Instead, this query should be rewritten to a filtered-query, like this:

이 query는 아래처럼, filtered-query로 재작성되어야 한다.

query:
   filtered:
       query:
              multi_match:
              query: "query tuning"
              fields: ["title^5", "body"]
       filter:
           term:
               tag: "elasticsearch"

The filtered-query is smart enough to apply filters before queries, which reduces the search space before expensive scoring is performed.

filtered-query는 query 전에 filter를 적용 할만큼, 충분히 스마트하기 때문에, 비용이 많이 소모되는 score 계산을 수행하기 전에, 검색 범위를 줄인다.

Use a filter
Place filters in the right place. (Probably in a filtered-query!)

filter를 사용하자. filter를 올바른 위치에 배치하자. (filtered-query에)

Combining Filters

Elasticsearch has several ways to combine filters: andornot, and … bool.

Elasticsearch는 다양한 방법으로 filter를 조합한다, and, or, not 그리고 bool

You should probably always use bool and not and or or. For more detailed reasoning for this, see Zachary Tong’s post all about elasticsearch filter bitsets. The gist is that most filters can be cached, while some filters (e.g. geo_distance or script) need to work document-by-document anyway. Therefore, you’ll want cached (and therefore cheap) filters to be applied before the expensive ones.

항상 and나 or가 아닌 bool을 사용해야 한다. 이에 대한 더 자세한 이유는 Zachary Tong의 게시물, elasticsearch filter bitset에 대한 모든 것을 참조하자. 요지는 대부분의 filter는 cache될 수 있지만, 일부  filter(예: geo_distance 또는 script)는 document별로 작업해야 한다는 것이다. 따라서, cache된 (따라서 저렴한) filter를 비용이 많이 드는 것 앞에 적용해야 한다.

These subtle differences have, for the most part, been worked into the bool filter so you no longer have to worry about them, but it is always a good idea to test anyway!

대부분의 경우에서, 이 미묘한 차이점은 bool filter에 적용되어, 더 이상 걱정할 필요가 없지만, 항상 테스트하는 것이 좋다.

That said, you still need to think about which order you filter in. You want the more selective filters to run first. Say you filter on type: book and tag: elasticsearch. If you have 30 million documents, 10 million of type book and only 10 tagged Elasticsearch, you’ll want to apply the tag filter first. It reduces the number of documents much more than the book filter does.

그렇기는 하지만, 어떤 순서로 filtering할지 고려해야 한다. 보다 선별적인 filter를 먼저 실행하는 것이 좋다. type: book 그리고 tag: elasticsearch로 filtering한다고 가정해 보자. 3천만 개의 document, 1천만 권의 책과 Elasticsearch로 tage된 것이 10 개가 있다면, tag filter를 먼저 적용해야 한다. 그것은 book filter가 하는 것보다 훨씬 많은 document의 수를 줄인다.

Combine filters with bool. bool로 filter를 조합하자.
Order filters by their selectivity. 선별력있는 filter 순으로

Cache Granularity and Acceleration Filters

The cacheability of filters is an important reason why they can be so fast. Not all filters can (sensibly) be cached, however. Consider a user with a smartphone at location x wanting to see nearby events occurring within the next hour. These two filters (location and time) would be highly specific to that user and to that exact time. It is unlikely that those filters will be reused, so it makes no sense to cache them.

filter가 cache되는 것은 filter가 매우 빠를 수 있는 중요한 이유이다. 그러나 모든 filter가 cache될 수 있는 것은 아니다. 위치 x에 있는 스마트폰 사용자가 다음 한 시간 내에 발생하는 근처의 이벤트를 보고 싶어 한다고 가정해 보자. 이들 두 filter(위치 및 시간)는 해당 사용자와 그 정확한 시간에 매우 한정적이다. 이러한 filter는 재사용될 가능성이 낮으므로, cache할 필요가 없다.

In such scenarios it can be useful to add auxiliary filters that are less specific, but cacheable. For example, while it is unlikely that finding documents within 5 kilometers of the specific location (63.4305083, 10.3951494) (in downtown Trondheim) will be reused, any similar distance filter for users in the same area will fall within the much wider grid defined by the geohash u5r. (This is not necessarily true near meridians or the equator). Another possibility would be to filter on city or county, for instance.

이러한 시나리오에서는, 덜 한정적이지만 cache할 수 있는 보조 filter를 추가하는 것이 유용할 수 있다. 예를 들어, 특정 위치(63.4305083, 10.3951494) (트론헤임-Trodheim 시내)에서 5km 이내의 document를 찾는 것은 재사용될 가능성이 낮지만, 동일한 지역의 사용자에 대한 유사 거리 filter는 geohash u5r(이것은 자오선 또는 적도 근처에서 반드시 그런 것은 아니다.)에 의해 정의된 훨씬 더 넓은 그리드에 속하게 된다. 또 다른 가능성은 예를 들어 도시 또는 자치주를 filtering하는 것이다.

Similarly, Elasticsearch does not cache any time filter using the now keyword in date math unless a rounding is specified. If you want to find all documents with timestamp >= 'now-1h', the filter will not be cached, because now is (hopefully) continuously moving. However, any document that less than an hour old is also necessarily less than one day old. Thus, you can have a filter like timestamp >= 'now/1d' AND timestamp >= 'now - 1h'. The timestamp >= 'now/1d' component, which should be applied first, can be cached because it is rounded to the current day. It is not exactly what we want, but it reduces the number of documents needed to be considered for the now-1h filter.

마찬가지로, Elasticsearch는 반올림을 지정하지 않으면,  date 연산에서 now keyword를 사용하는 time filter를 cache하지 않는다. timestamp >= 'now-1h' 인 모든 document를 찾는다면, filter는 cache되지 않는다. 왜냐하면, now는  (아마도) 지속적으로 변하기 때문이다. 그러나 1시간 미만의 모든 document는 반드시 1일 미만이다. 따라서 timestamp >= 'now/1d' AND timestamp >= 'now-1h' 와 같은 필터를 가질 수 있다. timestamp >= 'now/1d' 요소는 먼저 적용되어야 하며, 현재 날짜로 반올림되기 때문에, cache될 수 있다. 이것은 정확히 우리가 원하는 것은 아니지만, now-1h filter에서 고려해야 할 document 수를 줄인다.

In other words, filters that seem redundant can speed up things a lot, because they can be cached and reduce the search space for filters that cannot. When you face a challenge with a filter that is not being cached, you should consider if you can accelerate the filter enough in other ways.

즉, 중복된 것처럼 보이는 filter는, cache될 수 있고 cache할 수 없는 filter의 검색 공간을 줄일 수 있기 때문에, 속도를 크게 높일 수 있다. caching되지 않는 filter로 문제가 발생하면, 다른 방식으로 filter를 충분히 가속화할 수 있는지 고려해야 한다.

Mind which filters can(not) be cached.
Consider cacheable “accelerator” filters to reduce the burden of more expensive filters.
filter의 cache 가능 여부에 주의하자.
보다 비싼 filter의 부담을 줄이기 위해, cache가 가능한 "가속기" filter를 고려하자.

Filter Aggregations

As for queries and filters, there can be multiple ways of achieving the same aggregation. The filter aggregation (or facet) is incredibly useful, also when a terms or range aggregation could do the same.

query 및 filter의 경우, 동일한 aggregation을 수행하는 여러 가지 방법이 있을 수 있다. termsrange aggregation이 동일하게 동작할 수 있는 경우에도, filter aggregation(또는 facet)은 매우 유용하다.

Assume you have a web site with three different sections, and you want to show how many hits there are in each section. The most obvious approach would be to do a terms aggregation on the section field to get an aggregation that says e.g. {general: 123, news: 40, blog: 12}. To limit the search to a section, you would use a term filter like {term: {section: news}}. You might even be using these filters for function scores as well. A cached filter can be reused in many settings. Since you are already paying for the filters’ memory, it can make sense to replace the terms aggregation with a filters aggregation.

3개의 다른 section이 있는 웹 사이트가 있고, 각 section의 hit 수를 표시하고 싶다고 가정해 보자. 가장 확실한 방법은 section field에서 terms aggregation을 수행하여, 예를 들어 {general: 123, news: 40, blog: 12} 라는 aggregation을 얻는 것이다. section 검색을 제한하려면,  {term: {section: news}} 와 같은 term filter를 사용하자. 이 필터를 function score에도 사용할 수 있다. cache된 filter는 여러 설정에서 재사용할 수 있다. 이미 filter에 메모리 비용을 지불하고 있으므로, terms aggregation을 filters aggregation으로 바꾸는 것이 좋다.

A terms aggregation will need the entire section field in memory, then count and bucket for every request. AND-ing together a few bitmaps is probably a lot faster. This can work well for low-cardinality fields: I am not suggesting replacing all your term aggregations with a huge number of filters!

terms aggregation은 memory의 전체 section field가 필요하며, 모든 request에 대해 count와 bucket을 생성한다. 몇 개의 bitmap을 함께 하면, 아마도 훨씬 더 빨라질 것이다. 이는 낮은 cardinality field에서 잘 동작할 수 있다. 모든 term aggregation을 엄청난 수의 filter로 바꾸라고 제안하는 것은 아니다.

The same can apply to range aggregations.

range aggregation에 동일하게 적용할 수 있다.

Consider whether your aggregation can be implemented with a filter aggregation instead.
filter aggregation 대신 구현할 수 있는 aggregation을 고려하자.

Aggregation Abundance

Aggregations are powerful, but they can easily dominate the performance cost of your searches – and consume a great deal of memory.

aggregation은 강력하지만, 쉽게 검색의 성능 비용을 좔루할 수 있으며, 많은 memory를 소비한다.

Therefore, it can be worthwhile to minimize the number of aggregations you do. If you have a search results page where not all facets are visible, consider lazy loading the aggregation when the user enables the facet.

따라서, aggregation의 수를 최소화하는 것이 좋다. 모든 facet이 보이지 않는 검색 결과 페이지가 있다면, aggregation을 지연(lazy) load하는 것을 고려하자.

The same holds for pagination. When a user requests a second page of hits, the facets in the navigation will remain the same – after all, they’re aggregates. Therefore, you can skip the aggregations and just ask for the hits. This can make your user interface more stateful and complex, of course, but you can save a lot of CPU-cycles at your backend.

page navigation도 마찬가지이다. 사용자가 hits의 2번째 page를 request하면, navigation의 facet은 동일하게 유지된다. 결국, aggregation된다. 따라서, aggregation을 생략하고, hits만 요청할 수 있다. 이는 user interface를 더 안정적이고 복잡하게 만들 수 있지만, 백엔드에서 많은 CPU 사이클을 절약할 수 있다.

Aggregations are expensive. Reuse cached results or skip them entirely if possible.
aggregation은 비용이 많이 든다. 가능하다면 cache된 결과를 재사용하거나 그들 전체를 생략하자.

Scoring and Scrolling

We mentioned above that you should filter when you can and query when you need scoring. Elasticsearch has really powerful scoring capabilities, and you can express quite intricate relevancy rules.

가능한 한 filter를 사용하고, score 계산이 필요한 경우에 query를 사용해야 한다고 위에서 언급하였다. Elasticsearch는 매우 강력한 score 계산 능력을 가지고 있고, 매우 복잡한 관련성 규칙을 표현할 수 있다.

Scoring happens in two phases. First, there is the query phase, and then you may have rescorers that apply more detailed and expensive scoring rules to documents that survive the first round(s). Conceptually, they are a bit like the accelerator filters - we reduce the space where more computationally expensive scoring happens.

score 계산은 2 단계로 이루어진다. 첫번째는 query이며, 첫번째에서 생존한 document에 보다 상세하고 값 비싼 score 계산 규칙을 적용하는 rescorer가 있을 수 있다. 개념적으로 이는 accelerator filter와 약간 비슷하다. 계산적으로 비용이 많이 드는 score 계산이 발생하는 곳을 줄인다.

Where Scoring Happens

Elasticsearch works hard to do as little as possible to find the top n results. Calculating the scores for hits we are not going to return anyway is just wasteful. But if you want to do really deep pagination and want e.g. hits 10 000 000 – 10 000 010, it will require a lot of expensive scoring just to show those 10 hits. It is not that uncommon to have a “Last” link in a search results paginator, which will put you in this situation. This is quite questionable UX-wise as well: “Hey, check out the worst results!”

Elasticsearch는가능한 한 작은 작업으로 상위 n개의 결과를 찾기 위해 노력한다. 어차피 return되지 않을 hits에 대한 score를 계산하는 것은 낭비일 뿐이다. 하지만, 깊은(deep) pageination을 하고 싶다면, 예를 들어 10,000,000 ~ 10,000,010을 원한다면, 단지 그들 10개의 결과를 보여주기 위해 비용이 많이 드는 많은 score 계산이 필요하다. 검색 결과 page navigator에 "Last" link를 가지는 경우가 드문 것은 아니며, 이렇게 하면 이런 상황에 빠지게 된다. This is quite questionable UX-wise as well: “Hey, check out the worst results!”

If you really do have needs to scroll through huge result sets, such as when reindexing, use the scroll and scanAPIs.

reindex를 할 경우처럼, 큰 결과 집합을 scroll해야 한다면, scroll and scanAPIs를 사용하자.

Index vs. Search Time

When you work with Elasticsearch, it is important to get your text analysis and mappings right to support the searches you need to do. For the time being, changing mappings and reindexing can be quite painful.

Elasticsearch를 사용할 때에는, 해야 할 검색을 지원하는 text analysis와 mapping을 올바르게 하는 것이 중요하다. 당분간은 mapping을 변경하고 reindex하는 것이 꽤 힘들 수 있다.

It is not unusual to see suboptimal searches used to work around the fact that the original mappings were not designed to support that kind of search. A common example is searching for substrings. If you have indexed "AbstractPluginFactory" as "abstractpluginfactory" (the default analyzer will lowercase terms), you cannot search for "plugin". Elasticsearch has capabilities to let you wrap wildcards around your search, i.e. "*plugin*". Do not do that.

원래의 mapping이 특정 종류의 검색을 지원하도록 설계되지 않았다는 사실을 해결하기 위하여 사용되는 차선의 검색을 보는 것은 드문 일이 아니다. 흔한 예는 부분 문자열 검색이다. "AbstractPluginFactory"를as "abstractpluginfactory"로 index했다면, "plugin"를 검색할 수 없다. Elasticsearch는 검색 시에 wildcard를 사용할 수 있는 기능(예: "*plugin*")이 있다. 그렇게 하지 말자.

Instead, index properly. In this case, you could use an ngram-analyzer, or a CamelCase-tokenizer.

대신, 적절하게 index하자. 이런 경우 ngram-analyzer나 CamelCase-tojenizer를 사용할 수 있다.

Things to Avoid

If you search the documentation for optimization, you will find the index optimization API. Unless you have an index that is no longer changing, you should probably avoid it. It’s for merging segments in an index, which you can learn more about in our article on Elasticsearch from the Bottom Up. If you run it on an index with lots of indexing activity, you will hurt performance big-time.

최적화에 대한 참조 문서를 검색해 보면, index optimization API를 찾을 수 있다. 더 이상 변경되는 않는 index가 없다면, 이를 피하는 것이 좋다. 그것은 index에서 segment를 병합하는 것인데,  Elasticsearch from the Bottom Up 이라는 게시물에서 자세히 볼 수 있다. index 동작이 많은 index에서 이를 실행하면, 성능이 크게 저하된다.

You probably should not _optimize

_optimize를 하지 않는 것이 좋다.

As mentioned earlier, there are filters that can be cached, and there are filters that are not cacheable. There is a _cache option you can put on a filter to force it to be cached. Be careful with it. Enabling it at will can reduceperformance: it can cause other filters to be expunged from the cache, and the cost of running the filter the first time can increase since it must now run across all documents.

앞에서 이야기 했듯이, cache될 수 있는 filter가 있고 cache될 수 없는 filter가 있다. filter를 강제로 cache에 넣을 수 있는 _cache option이 있다. 그것을 활성화하면 성능이 저하될 수 있다. 그것으로 인해 cache에서 다른 filter가 제거될 수 있고, 모든 document에서 실행되어야 하므로, filter가 처음으로 실행될 때 비용이 증가할 수 있다.

Enabling _cache on all filters does not magically make things faster.
모든 filter에서 _cache를 활성화해도 마술처럼 빨라지지는 않는다.

Occasionally, I see an over-complicated search where the goal is to do as much as possible in as few search requests as possible. These tend to have filters as late as possible, completely in contrary to the advise in Filter First. Do not be afraid to use multiple search requests to satisfy your information need. The multi-search API lets you send a batch of search requests.

가끔, 가능한 한 적은 검색 request로 가능한 한 많은 작업을 하도록 한 곳에서, 지나치게 복잡한 검색을 볼 수 있다. 이들은 Filter First라는 권고와는 완전히 반대로, 가능한 한 나중에 filter를 가지는 경향이 있다. 필요한 정보를 위해 다양한 검색 request를 사용하는 것을 두려워하지 말자. multi-search API를 사용하면 검색 request를 일괄적으로 전송할 수 있다.

Do not shoehorn everything into a single search request.
모든 것을 단 한번의 검색 request에 맡기지 말자

Whenever you use a script for something, consider whether there are other approaches to the same problem. When you need to resort to them, make sure you are careful with how you access document fields. If you use _source or _fields you will quickly kill performance. They access the stored fields data structure, which is intended to be used when accessing the resulting hits, not when processing millions of documents. If you use doc['field_name'], the field data APIs will be used.

scipt를 사용할 경우, 동일한 문제에 대한 다른 접근 방법이 있는지 교려하자. script를 사용해야 한다면, document field에 access하는 방법에 주의해야 한다. _source나 _fields를 사용하면, 빠르게 성능이 감소한다. 이들은 stored filed라는 data 구조를 access하는데, 이 data 구조는 수백만개의 document를 처리하는 경우가 아니라 결과 hits를 access할 때 사용된다. doc['field_name']를 사용한다면, field data API가 사용된다.

As covered in Index vs. Search Time, some things are better to do when indexing than when searching. If you have indexed a timestamp and need to filter by weekday, you could use a script. However, it would probably be better to just index the weekday. You can use a transform-script to do that, which is okay.

Index vs. Search Time에서 이야기 했듯이, 몇 가지 작업은 검색시보다 index시에 하는 것이 더 효과적이다. timestamp를 index했고, 요일별로 filtering해야 한다면, script를 사용할 수 있다. 그러나 요일을 index하는 것이 더 효과적일 것이다. transform-script를 사용하여 이 작업을 수행할 수 있다.

Avoid scripts in searches when you can.
가능한 한 검색시에 script 사용을 피하자.

Optimize Maturely

Optimizations do not always apply. Test and confirm. Also, is it really your bottleneck?
최적화는 항상 적용되는 것은 아니다. 테스트하고 확인하자. 또한 그것이 병목현상인지?

While we have covered several things that can improve or hurt search performance, it is important to know where your bottlenecks are.

검색 성능을 향상시키거나 손상시킬 수 있는 몇 가지 사항을 살펴보았지만, 병목현상이 어디인지를 파악하는 것이 중요하다.

There is no point in trying to shave milliseconds off your filters if you spend a majority of the time establishing SSL connections because you use a poor client library.

client library를 제대로 사용하지 않아, SSL 연결을 생성하는데 대부분의 시간을 소비하고 있다면, filter가 수 milliseconds를 절약해도 의미가 없다.

Changing the way you cache filters can improve that one search you are working on right now, but it can also possibly cause higher filter cache churn, negatively impacting overall performance. It is important to test things both in isolation as well as seeing its effect in the bigger picture.

filter를 cache라는 방법을 변경하면, 지금 동작중인 검색 하나는 성능이 향상될 수 있지만, filter cache 변환이 증가하여, 전체 성능에 부정적인 영향을 줄 수도 있다. 

There are few rules that are absolute and without exceptions when it comes to optimizing searches, so proceed judiciously. 따로 테스트하는 것뿐만 아니로 더 큰 그림에서 그것의 효과를 보는 것도 중요하다.

Further Reading

This article has focused on how you can improve your searches. It has not touched sharding and partitioning strategies, nor production considerations, such as the importance of having sufficient memory. These issues and more are covered in various other articles, which may be of interest:

이 게시물은 검색 성능을 향상시키는 방법에 대해 중점을 둔다. sharding과 partitioning 전략이나, 충분한 memory를 갖는 것의 중요성 같은 고려사항은 다루지 않았다. 이들 issue와 그 외의 것들은 아래 게시물에서 다루고 있다.

원문 : Optimizing Elasticsearch Searches