Elasticsearch'te 'search-as-you-type' performansını edge n-gram ile nasıl optimize ederim?
Soru
E-ticaret arama çubuğunda kullanıcı her harf yazdığında Elasticsearch'te arama tetikleniyor; ürün sayısı 10M+. `Wildcard`/`Regexp` sorguları CPU'yu tepetaklak ediyor ve gecikme büyüyor. Aramayı milisaniyelere indirmek için Elasticsearch'te `Edge N-gram` tokenizer'ını ve index-time analizini nasıl kurgulamalıyım?
Cevap
Kısa cevap: wildcard/regexp’i bırak; işi sorgu zamanından index zamanına taşı — edge_ngram ile önekleri yazarken üret, autocomplete’in düz bir term lookup’a insin.
Asıl mesele şu: wildcard/regexp sorgu anında çalışan birer taramadır; inverted index’i verimli kullanamaz, her harfte 10M dokümanı süzmeye çalışır ve CPU’yu yakar. Çözüm sorguyu hızlandırmak değil, çalışmayı önceden yapmak.
- Maliyeti index zamanına kaydır.
edge_ngramtoken filter’ı, bir kelimeyi indexlerken tüm öneklerini (“a”, “ay”, “ayk”, “ayka”…) ayrı token olarak üretir. Kullanıcı “ayk” yazınca artık tarama yok; doğrudan “ayk” token’ı aranır — bu sıradan bir term lookup, milisaniyeler sürer. Anlık aramanın bütün hızı buradan gelir. - Index analyzer ile search analyzer’ı AYIR. Bu en sık yapılan hata.
edge_ngram’ı yalnızca index tarafında uygula (analyzer); arama tarafında standart bir analyzer kullan (search_analyzer). Sorguyu da ngram’larsan kullanıcının yazdığı her önek tekrar parçalanır, alakasız eşleşmeler (noise) ve şişmiş skorlar gelir. Önekleri index üretir, arama sadece eşleştirir. - Türkçe için
lowercase+asciifoldingekle. Custom analyzer’ında ngram’dan önce bu filtreleri koy: “Şişe” ile “sise”, “Ürün” ile “urun” eşleşsin. Kullanıcı aksansız yazsa bile sonucu bulur — Türkçe arama çubuğunda bu pazarlık konusu değil. - Index büyümesini ve gürültüyü sınırla.
min_gram/max_gram’ı dar tut (ör. 2-15); aksi halde index katlanarak şişer. Hangi alanların aranacağını sınırla, client’tadebounce(ör. 150 ms) ile her tuş vuruşunda istek atma. İsteğe bağlı kısayol: ES’insearch_as_you_typealan tipini kullan — bu kurulumu (edge ngram + shingle) senin yerine hazır yapar.
Sonuç: Ben olsam autocomplete’i ya custom edge_ngram analyzer’ı ile ya da hazır search_as_you_type alanıyla index zamanında kurardım; wildcard’ı otomatik tamamlama için asla kullanmazdım. Index analyzer’da ngram + lowercase + asciifolding, search analyzer’da standart eşleştirme, gram aralığını dar tut ve client’ta debounce ekle. İş bittiğinde 10M üründe arama, harf başına milisaniyeye iner.
Yorumlar
Yorum yapmak için GitHub hesabınızla giriş yapmanız yeterli. Yorumlar GitHub Discussions üzerinde saklanır.