Реализация AI-автодополнения поисковых запросов в мобильном приложении

TRUETECH занимается разработкой, поддержкой и обслуживанием мобильных приложений iOS, Android, PWA. Имеем большой опыт и экспертизу для публикации мобильных приложений в популярные маркеты Google Play, App Store, Amazon, AppGallery и другие.

Разработка и поддержка любых видов мобильных приложений:

Информационные и развлекательные мобильные приложения
Новостные приложения, игры, справочники, онлайн-каталоги, погодные, фитнес и здоровье, туристические, образовательные, социальные сети и мессенджеры, квиз, блоги и подкасты, форумы, агрегаторы
Мобильные приложения электронной коммерции
Интернет-магазины, B2B-приложения, маркетплейсы, онлайн-обменники, кэшбэк-сервисы, биржи, дропшиппинг-платформы, программы лояльности, доставка еды и товаров, платежные системы
Мобильные приложения для управления бизнес-процессами
CRM-системы, ERP-системы, управление проектами, инструменты для команды продаж, учет финансов, управление производством, логистика и доставка, управление персоналом, системы мониторинга данных
Мобильные приложения электронных услуг
Доски объявлений, онлайн-школы, онлайн-кинотеатры, платформы предоставления электронных услуг, платформы кешбека, видеохостинги, тематические порталы, платформы онлайн-бронирования и записи, платформы онлайн-торговли

Это лишь некоторые из типы мобильных приложений, с которыми мы работаем, и каждый из них может иметь свои специфические особенности и функциональность, а также быть адаптированным под конкретные потребности и цели клиента.

Услуги, которые мы предлагаем
Показано 1 из 1Все 1735 услуг
Реализация AI-автодополнения поисковых запросов в мобильном приложении
Средний
~3-5 дней
Часто задаваемые вопросы

Наши компетенции:

Этапы разработки

Последние работы

  • image_mobile-applications_feedme_467_0.webp
    Разработка мобильного приложения для компании FEEDME
    792
  • image_mobile-applications_xoomer_471_0.webp
    Разработка мобильного приложения для компании XOOMER
    671
  • image_mobile-applications_rhl_428_0.webp
    Разработка мобильного приложения для компании RHL
    1097
  • image_mobile-applications_zippy_411_0.webp
    Разработка мобильного приложения для компании ZIPPY
    969
  • image_mobile-applications_affhome_429_0.webp
    Разработка мобильного приложения для компании Affhome
    914
  • image_mobile-applications_flavors_409_0.webp
    Разработка мобильного приложения для компании FLAVORS
    495

Реализация AI-автодополнения поисковых запросов в мобильном приложении

Автодополнение — одна из самых требовательных к latency функций мобильного приложения. Пользователь ожидает подсказки быстрее, чем успевает заметить их появление: идеал — < 100 мс от ввода символа до появления вариантов. При этом запросы должны быть релевантными, а не просто «популярными».

Почему простой prefix-поиск не работает

Наивная реализация — хранить частые запросы в словаре и искать по префиксу. Это работает для «nike» → «nike кроссовки», но ломается для:

  • орфографических ошибок: «найк» вместо «nike»
  • транслитерации: «krossovki» vs «кроссовки»
  • семантически близких запросов: «беговая обувь» при вводе «кросс»
  • персонализации: одинаковый запрос «платье» для разных пользователей должен давать разные топ-подсказки

Архитектура production-ready автодополнения

Trie + нечёткий поиск для скорости

Базовый слой — Trie на популярных запросах с нечётким поиском через BK-tree или симметричное удаление (Symmetric Delete). Elasticsearch с маппингом completion field — готовое решение с fuzzy matching из коробки:

{
  "mappings": {
    "properties": {
      "suggest": {
        "type": "completion",
        "analyzer": "standard",
        "contexts": [
          {"name": "category", "type": "category"}
        ]
      },
      "weight": {"type": "integer"}
    }
  }
}
# Поиск автодополнений через ES Completion Suggester
async def get_suggestions(prefix: str, category: str, user_id: str) -> list[str]:
    response = await es.search(
        index="search_suggestions",
        body={
            "suggest": {
                "query_suggest": {
                    "prefix": prefix,
                    "completion": {
                        "field": "suggest",
                        "size": 8,
                        "fuzzy": {"fuzziness": "AUTO"},
                        "contexts": {"category": [category]}
                    }
                }
            }
        }
    )
    return [hit["_source"]["query"] for hit in response["suggest"]["query_suggest"][0]["options"]]

Персонализированный ранжировщик подсказок

Базовые подсказки из ES переранжируются с учётом истории пользователя. Признаки ранжировщика:

  • global_frequency — сколько раз этот запрос вводили все пользователи
  • user_query_history_match — вводил ли этот пользователь похожий запрос раньше
  • user_category_affinity — насколько категория запроса близка интересам пользователя
  • recency_boost — трендовые запросы за последние 24 часа получают буст

On-device кэш для мгновенного отклика

Первые 3–5 символов запроса покрывают ~80% популярных prefix-комбинаций. Кэшируем подсказки для них на устройстве при старте приложения (или в фоне):

// Android: предзагрузка популярных prefix-подсказок
class AutocompleteCache(context: Context) {
    private val db = Room.databaseBuilder(context, AutocompleteDatabase::class.java, "autocomplete").build()

    suspend fun preload() {
        val popularPrefixes = autocompleteApi.getPopularPrefixes(limit = 500)
        db.suggestionDao().insertAll(popularPrefixes)
    }

    suspend fun getSuggestions(prefix: String): List<String> {
        // сначала проверяем локальный кэш
        val cached = db.suggestionDao().getSuggestions(prefix)
        if (cached.isNotEmpty()) return cached

        // если нет в кэше — запрос на сервер
        return autocompleteApi.getSuggestions(prefix)
    }
}

Debounce и cancellation на клиенте

Каждый символ не должен триггерить новый запрос. Debounce 150–200 мс + отмена предыдущего in-flight запроса:

// iOS: debounced автодополнение с cancellation
class SearchViewModel: ObservableObject {
    @Published var suggestions: [String] = []
    private var searchTask: Task<Void, Never>?

    func onQueryChanged(_ query: String) {
        searchTask?.cancel()
        guard query.count >= 2 else { suggestions = []; return }

        searchTask = Task {
            try? await Task.sleep(nanoseconds: 150_000_000)  // 150ms debounce
            guard !Task.isCancelled else { return }

            let results = try? await autocompleteService.getSuggestions(query)
            await MainActor.run {
                suggestions = results ?? []
            }
        }
    }
}

Task.isCancelled проверяется после debounce — если пользователь продолжил ввод, предыдущая задача уже отменена.

Логирование выбора подсказки

Когда пользователь тапает на подсказку, логируем: позицию в списке, prefix при котором она была выбрана, итоговый запрос. Эти данные — обучающая выборка для следующей версии ранжировщика.

Процесс работы

Анализ поисковых логов: топ-1000 запросов, паттерны опечаток, язык/транслитерация.

Настройка Elasticsearch Completion Suggester с fuzzy matching.

Разработка персонализированного ранжировщика подсказок.

Реализация on-device кэша + debounce логики на iOS/Android.

Ориентиры по срокам

ES Completion Suggester без персонализации — 2–3 дня. С персонализированным ранжировщиком и on-device кэшем — 1,5–2 недели.