Чи слід використовувати API перехідних процесів для зберігання HTML-рядків чи об’єктів?


18

Припустимо, що існує плагін, який відображає 20 пов’язаних публікацій (для кожної публікації) з дуже складним запитом. А потім, використовуючи дані цього запиту, він будує складний HTML-макет. Також слід зазначити, що плагін є загальнодоступним і може бути встановлений на будь-якому сервері з будь-якою конфігурацією.

Щось на зразок:

/* complex and large query */
$related_posts = get_posts( ... );

$html_output = '';
foreach($related_posts as $key => $item) {
     /* complex layout rendering logic (but not as slow as the previous query) */   
     $html_output .= ...;
}

Тому мої запитання:

  • Який найбезпечніший і найправильніший спосіб кешування таких даних?
  • Чи слід використовувати API перехідних процесів для кешування $related_postsмасиву чи $html_outputрядка? Якщо я буду кешувати $html_ouputрядок, чи досягне це обмеження максимального розміру? Чи, можливо, я можу отримати його, перед тим як зберегти?
  • Чи варто взагалі використовувати перехідний API?

Відповіді:


18

Чи варто взагалі використовувати перехідний API?

Ні.

На складі перехідні програми WordPress зберігаються в таблиці wp_options і очищаються лише під час оновлення ядра. Припустимо, у вас є 50 000 публікацій, це 50 000 додаткових рядків у таблиці параметрів. Очевидно, що вони налаштовані на автоматичне завантаження = ні, тому це не буде споживати всю вашу пам'ять, але є ще один застереження.

Поле автоматичного завантаження в таблиці параметрів не має індексу, а це означає, що виклик до wp_load_alloptions()буде виконувати повне сканування таблиці. Чим більше рядків у вас, тим довше це займе. Чим частіше ви пишете в таблицю параметрів, тим менш ефективними є внутрішні кеші MySQL.

Якщо кешовані дані безпосередньо пов’язані з публікацією, вам краще зберігати їх у мета meta. Це також заощадить ваш запит щоразу, коли вам потрібно відобразити кешований вміст, оскільки мета-кеші після публікації (як правило) грунтуються під час пошуку публікації в WP_Query.

Ваша структура даних для мета-значення може змінюватись, ви можете мати часову позначку та виконувати свій дорогий запит, якщо кешоване значення застаріло, як і поводиться перехідний час.

Ще одна важлива думка, яку потрібно пам’ятати, - це те, що перехідні програми WordPress можуть бути нестабільними в середовищах із стійким кешуванням об’єктів. Це означає, що якщо ви зберігаєте кешовані дані протягом 24 годин у перехідному режимі, абсолютно немає гарантії, що вони будуть доступні через 23 години, 12, а то й 5 хвилин. Резервний об'єкт кеш-пам'яті об'єктів для багатьох установок - це запам'ятоване значення ключів у пам'яті, наприклад Redis або Memcached, і якщо недостатньо виділеної пам'яті для розміщення нових об'єктів, старі елементи будуть вилучені. Це величезна виграш для підходу до зберігання мета.

Недійсність теж може бути розумнішою, тобто чому ви скасовуєте кеші відповідних публікацій протягом X годин? Це тому, що якийсь зміст змінився? Додано нове повідомлення? Призначений новий тег? Залежно від вашого "складного та великого запиту", ви можете вибрати ТОЛЬКО недійсну, якщо трапилось щось, що змінить результати вашого запиту.

Чи варто використовувати API перехідних процесів для кешування масиву $ related_posts або рядка $ html_output? Якщо я буду кешувати рядок $ html_ouput, чи досягне це обмеження максимального розміру? Чи, можливо, я можу отримати його, перед тим як зберегти?

Це дуже залежить від розміру вашої рядка, оскільки це дані, які будуть обтікатися між PHP, MySQL і т. Д. Вам потрібно дуже постаратися, щоб досягти меж MySQL, але, наприклад, Memcached за замовчуванням ліміт на об'єкт - всього 1 мб.

Скільки часу займає ваша "складна логіка відображення макета"? Проведіть його через профайлер, щоб це дізнатися. Ймовірно, що це дуже швидко ніколи не стане вузьким місцем.

Якщо це так, я б запропонував кешувати ідентифікатори допису. Не об’єкти WP_Post, тому що вони будуть містити повний вміст публікації, а лише масив ідентифікаторів публікації. Потім просто використовувати WP_Queryз , post__inщо призведе до дуже швидкого запиту MySQL по первинному ключу.

Це означає, що якщо дані, необхідні для кожного елемента, досить прості, можливо, заголовок, URL-адреса мініатюри та постійна посилання, то ви можете зберігати лише ці три, без накладних витрат додаткового зворотного шляху до MySQL та без накладного кешування дуже довгого HTML струни.

Нічого, це багато слів, надія, що допомагає.


12

Не всі коди WP - це публічний код

Якщо ви збираєтесь випустити щось публічне, то всі речі, про які говорив Ковшенін , цілком справедливі.

Речі йнакше, якщо ви збираєтесь написати приватний код для себе або своєї компанії.

Зовнішній кеш об'єктів - велика перевага, в будь-якому випадку

Налаштувати зовнішній стійкий кеш-об'єкт дуже рекомендується , коли можна.

Все, що було сказано у відповіді ковшеніна про перехідні та MySQL, є дуже правдивим, і враховуючи, що сам WP і купа плагінів використовують кеш об'єктів ... то покращення продуктивності, яке ви отримали, абсолютно варто (малих) зусиль для налаштування. сучасна кеш-система типу Redis або Memcached.

Кешовані значення можуть не бути там: це добре

Крім того, так, кеш зовнішнього об'єкта не є надійним. Ніколи не слід покладатися на той факт, що є тимчасовий. Вам потрібно переконатися, що він працює, якщо кешоване не там, де вони повинні бути.

Кеш - це не зберігання, кеш - кеш.

Використовуйте кеш вибірково

Дивіться цей приклад:

function my_get_some_value($key) {
   // by default no cache when debug and if no external object_cache
   $defUse = ! (defined('WP_DEBUG') && WP_DEBUG) && wp_using_ext_object_cache();
   // make the usage of cache filterable
   $useCache = apply_filters('my_use_cache', $defUse);
   // return cached value if any
   if ($useCache && ($cached = get_transient($key))) {
     return $cached;
   }
   // no cached value, make sure your code works with no cache
   $value = my_get_some_value_in_some_expensive_way();
   // set cache, if allowed
   $useCache and set_transient($key, $value, HOUR_IN_SECONDS);

   return $value;
}

Використовуючи такий код на вашому приватному веб-сайті, продуктивність сайту може значно покращитися , особливо якщо у вас багато користувачів.

Зауважте, що:

  • За замовчуванням кеш не використовується при налагодженні, тому, сподіваємось, у вашому середовищі розробки. Повірте, кеш може зробити налагодження пеклом
  • За замовчуванням кеш також не використовується, коли WP не встановлено для використання зовнішнього кешу об'єктів. Це означає, що всі проблеми, пов'язані з MySQL, не існують, тому що ви не використовуєте перехідних при використанні MySQL. Ймовірно, легшою альтернативою було б використання wp_cache_*функцій , тому якщо не встановлений зовнішній кеш, кеш трапляється в пам'яті, а база даних ніколи не залучається.
  • Використання кеша є фільтрувальним, щоб обробити деякі крайні випадки, які можуть виникнути

Немає веб-шкали, якщо немає кешу

Не слід намагатися вирішувати проблеми з швидкістю з кешем. Якщо у вас проблеми зі швидкістю, то вам слід заново подумати про код.

Але для масштабування веб-сайту на веб-шкалі кеш дуже потрібен .

І багато разів (але не завжди) фрагмент кешований кеш-пам'ять набагато гнучкіший і підходить, ніж агресивне кешування повної сторінки.

Ваші запитання:

Чи варто взагалі використовувати перехідний API?

Це залежить .

Ваш код споживає багато ресурсів? Якщо ні, можливо, немає необхідності кешу. Як говорилося, справа не лише в швидкості. Якщо ваш код працює швидко, але для нього потрібна купа процесора та пам'яті для пари користувачів ... що буде, коли у вас є 100 або 1000 одночасних користувачів?

Якщо ви усвідомлюєте, що кеш буде гарною ідеєю ..

... і є публічним кодом: напевно, немає . Ви можете розглянути можливість кешування вибірково, як у моєму прикладі в публічному коді, але, як правило, краще, якщо ви залишаєте такі рішення виконавцям.

... і є приватним кодом: дуже, мабуть, так . Але навіть для приватного коду вибіркове кешування - все-таки хороша річ, наприклад, для налагодження.

Пам'ятайте, все одно, що wp_cache_*функції можуть надати вам доступ до кешу без ризику забруднення бази даних.

Чи варто використовувати API перехідних процесів для кешування масиву $ related_posts або рядка $ html_output?

Це залежить від багатьох речей. Наскільки великі струни? Який зовнішній кеш ви використовуєте? Якщо ви збираєтеся кешувати публікації, зберігання ідентифікатора як масиву може бути хорошою ідеєю, запит на гідну кількість публікацій за їх ідентифікатором відбувається досить швидко.

Заключні ноти

Перехідний API - це, мабуть, одна з найкращих речей WordPress. Завдяки плагінам, які ви можете знайти для будь-якого типу кеш-систем, це стає дурним простим API для великої кількості програмного забезпечення, яке може працювати під кришкою.

Поза WordPress таку абстракцію, яка працює з коробки безліччю різних систем кешування, і дозволяє вам переходити з однієї системи в іншу без особливих зусиль.

Ви рідко можете почути, як я кажу, що WordPress кращий за інші сучасні речі, але тимчасовий API - це одна з небагатьох речей, які мені не вистачає, коли я не працюю з WordPress.

Безумовно, кеш складний, не вирішує проблем з кодом і не є срібною кулею, але це щось, що вам потрібно для створення сайту з високим трафіком, який працює.

Ідея WordPress використовувати недооптимізовану таблицю MySQL для кешування є досить божевільною, але не краще утримуватись від кешу лише тому, що WordPress за замовчуванням це робить.

Вам просто потрібно зрозуміти, як все працює, а потім зробити свій вибір.


2

У попередніх відповідях вже було виділено обов'язкове " Це залежить ". З цим я повністю згоден.

Я хотів би додати рекомендацію, однак виходячи з того, як я " гадаю ", це було б найкраще зробити в сценарії, який ви описуєте вище.

Я б не використовував Transients у цьому випадку, а швидше Post Meta через одну перевагу, яку має останній: Control .

Оскільки вам потрібно кешувати дані щодня, кількість даних, які ви будете кешувати, залежить від кількості публікацій і зростатиме з часом. Як тільки ви перевершите певну кількість публікацій, ви можете потрапити на межі пам’яті, яку дозволено використовувати кеш об’єктів, і він почне видаляти раніше кешовані дані з пам’яті до того, як вони закінчуються. Це може призвести до ситуації, коли у вас великий приплив відвідувачів, коли кожен відвідувач запускатиме "надмірно складний SQL" на кожен запит сторінки, і ваш сайт повністю забуває.

Якщо ви кешуєте дані у вашій Post Meta, ви зможете не тільки контролювати їх збереження та отримання, але й точно можете контролювати їх оновлення. Ви додасте для цього завдання cron, яке працює лише в періоди часу, коли на сайті менше трафіку. Отже, "повільний запит" ніколи не стикається з реальними користувачами сайту, і ви можете його попередньо завантажити, так що робота вже виконана, коли перший відвідувач потрапить.

Майте на увазі, що всі кешування - це компроміс! Ось чому звичайна відповідь - "Це залежить". і чому немає «святого грааля кешування».

Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.