TFTL · Підсумок виконаних робіт · для Avalon · 09.09.2026
Сайт віддає готові сторінки за півсекунди замість кількох секунд, статуси квартир з Salesforce оновлюються за лічені секунди, а запити залогінених користувачів обходять спільний кеш. Усе це працює на тестовому стенді, де ми це перевіряємо, і вимикається одним перемикачем.
Тестовий стенд · 32 із 32 перевірок пройденоГоловні результати
Раніше кожна сторінка збиралась заново для кожного відвідувача. Тепер готові сторінки віддаються з памʼяті — але лише анонімним відвідувачам, і лише доки дані не змінились.
10×
швидший перший байт сторінки «Компанія»: 5.7 с → 0.54 с
≤ 5 с
оновлення статусів квартир після зміни в Salesforce, виміряно на стенді
0
витоків у перевірці з 60 змішаних запитів анонімів і залогінених
2 с
щоб одним перемикачем вимкнути все кешування на обох серверах
Як це працює
Минулі проблеми з кешем на сайті мали дві причини: чужі дані в спільному кеші та застарілі статуси броні. Нова система побудована так, щоб закрити обидві причини — і саме це ми перевіряємо на стенді.
Правило 1
Нічого особистого в спільному кеші
У кеш потрапляє лише те, що бачить анонімний відвідувач. Будь-який запит залогіненого користувача обходить кеш і завжди отримує живу відповідь. Це перевіряється тричі — на CDN, на фронтенді і на API.
Правило 2
Свіжість за версіями, а не за таймером
Кожен вид даних має номер версії. Зміна в Salesforce чи в адмінці підвищує номер — і всі сторінки, зібрані зі старих даних, миттєво стають недійсними. Не треба чекати, поки «спливе» кеш.
Правило 3
У сумніві — віддати живу сторінку
Якщо фронтенд не може підтвердити, що його версії актуальні (звʼязок з API втрачено, систему вимкнено, сервер щойно перезапущено), він не віддає з кешу нічого. Краще повільніша сторінка, ніж застаріла.
Виконані роботи
Провели повний аудит усіх шарів: Cloudflare, сервери, фронтенд, API, база. Зʼясували, що правило Cloudflare після старого інциденту вимикало кеш для всього сайту, навіть для незмінних файлів.
Спроєктували архітектуру і провели її через три раунди незалежної технічної експертизи. Кілька слабких місць виправлено ще на етапі дизайну.
Виправили порядок запису статусів з Salesforce: статус квартири тепер зберігається до завантаження планувань, тому повільна картинка більше не затримує і не губить зміну статусу.
Закрили витік на рівні фронтенду: сервер більше не передає cookies відвідувачів до API під час збирання сторінки.
Побудували кеш відповідей API для 9 публічних розділів і кеш готових сторінок для 17 сторінок сайту — з версіями, миттєвим оновленням і захистом від збереження чужих даних.
Додали керування й прозорість: один перемикач вимикає все за 2 секунди, кожна відповідь повідомляє, звідки вона прийшла, є статистика влучань і статус синхронізації.
Покрили тестами: 99 автоматичних тестів у коді та приймальний сценарій із 32 перевірок, який прогонимо на стенді однією командою.
Задокументували для розробників: як система працює, як додати новий розділ у кеш, як повідомити про зміну даних, як вимкнути або прибрати її повністю.
Доказ №1 · швидкодія
Час до першого байта сторінки, виміряний на тестовому стенді: медіана з трьох прогонів, «до» — живе збирання сторінки, «стало» — з кешу. Стенд повільніший за бойовий сервер, тому важливе співвідношення, а не абсолютні цифри.
Каталог квартир, сторінки квартир і проєктів у цьому етапі ще не кешуються — навмисно. Спочатку система працює на статичному контенті під наглядом; квартири з окремим живим статусом — окремий етап.
Доказ №2 · безпека і свіжість
Приймальний сценарій навмисно ламає систему всіма способами, які колись призводили до проблем, і перевіряє, що вона поводиться правильно.
Витік даних
0 з 60
60 упереміш запитів анонімів і залогінених: жоден запит із cookie чи токеном не отримав відповідь із кешу, жодна анонімна сторінка не містила чужого токена.
Зміна в Salesforce
≤ 6 с
Вебхук Salesforce, редагування в адмінці або ручна команда — і сторінки на фронтенді та відповіді API оновлюються за секунди на обох серверах.
Перемикач
2 с
Одна команда на API вимикає кешування скрізь, включно з фронтендом на іншому сервері. Увімкнення назад — так само за 2 секунди.
Втрата звʼязку
живі сторінки
Коли фронтенд не може дістатись до API, він за 8 секунд перестає віддавати з кешу і збирає сторінки заново, доки звʼязок не повернеться.
Перезапуск
спочатку синхронізація
Після перезапуску сервера кеш порожній і не використовується, доки не підтверджені актуальні версії даних. Синхронізація займає 1 секунду.
Незнайомі параметри
повз кеш
Посилання з рекламними мітками чи будь-якими сторонніми параметрами віддаються живими і в кеш не потрапляють.
Технічна частина
Що саме відбувається з кожним запитом — без оцінок і обіцянок. Уся ця механіка працює на тестовому стенді, і саме її поведінку перевіряє приймальний сценарій із 32 перевірок.
1
Класифікація запиту
Запит спершу проходить класифікатор: GET без cookies і без заголовка Authorization вважається придатним до кешу. Будь-який cookie, токен, не-GET або незнайомий параметр в адресі — запит іде повз кеш, живим. Класифікатор стоїть і на фронтенді, і на API.
2
Версії замість таймера
Кожен тип контенту має тег (static-pages, news, offers, catalogue…) з цілим числом-версією в Redis. Запис у кеші зберігає версії, з якими його зібрали, і віддається лише доки всі вони збігаються з поточними.
3
Запис даних підвищує версію
Збереження в адмінці, вебхук Salesforce або фонове завантаження підвищує версії потрібних тегів одним атомарним інкрементом наприкінці операції (десять збережень в одному вебхуку — один інкремент). Кожне підвищення записується в лог.
4
Фронтенд звіряє версії
Сервер сторінок кожні 5 секунд опитує API про поточні версії (heartbeat), а одразу після зміни ще отримує підписаний push від API. Готова сторінка віддається з памʼяті лише коли її версії збігаються з останніми підтвердженими.
5
У сумніві — живий рендер
Якщо фронтенд не синхронізований (пропущено два heartbeat-и, API недоступне, сервер щойно перезапущено), сторінки збираються заново. Помилка всередині кеш-логіки теж переводить запит у живий режим, а не в помилку чи стару відповідь.
6
Перевірка перед збереженням і мітка
Відповідь потрапляє в кеш лише якщо: статус 200, немає Set-Cookie, немає авторизованого користувача, JSON, розмір у межах ліміту, версії не змінились під час збирання. Кожна відповідь несе заголовок X-Cache-Layer (HIT / MISS / BYPASS із причиною); команда cache-system:off вимикає систему на обох серверах.
Підсумок
* Правило Cloudflare на стенді не змінювалось; його звуження — частина переносу на бойовий сервер. Уся система працює лише на тестовому стенді з повними даними; на бойові сервери нічого не переносилось.