Simple Redis Cache
Redis-only object cache and full-page HTML cache for WordPress.
Install
This is the repository archive. It installs, but the folder name will carry the branch suffix and updates will not flow.
Install straight from GitHub with WP-CLI:
wp plugin install https://github.com/vitaliikaplia/simple-redis-cache/archive/refs/heads/master.zipМінімалістичний WordPress-плагін для двох незалежних рівнів кешування в одному Redis:
- постійний кеш через WordPress Object Cache API;
- повносторінковий кеш готового HTML.
Плагін не використовує файловий кеш, не містить реклами та не виконує мініфікацію. За бажанням він може точково інвалідувати HTML-кеш оновленої сторінки та пов'язаних публічних архівів таксономій без очищення решти сайту.
Можливості
- TCP, TLS або Unix-сокет;
- Redis ACL, пароль і вибір бази Redis;
- окремий TTL для об'єктів і HTML-сторінок;
- опційний час життя для CDN — на кожне анонімне попадання додається
Cache-Control: public, max-age=0, s-maxage=N, тож проксі чи CDN може зберігати сторінку, а браузер щоразу перепитує. Значення задається на вкладці Кеш HTML-сторінок у полі Час життя в CDN (від 0 секунд до одного місяця). Вимкнено за замовчуванням. Якщо перед сайтом Cloudflare, увімкніть відповідні тригери на вкладці Кеш Cloudflare — інакше CDN про інвалідацію сторінки не дізнається й доведеться чистити його вручну. НаявнийCache-Controlу збереженій відповіді ніколи не перезаписується, а на попадання авторизованого користувача заголовок не надсилається взагалі. Заголовок формується під час віддачі й не входить у збережений payload, тому нове значення діє з наступного попадання й не інвалідує кеш — так само, як налаштування діагностичного заголовка; - опційне очищення кешу Cloudflare: кнопка ручного очищення зони, перевірка підключення реальним purge і три незалежні автоматичні тригери — разом із очищенням усього кешу, разом із очищенням HTML-кешу та при оновленні запису;
- опційне дублювання транзієнтів WordPress у базу даних;
- кешування головної, записів, сторінок, CPT, архівів, пошуку та 404;
- опційне очищення всіх HTML-варіантів оновленого запису, сторінки або CPT разом із перекладами WPML/Polylang;
- окрема опція очищення архівів призначених публічних категорій і термів користувацьких таксономій, включно з попередніми, новими та батьківськими термами;
- виключення за URL, cookie, User-Agent і параметрами запиту;
- окремі HTML-варіанти за мовними cookie;
- опційне ізольоване кешування авторизованих користувачів;
- автоматична інвалідація відповідного шару після зміни його налаштувань або Redis-namespace;
- ручне очищення всього кешу або окремого шару;
- ручний прогрів HTML-кешу з живим прогресом для системних сторінок, доступних публічних типів записів і непорожніх термінів публічних таксономій;
- діагностика Redis, drop-in-файлів, ранньої конфігурації та їхніх прав доступу;
- англомовна й україномовна адмінка відповідно до мови профілю WordPress;
- логічні вкладки для Redis, об'єктного кешу, HTML-кешу, Cloudflare, прогріву та діагностики;
- оновлення з публічної гілки
masterна GitHub через стандартний механізм WordPress.
Вимоги
- WordPress 6.5 або новіший;
- PHP 8.1 або новіший;
- розширення PhpRedis;
- один доступний окремий сервер Redis, закритий від стороннього доступу й запису;
- звичайна односайтова інсталяція WordPress — Multisite не підтримується.
Встановлення
- Скопіюйте плагін у
wp-content/plugins/simple-redis-cache. - Активуйте Simple Redis Cache.
- Відкрийте Налаштування → Redis Cache.
- На вкладці Підключення до Redis вкажіть параметри сервера й збережіть їх.
- На окремих вкладках увімкніть Об'єктний кеш, Кеш HTML-сторінок або обидва шари.
- За потреби на вкладці Кеш HTML-сторінок окремо увімкніть очищення оновленої сторінки та/або пов'язаних архівів таксономій, а якщо перед сайтом стоїть проксі чи CDN — задайте Час життя в CDN.
- За потреби на вкладці Кеш Cloudflare вкажіть Zone ID та API-токен, оберіть потрібні тригери й натисніть Перевірити підключення до Cloudflare.
- За потреби виберіть публічні розділи на вкладці Прогрів кешу й дочекайтеся завершення прогресу.
- На вкладці Стан перевірте збережене підключення та діагностику.
Для Unix-сокета оберіть Unix-сокет і введіть у поле Шлях до Unix-сокета звичайний абсолютний шлях, наприклад /home/account/.system/redis.sock. Префікс unix:// додавати не треба; поля Хост і Порт для цього типу підключення ігноруються.
Під час увімкнення HTML-кешу плагін намагається додати define( 'WP_CACHE', true ); до wp-config.php, а наявне define( 'WP_CACHE', false ); змінює на true. Якщо WP_CACHE задано динамічним виразом, плагін нічого не змінює й повідомляє про це. Якщо автоматичне ввімкнення не вдалося, вручну встановіть для WP_CACHE значення true й перевірте вкладку Стан.
Кнопка Перевірити збережене підключення виконує не лише PING, а й ізольовану перевірку SET → GET → DELETE з 30-секундним TTL. Вкладка Стан також показує версію й maxmemory_policy Redis, фактичні шляхи та права drop-in-файлів, стан WP_CACHE, синхронізацію згенерованої конфігурації та поточний namespace ключів — без показу Redis credentials.
Для спільного Redis бажано визначити у wp-config.php унікальний префікс:
define( 'WP_CACHE_KEY_SALT', 'example.com' );
Плагін використовує непорожнє значення цієї константи без змін, байт у байт, як основу префікса для всіх власних Redis-ключів. Якщо константи немає або вона порожня, використовується згенерований префікс сайту. Решта параметрів Redis задається тільки в адмінці.
Прогрів і очищення кешу
Вкладка Прогрів кешу працює лише із зареєстрованими публічними джерелами, доступними для перегляду на фронтенді та дозволеними поточними налаштуваннями кешу головної, окремих матеріалів і архівів. Вона знаходить головну й сторінку записів, архіви авторів і дат, публічні стандартні та користувацькі типи записів, а також непорожні терміни публічних таксономій. Сторінки вкладень доступні лише тоді, коли їх увімкнено у WordPress.
Пагінація розраховується за даними БД і загальним posts_per_page, тому користувацькі правила запитів можуть дати окремі невдалі URL. Кількість знайдених URL обмежена 20000 за запуск; після досягнення межі показується попередження, а решту розділів можна прогріти окремо. Лічильники охоплюють усі результати, а детальний список проблем показує щонайбільше перші 100 попереджень, обходів кешу й помилок; кількість решти відображається окремо. Для звичайної структури постійних посилань на основі рядка запиту потрібно увімкнути Кешувати рядки запиту, інакше URL з ?p=, ?page_id=, ?cat=, ?paged= тощо отримають BYPASS. Небезпечні параметри запиту завжди залишаються виключеними. Якщо відповідні опції ввімкнено, пошук і 404 кешуються під час реального запиту, але не мають скінченного списку URL для автоматичного виявлення, тому прогрів їх не додає.
Відкрита вкладка послідовно керує процесом. Коли адмінка і фронтенд мають однаковий origin, вона виконує анонімні запити з браузера. Кожен прямий запит має 30-секундний таймаут; за іншого origin, мережевої помилки або таймауту використовується захищений серверний loopback-запит. Сторінка вважається прогрітою лише після підтвердженого Redis HIT.
Це ручний прогрів: він не запускається через cron, не очищає попередній кеш і створює лише анонімний варіант без cookie. Окремі мовні варіанти за vary_cookies не прогріваються. Вкладку потрібно залишити відкритою до завершення.
У верхній панелі WordPress доступне меню Кешування з такими діями:
- очистити весь кеш;
- очистити лише HTML-сторінки;
- очистити лише об'єктний кеш;
- перейти до ручного прогріву HTML-кешу;
- відкрити налаштування плагіна.
Записи Redis інвалідуються логічно через перемикання покоління ключів; плагін ніколи не виконує FLUSHDB або FLUSHALL. Водночас дії очистити об'єктний кеш і очистити весь кеш після окремого підтвердження фізично видаляють із wp_options усі стандартні транзієнти WordPress поточного сайту, включно зі створеними іншими плагінами. Видалення транзієнтів починається лише після успішної інвалідації object-generation. Очищення лише HTML-кешу транзієнти в БД не зачіпає.
Кеш Cloudflare
Вкладка Кеш Cloudflare очищає кеш на боці CDN. Потрібні дві речі: Zone ID зі сторінки огляду зони та API-токен, створений у Cloudflare з правом Zone / Cache Purge саме для цієї зони. Account-wide Global API Key не використовується й не потрібен — обмежений токен безпечніший, бо в разі витоку ним не можна зробити нічого, крім очищення кешу цієї зони.
Кнопка Перевірити підключення до Cloudflare намагається прочитати зону (щоб показати її назву й статус), а потім виконує справжнє очищення однієї адреси — головної сторінки. Читання зони потребує окремого права Zone Read, тож для токена лише з Cache Purge воно не спрацює — це не вважається помилкою, бо доказом є саме очищення. Це єдиний спосіб довести, що токен має саме право на очищення: токен лише для читання успішно проходить перевірку зони й падає вже на першому реальному purge. Побічний ефект мінімальний — головна один раз завантажиться з origin.
Кнопка Очистити кеш Cloudflare очищає всю зону й не чіпає Redis.
Три автоматичні тригери вмикаються окремо:
- разом із Очистити весь кеш — очищається вся зона;
- разом із Очистити кеш HTML-сторінок — очищається вся зона;
- при оновленні запису — очищаються точні адреси, які плагін уже інвалідує в Redis. Цей тригер спирається на опції вкладки Кеш HTML-сторінок: якщо там очищення при оновленні вимкнене, очищати на Cloudflare теж нічого.
Cloudflare очищає точні адреси, тож при оновленні запису поїде сам запис і перша сторінка пов'язаних архівів, але не вся їхня пагінація — масковий purge доступний лише на тарифі Enterprise. За один прохід надсилається щонайбільше 300 адрес пакетами по 30; про решту плагін окремо попереджає. Адреса запам'ятовується до зміни, тому зняття з публікації, переміщення в кошик і зміна посилання очищають саме те, що лежить у CDN. Очищення відбувається лише після успішної локальної інвалідації — інакше CDN одразу забрав би стару сторінку назад. Якщо Cloudflare недоступний або відмовив, збереження запису й локальне очищення все одно відбуваються, а адміністратор отримує попередження.
Якщо ви кешуєте HTML на Cloudflare
Це окрема історія, і її треба налаштувати на боці Cloudflare — плагін тут допомогти не може.
Ключ кешу Cloudflare за замовчуванням складається з методу, хоста й URL. Cookie в нього не входять. Для CDN запит залогіненого адміністратора й запит анонімного відвідувача — це буквально один і той самий запит. Тому послідовність виходить така:
- ви прогріваєте кеш — прогрів робить анонімні запити, плагін віддає
HITі додаєs-maxage; - Cloudflare зберігає анонімну копію сторінки;
- ви відкриваєте фронтенд залогінені — Cloudflare знаходить збіг за ключем і віддає ту саму анонімну копію з edge.
На третьому кроці запит до сайту не доходить узагалі. Плагін не має нагоди зробити BYPASS, бо його в цьому запиті немає. Саме тому опція Кешувати авторизованих користувачів тут ні до чого: вона керує кешем у Redis, а рішення ухвалює CDN раніше.
Виправляється це умовою в самому Cache Rule — щоб запит із cookie авторизації під правило просто не підпадав. Через Edit expression приведіть вираз до такого вигляду (підставте свій домен):
(http.host eq "example.com"
and not starts_with(http.request.uri.path, "/wp-admin")
and not starts_with(http.request.uri.path, "/wp-json")
and not starts_with(http.request.uri.path, "/wp-login")
and not starts_with(http.request.uri.path, "/wp-cron.php")
and not http.cookie contains "wordpress_logged_in_"
and not http.cookie contains "wp-postpass_"
and not http.cookie contains "comment_author_")
Для WooCommerce додайте ще and not http.cookie contains "woocommerce_items_in_cart" і and not http.cookie contains "wp_woocommerce_session_".
Умову варто тримати саме всередині наявного правила, а не виносити в окреме bypass-правило: під один запит може підпадати кілька Cache Rules, і тоді результат залежить від їхнього порядку. Одне правило з повним виразом такого питання не створює.
Для Edge TTL залишайте варіант Use cache-control header if present, bypass cache if not. За нього те, що edge має право зберігати, вирішує сам плагін: s-maxage додається лише на анонімне попадання, а на MISS, BYPASS і на будь-який запит авторизованого користувача не додається взагалі. Тобто ані сторінка залогіненого користувача, ані відповідь із небезпечним параметром запиту на CDN не потраплять.
Після збереження правила один раз очистіть зону — інакше вже збережена анонімна копія довисить до кінця свого s-maxage. Перевірити можна так: залогінений curl -I має віддати cf-cache-status: BYPASS або DYNAMIC, анонімний — HIT.
Важливо
- Опція Очищати кеш сторінки при її оновленні вимкнена за замовчуванням. Коли вона активна,
post_updatedлогічно інвалідує всі Redis HTML-варіанти саме оновленого запису, сторінки або публічного CPT. Для WPML і Polylang одночасно інвалідуються всі знайдені переклади. Застарілі payload фізично зникають за TTL або видаляються під час наступного звернення. - Окрема опція Очищати кеш пов'язаних архівів таксономій при оновленні запису також вимкнена за замовчуванням. Вона інвалідує всі HTML-варіанти архівів термів публічних стандартних і користувацьких таксономій, до яких належить оновлений запис або його переклади. Під час перепризначення враховуються старі й нові терми; для ієрархічних таксономій також очищуються батьківські архіви, бо вони можуть показувати матеріали дочірніх термів. Опція працює незалежно від очищення самої сторінки.
- Точкова інвалідація навмисно не очищає непов'язані архіви, загальні архіви post type/автора/дат, пошук, 404, меню, коментарі чи похідні WooCommerce-сторінки. Статична головна або сторінка записів інвалідується лише тоді, коли увімкнена опція очищення самої сторінки й ця сторінка є оновленим
WP_Post. Оновлення лише post meta без стандартногоpost_updatedне очищає singular payload; присвоєння термів через WordPress API очищає відповідні старі та нові архіви лише за ввімкненої опції архівів таксономій, а за одночасно ввімкненого очищення самої сторінки — також її singular cache. Для ширшого оновлення скористайтеся ручним очищенням HTML-кешу. - Плагін реагує лише на оновлення запису та присвоєння термів, і лише для таксономій, зареєстрованих саме для цього типу запису. Остаточне видалення запису, перейменування, злиття чи видалення самого терміна, зняття зв'язку через
wp_remove_object_terms()і публікація за розкладом не очищають кеш: відповідні сторінки лишаються до завершення TTL або ручного очищення HTML-кешу. - Якщо точкова інвалідація не вдалася, попередження отримає адміністратор навіть тоді, коли зміну зробив редактор, фронтенд, вебхук або cron: такі повідомлення потрапляють у спільну чергу, яку адмінка показує наступному адміністраторові.
- Якщо точкова інвалідація не змогла звернутися до Redis, збереження WordPress не ламається: плагін працює fail-open, показує адміністратору попередження, а попередній HTML лишається до TTL або ручного очищення.
- Збої Redis обробляються в режимі fail-open і не повинні робити сайт недоступним.
- Зміна семантики об'єктного або HTML-кешу автоматично перемикає покоління лише відповідного активного Redis-шару. Зміна Redis server/database/credentials або згенерованої ідентичності сайту інвалідує активні шари на старому й новому target; таймаути, retry, persistent connection, debug header і час життя в CDN зайвого очищення не спричиняють.
- Автоматична інвалідація Redis object namespace не видаляє DB-mirror транзієнти: вони можуть повторно прогріти Redis. Плагін показує попередження; для їх фізичного видалення скористайтеся окремо підтвердженою дією Очистити об'єктний кеш.
- Якщо дублювання транзієнтів у базу увімкнене, стандартний виклик
wp_cache_flush()— наприклад,wp cache flushчерез WP-CLI — теж видаляє зwp_optionsусі транзієнти WordPress, включно з чужими, і підтвердження, на відміну від кнопок в адмінці, у цього шляху немає. Якщо Redis у цей момент недоступний і покоління не змінилося, рядки зберігаються, а виклик повертає помилку. - Зміна
WP_CACHE_KEY_SALTпоза адмінкою одразу перемикає namespace, але плагін не може побачити попереднє значення константи. Перед такою зміною очистьте потрібні шари, поки старий salt ще активний, або не повертайте старе значення до завершення TTL його записів. - Якщо Redis недоступний під час такої інвалідації, нові правила не накладаються на старе покоління: плагін перечитує актуальний runtime і консервативно вимикає обидва керовані шари та їхні drop-in у режимі fail-open. Це також унеможливлює часткове повернення старої конфігурації під час паралельного збереження. На наступному адмін-запиті авторизованого адміністратора інвалідація повторюється; після успіху застосовуються найновіші збережені налаштування й відновлюються потрібні drop-in.
- Звичайне й примусове перезавантаження браузера не обходить серверний HTML-кеш через
no-cache,max-age=0абоPragma: no-cache;no-store,Rangeта умовні HTTP-запити й далі даютьBYPASS. - Ранні виключення працюють за іменем cookie. Залишкова або дубльована cookie автентифікації WordPress,
PHPSESSIDчи інша налаштована cookie сесії може й після виходу даватиBYPASS, доки браузер її не видалить. - Для WordPress Object Cache API значення
expire=0означає налаштований Максимальний TTL, а не безстрокове зберігання. - API-токен Cloudflare зберігається там само, де й облікові дані Redis: у базі WordPress і в згенерованому файлі конфігурації. Використовуйте токен, обмежений однією зоною й правом Cache Purge.
- Облікові дані Redis зберігаються в базі WordPress і у
wp-content/simple-redis-cache-config.php; плагін лише намагається встановити для файла права0640, тому захист БД і файлової системи залежить від власника сайту. - Redis має бути приватним і довіреним: об'єктний кеш може містити серіалізовані PHP-об'єкти. Відсутні метадані поколінь відновлюються з випадкового безпечного значення, а не з
1, однак для стабільного hit rate все одно бажана політикаnoevictionабо з групиvolatile-*; плагін не налаштовує Redis сам. - Плагін не перезаписує
object-cache.phpабоadvanced-cache.php, якщо ними володіє інший компонент. - Після деактивації налаштування зберігаються, а власні drop-in і згенерований
wp-content/simple-redis-cache-config.phpвидаляються. WP_CACHEнавмисно не видаляється зwp-config.php, оскільки його може використовувати інший кеш.
Видалення плагіна
Видалення через WordPress прибирає налаштування, повідомлення, метадані оновлень, згенерований config і drop-in-файли з маркером власності плагіна. Власний службовий site transient механізму оновлень теж видаляється, але масове очищення решти транзієнтів WordPress із БД не виконується. Записи й метадані Redis, WP_CACHE і WP_CACHE_KEY_SALT залишаються. Щодо Redis, ручне очищення перед видаленням лише логічно перемикає поточне покоління і не звільняє пам'ять негайно: записи зникнуть за TTL, а ключі метаданих поколінь не мають TTL. Водночас очищення об'єктного або всього кешу, як зазначено вище, фізично видаляє стандартні транзієнти з БД.
Оновлення
Updater читає Version із файла simple-redis-cache.php у публічній гілці master репозиторію vitaliikaplia/simple-redis-cache. Якщо ця версія новіша за локальну, WordPress отримує стандартну пропозицію оновлення та ZIP-архів поточної гілки master. Результат перевірки кешується на 12 годин, а невдала перевірка — на 1 годину; примусово перечитати гілку можна посиланням «Перевірити знову» на сторінці Консоль → Оновлення. Нативні автоматичні оновлення WordPress працюють, якщо адміністратор окремо ввімкнув їх для плагіна.
Щоб опублікувати версію, потрібно однаково змінити Version, SIMPLE_REDIS_CACHE_VERSION, Stable tag, changelog у readme.txt і текст changelog у стандартному WordPress plugin-details modal, оновити POT/PO/MO разом із заголовком Project-Id-Version у них, закомітити та запушити узгоджене дерево в master. Створювати GitHub-тег або GitHub Release не потрібно. Гілка master є змінною, а пакет не має незалежної контрольної суми чи криптографічного підпису, тому механізм оновлення покладається на HTTPS GitHub і цілісність публічного репозиторію.
Ліцензія
GPL-2.0-or-later.