Оптимизация переиндексации Elasticsearch для 1С-Битрикс

Наша компания занимается разработкой, поддержкой и обслуживанием решений на Битрикс и Битрикс24 любой сложности. От простых одностраничных сайтов до сложных интернет магазинов, CRM систем с интеграцией 1С и телефонии. Опыт разработчиков подтвержден сертификатами от вендора.
Предлагаемые услуги
Показано 1 из 1 услугВсе 1626 услуг
Оптимизация переиндексации Elasticsearch для 1С-Битрикс
Средняя
~1-2 недели
Часто задаваемые вопросы
Наши компетенции:
Этапы разработки
Последние работы
  • image_website-b2b-advance_0.png
    Разработка сайта компании B2B ADVANCE
    1173
  • image_bitrix-bitrix-24-1c_fixper_448_0.png
    Разработка веб-сайта для компании ФИКСПЕР
    811
  • image_bitrix-bitrix-24-1c_development_of_an_online_appointment_booking_widget_for_a_medical_center_594_0.webp
    Разработка на базе Битрикс, Битрикс24, 1С для компании Development of an Online Appointment Booking Widget for a Medical Center
    564
  • image_bitrix-bitrix-24-1c_mirsanbel_458_0.webp
    Разработка на базе 1С Предприятие для компании МИРСАНБЕЛ
    745
  • image_crm_dolbimby_434_0.webp
    Разработка сайта на CRM Битрикс24 для компании DOLBIMBY
    655
  • image_crm_technotorgcomplex_453_0.webp
    Разработка на базе Битрикс24 для компании ТЕХНОТОРГКОМПЛЕКС
    976

Оптимизация переиндексации Elasticsearch для 1С-Битрикс

Оптимизация переиндексации Elasticsearch для 1С-Битрикс

На проекте с 800 000 SKU плановая переиндексация из 1С занимала 14 часов. За это время накапливалась очередь изменений, поиск отдавал устаревшие данные, а импорт из 1С конкурировал с переиндексацией за ресурсы. Задача — сократить полную переиндексацию до 1–2 часов без остановки поиска.

Почему переиндексация тормозит

Типичные причины медленной переиндексации:

Последовательная индексация через одиночные запросы. Каждый документ отправляется отдельным PUT /bitrix_catalog/_doc/{id}. HTTP-накладные расходы, TCP-соединение на каждый запрос, ответ 200ms * 800000 = 160000 секунд.

Слишком маленький batch в Bulk API. Размер пакета 10 документов вместо оптимальных 200–1000.

Refresh после каждого пакета. Принудительный POST /bitrix_catalog/_refresh после каждого batch — самоубийство производительности. Refresh создаёт новый сегмент Lucene, блокирует индексацию на десятки миллисекунд.

Неправильный refresh_interval во время переиндексации. Дефолтные 1 секунда генерируют сотни тысяч мелких сегментов, которые ES тратит силы на merge.

Стратегия zero-downtime переиндексации

Ключевой приём — индексировать в новый индекс, а не поверх рабочего:

Текущий: bitrix_catalog_v1  <-- алиас bitrix_catalog
Новый:   bitrix_catalog_v2  <-- индексируем сюда
После:   переключаем алиас на v2
// Создаём алиас при начальной настройке
POST /_aliases
{
  "actions": [
    { "add": { "index": "bitrix_catalog_v1", "alias": "bitrix_catalog" } }
  ]
}

Битрикс работает с алиасом bitrix_catalog. Пока идёт переиндексация в v2, поиск продолжает работать через v1. После завершения атомарно переключаем алиас.

Настройка Elasticsearch для быстрой индексации

Перед переиндексацией временно меняем настройки через API:

PUT /bitrix_catalog_v2/_settings
{
  "index": {
    "refresh_interval": "-1",
    "number_of_replicas": 0,
    "translog.durability": "async",
    "translog.sync_interval": "30s"
  }
}

refresh_interval: -1 полностью отключает автоматический refresh — документы не попадают в поиск до явного refresh, зато индексация ускоряется в 3–5 раз.

number_of_replicas: 0 отключает репликацию на время индексации. ES не тратит время на копирование шардов.

translog.durability: async — транслог сбрасывается на диск не при каждой операции, а по таймеру. Риск потери данных при сбое за последние 30 секунд — приемлемо для переиндексации, не для продакшн-данных.

После завершения восстанавливаем настройки:

PUT /bitrix_catalog_v2/_settings
{
  "index": {
    "refresh_interval": "5s",
    "number_of_replicas": 1,
    "translog.durability": "request"
  }
}

Затем принудительный merge для уменьшения числа сегментов:

POST /bitrix_catalog_v2/_forcemerge?max_num_segments=1

Оптимизация PHP-индексатора

Размер пакета для Bulk API подбираем эмпирически. Ориентир — 5–15 МБ на один запрос:

$batchSize = 500; // документов на один bulk-запрос
$bulk = [];

foreach ($products as $product) {
    $bulk[] = ['index' => ['_index' => 'bitrix_catalog_v2', '_id' => $product['ID']]];
    $bulk[] = buildDocument($product);

    if (count($bulk) >= $batchSize * 2) {
        $client->bulk(['body' => $bulk]);
        $bulk = [];
        // НЕ вызываем _refresh здесь
    }
}

if (!empty($bulk)) {
    $client->bulk(['body' => $bulk]);
}

Параллельная индексация через несколько процессов — делим каталог по диапазонам ID:

# Процесс 1: ID 1 - 200000
php index_products.php --from=1 --to=200000 &

# Процесс 2: ID 200001 - 400000
php index_products.php --from=200001 --to=400000 &

# Процесс 3: ID 400001 - 600000
php index_products.php --from=400001 --to=600000 &

wait
echo "Indexing complete"

Три параллельных процесса на 3-нодовом кластере дают линейное ускорение. Ограничение — пропускная способность MySQL при чтении данных.

Переключение алиаса

После завершения индексации атомарно переключаем алиас:

POST /_aliases
{
  "actions": [
    { "remove": { "index": "bitrix_catalog_v1", "alias": "bitrix_catalog" } },
    { "add":    { "index": "bitrix_catalog_v2", "alias": "bitrix_catalog" } }
  ]
}

Операция атомарна — между удалением старого алиаса и добавлением нового нет момента, когда алиас не существует. Переключение занимает миллисекунды, поиск не прерывается.

Результат

На каталоге 800к SKU после оптимизации: полная переиндексация 1 ч 20 мин (было 14 ч), инкрементальное обновление 200–300 документов в секунду через Bulk API вместо 15–20 через одиночные запросы.