Навантажувальне тестування інтернет-магазину 1С-Бітрікс
Магазин на Бітрікс, стабільно працюючий при 50 відвідувачах онлайн, може впасти при 500 — і причина не завжди в слабкому сервері. Важкі компоненти, неоптимальні SQL-запити, відсутність кешування — все це виявляється тільки під навантаженням. Навантажувальне тестування показує реальну пропускну спроможність сайту й локалізує вузькі місця до того, як вони ударять по продажам.
Інструменти
Три основні інструменти для генерації навантаження:
Apache JMeter — стандарт де-факто. Java-додаток з GUI для створення тестових сценаріїв. Підтримує HTTP, HTTPS, cookies, авторизацію. Вміє записувати сценарій через проксі — достатньо пройтися по сайту, і JMeter збереже всі запити. Мінус — висока утримання пам'яті при великій кількості потоків, один екземпляр рідко видає більше 1000-2000 RPS.
Gatling — інструмент на Scala з DSL для описання сценаріїв в коді. Генерує детальні HTML-звіти з графіками розподілу часів відповіді. Ефективніший за JMeter по утриманню ресурсів завдяки неблокуючому I/O. Підходить для CI/CD — сценарій зберігається в репозиторії, запускається в пайплайні.
k6 — сучасний інструмент від Grafana Labs. Сценарії пишуться на JavaScript, що знижує поріг входу для фронтенд-команди. Нативна інтеграція з Grafana Cloud для візуалізації результатів у реальному часі. Утримує мінімум ресурсів — один пристрій легко генерує 5000+ RPS.
| Інструмент | Мова сценаріїв | Утримання ресурсів | Звітність | CI/CD |
|---|---|---|---|---|
| JMeter | GUI / XML | Високе | Плаґіни (JTL) | Через CLI-режим |
| Gatling | Scala DSL | Середнє | Вбудовані HTML | Нативна |
| k6 | JavaScript | Низьке | Grafana / JSON | Нативна |
Сценарії тестування
Навантажувальний тест без реалістичних сценаріїв — гаяння часу. Для інтернет-магазину на Бітрікс критичні чотири сценарії:
1. Перегляд каталогу — 60-70% трафіку. Включає: головна → розділ каталогу → фільтрація за властивостями → карточка товара. Важливо тестувати з smart-фільтром (catalog.smart.filter), який генерує важкі SQL з множественими JOIN по таблицях властивостей інфоблоків.
2. Пошук — 10-15% трафіку. Модуль пошуку Бітрікс (search) при повнотекстовому пошуку через LIKE/MATCH звертається до b_search_content — таблиці, яка на 100 000+ товарів стає вузьким місцем. Якщо використовується Elasticsearch через модуль search або сторонне рішення — тестуйте окремо.
3. Робота з кошиком — 5-10% трафіку. Додавання, зміна кількості, видалення, застосування купона. Кожна дія викликає перерахунок знижок через \Bitrix\Sale\Discount\RuntimeCache — операція, яка при 50+ правилах знижок стає помітною.
4. Оформлення замовлення — 2-5% трафіку, але найкритичніший сценарій. Включає: вибір доставки (розрахунок вартості через API транспортної компанії), вибір оплати, підтвердження. Оформлення замовлення — найважча операція: створюються записи в b_sale_order, b_sale_basket, b_sale_order_props_value, b_sale_payment, спрацьовують обробники подій.
Розподіл навантаження: сценарії комбінуються з вагами, що відповідають реальному трафіку. У k6 це робиться через scenarios з різними rate для кожної VU-групи.
Ключові метрики
- RPS (Requests Per Second) — кількість запитів на секунду, яку сайт обробляє без деградації.
- TTFB (Time To First Byte) — час до першого байту відповіді. Для Бітрікс прийнятний TTFB — до 200 мс при кешованих сторінках, до 500 мс для динамічних.
- 95-й перцентиль часу відповіді — час, у який укладаються 95% запитів. Саме цей показник, а не середнє, показує реальний користувальницький досвід. Якщо середнє 200 мс, а P95 — 3 секунди, значить кожний двадцатий відвідувач чекає неприйнятно довго.
- Error rate — відсоток помилок (5xx, таймаути). При навантаженні вищій за поріг error rate різко зростає — це й є межа пропускної спроможності.
Профілювання: пошук вузьких місць
Навантажувальний тест показує що гальмує, профілювання — чому.
Xdebug в режимі профілювання (xdebug.mode=profile) генерує cachegrind-файли, які відкриваються в KCachegrind або Webgrind. Показує дерево викликів з часом виконання кожної функції. Мінус — Xdebug сповільнює PHP у 3-5 разів, тому профілювання виконується окремо від навантажувального тесту на одиничних запитах.
Blackfire — комерційний профайлер від SensioLabs. Працює як розширення PHP з мінімальним оверхедом (5-10%). Дозволяє профілювати під навантаженням, будує порівняльні графіки між версіями коду. Інтеграція з CI/CD — можна задати assertion: «час виконання сторінки каталогу не повинен перевищувати 300 мс».
MySQL/PostgreSQL slow query log — обов'язковий під час навантажувального тесту. Для MySQL: slow_query_log = 1, long_query_time = 0.5. Для PostgreSQL: log_min_duration_statement = 500. Аналіз логу виявляє запити без індексів, повні сканування таблиць, deadlock-и.
Типові вузькі місця Бітрікс
Важкі компоненти без кешу. catalog.section з увімкненим smart-фільтром та без CACHE_TIME — кожний хіт генерує запити до таблиць b_iblock_element, b_iblock_element_property, b_catalog_price. На розділі з 1000 товарів і 20 фільтрованими властивостями — це десятки SQL-запитів. Рішення: увімкнути компонентний кеш (CACHE_TIME = 3600) та кеш фільтра.
Неоптимальні властивості інфоблоків. Властивості типу «Список» зі сотнями значень, множественні властивості — кожна множественна властивість зберігається окремою рядком в b_iblock_element_prop_m*. При фільтрації за декількома множественими властивостями MySQL/PostgreSQL будує план з множественими JOIN, які деградують нелінійно.
OPcache. Без OPcache кожний запит компілює PHP-файли заново. Бітрікс містить тисячі файлів — ядро, компоненти, шаблони. Переконайтеся: opcache.enable = 1, opcache.memory_consumption = 256 (мінімум), opcache.max_accelerated_files = 20000. Перевіряйте opcache_get_status() — якщо cache_full = true, збільшуйте memory_consumption.
Сесії у файлах. За замовчуванням PHP зберігає сесії у файлах. При 500+ одночасних користувачах каталог сесій містить тисячі файлів, і файлова система сповільнюється. Перенесіть сесії в Redis або Memcached через налаштування session.save_handler.
Модуль пошуку. Стандартний пошук Бітрікс використовує таблицю b_search_content з FULLTEXT-індексом. На 100 000+ товарів повнотекстовий пошук через MySQL MATCH AGAINST стає повільним. Рішення: Elasticsearch через модуль search або Sphinx.
Оптимізація після тестів
Результати навантажувального тесту транслюються в конкретні завдання:
| Проблема | Метрика | Рішення |
|---|---|---|
| TTFB > 1 с на каталозі | P95 response time | Компонентний кеш + композитний кеш |
| Error rate 5% при 200 RPS | Error rate | Збільшення PHP-FPM workers, тюнінг БД |
| Slow query > 2 с на фільтрації | Slow query log | Складені індекси, Elasticsearch |
| OOM при 300 users | Memory consumption | OPcache, оптимізація модулів |
| Таймаут при оформленні | TTFB checkout | Асинхронна обробка подій замовлення |
Навантажувальне тестування — не разова процедура. Виконується перед кожною крупною акцією (Чорна п'ятниця, сезонні розпродажи), після міграції сервера, після оновлення ядра Бітрікс. Автоматизація через k6 + CI/CD дозволяє запускати базовий тест при кожному деплої та вловлювати деградацію продуктивності на ранній стадії.







