Кешування фрагментів відноситься до кешуванню фрагментів сторінки. Наприклад, якщо сторінка відображає в таблиці сумарні річні продажі, ми можемо зберегти цю таблицю в кеші з метою економії часу, необхідного для генерації таблиці при кожному запиті.
Для використання кешування фрагментів ми викликаємо методи CController::beginCache() і CController::endCache() у скрипті представлення контролера. Ці два методи є мітками початку і кінця вмісту сторінки, який має бути кешуваний. Як і в кешуванні даних, нам потрібен ідентифікатор для визначення кешованого фрагмента.
…інший HTML-вміст…
<?php if($this->beginCache($id)) { ?>
…кешований вміст…
$this->endCache(); } ?>
…інший HTML-вміст…
У коді вище, якщо метод beginCache() повертає false, то кешований вміст буде автоматично вставлений в дане місце, інакше, вміст всередині виразу if
буде виконано і збережено в кеші, коли буде викликаний метод endCache().
Викликаючи метод beginCache(), ми можемо передати у якості другого параметра масив, що містить параметри кешування для управління кешуванням фрагмента. Фактично, методи beginCache() і endCache() є зручною обгорткою віджету COutputCache. Тому, параметри кешування можуть бути початковими значеннями для будь-яких властивостей віджету COutputCache.
Напевно, найбільш часто використовуваним параметром є duration, який визначає, наскільки довго вміст кешу буде залишатися дійсним (валідним). Це схоже на параметр терміну дії методу CCache::set(). Код нижче кешує фрагмент на час не більше години:
…інший HTML-вміст…
<?php if($this->beginCache($id, array('duration'=>3600))) { ?>
…кешований вміст…
$this->endCache(); } ?>
…інший HTML-вміст…
Якщо ми не встановимо тривалість (термін зберігання), вона буде дорівнювати значенню за замовчуванням (60 секунд). Це означає, що кешований вміст стане недійсним через 60 секунд.
Починаючи з версії 1.1.8, якщо виставити duration в 0, то відповідне значення буде видалено з кешу. Якщо ж застосувати відʼємне значення duration, кеш буде відключений, але існуюче значення в ньому залишиться. До 1.1.8, як при виставленні 0, так і при використанні відʼємного значення кеш відключався без очищення значення.
Як і кешування даних, кешований вміст фрагмента теж може мати залежності. Наприклад, відображення вмісту повідомлення залежить від того, змінено це повідомлення чи ні.
Для визначення залежності, ми встановлюємо параметр dependency, який може бути або обʼєктом, що реалізує інтерфейс ICacheDependency, або масивом налаштувань, який може бути використаний для генерації обʼєкта залежності. Наступний код визначає вміст фрагмента, який залежить від зміни значення стовпця lastModified
:
…інший HTML-вміст…
<?php if($this->beginCache($id, array('dependency'=>array(
'class'=>'system.caching.dependencies.CDbCacheDependency',
'sql'=>'SELECT MAX(lastModified) FROM Post')))) { ?>
…кешований вміст…
$this->endCache(); } ?>
…інший HTML-вміст…
Кешований вміст може бути змінено відповідно до деяких параметрів. Наприклад, особистий профіль може по-різному виглядати для різних користувачів. Для кешування вмісту профілю ми б хотіли, щоб кешована копія була різною у відповідності з ідентифікатором користувача. По-суті, це означає, що ми повинні використовувати різні ідентифікатори при виклику метода beginCache().
Замість того, щоб запитувати у розробника різні ідентифікатори, відповідні деякій схемі, існує клас COutputCache, який містить таку можливість. Нижче наведено перелік вбудованих варіацій:
varyByRoute: якщо встановлено у значення true, кешований вміст буде змінюватися у відповідності з налаштуваннями маршруту. Тому, кожна комбінація запитуваного контролера і дії будуть мати різний кешований вміст;
varyBySession: якщо встановлено у значення true, кешований вміст буде змінюватися відповідно до ідентифікатора сесії. Тому, кожна користувацька сесія може бачити різний вміст і отримувати його з кешу;
varyByParam: якщо встановлено в якості масиву імен, кешований вміст буде змінюватися у відповідності з певними GET параметрами. Наприклад, якщо сторінка відображає вміст повідомлення залежно від GET-параметра id
, ми можемо визначити varyByParam у вигляді масиву array('id')
і потім кешувати вміст кожного повідомлення. Без такої варіації, ми могли б кешувати лише одне повідомлення;
varyByExpression: якщо встановлено у якості виразу PHP, кешований вміст буде змінюватися відповідно до результату даного виразу PHP.
Іноді ми хочемо, щоб кешування фрагменту було увімкнено тільки для деяких типів запиту. Наприклад, сторінку з формою ми хочемо кешувати тільки тоді, коли вона ініціалізована (GET запитом). Будь-яке подальше відображення форми (отримане POST запитом) не повинно бути кешованим, бо може містити дані, введені користувачем. Щоб так зробити, ми визначаємо параметр requestTypes:
…інший HTML-вміст…
<?php if($this->beginCache($id, array('requestTypes'=>array('GET')))) { ?>
…кешований вміст…
$this->endCache(); } ?>
…інший HTML-вміст…
Кешування фрагментів може бути вкладеним. Це означає, що кешований фрагмент оточений більшим фрагментом (міститься в ньому), який теж кешується. Наприклад, коментарі кешовані у внутрішньому фрагменті кешу, і вони ж кешовані разом із вмістом повідомлення у зовнішньому фрагменті кешу.
…інший HTML-вміст…
<?php if($this->beginCache($id1)) { ?>
…зовнішній кешований вміст…
if($this->beginCache($id2)) { ?>
…внутрішній кешований вміст…
$this->endCache(); } ?>
…зовнішній кешований вміст…
$this->endCache(); } ?>
…інший HTML-вміст…
Параметри кешування можуть бути різними для вкладених кешей. Наприклад, внутрішній і зовнішній кеші у вищенаведеному прикладі можуть мати різні терміни зберігання. Навіть коли кешовані дані у зовнішньому кеші стають недійсними, внутрішній кеш все ще може видавати дійсні фрагменти. Тим не менш, це невірно у зворотньому випадку. Якщо зовнішній кеш є актуальним, він завжди буде давати кешовану копію, навіть якщо у вмісті внутрішнього кеша закінчився термін дії (воно застаріло). Слід проявляти обережність при виставленні терміну зберігання та завдання залежностей для вкладених кешей. В іншому випадку ви можете отримати застарілі дані.