MDL-41492 cache: Added ability for alternate cache config
[moodle.git] / cache / renderer.php
1 <?php
2 // This file is part of Moodle - http://moodle.org/
3 //
4 // Moodle is free software: you can redistribute it and/or modify
5 // it under the terms of the GNU General Public License as published by
6 // the Free Software Foundation, either version 3 of the License, or
7 // (at your option) any later version.
8 //
9 // Moodle is distributed in the hope that it will be useful,
10 // but WITHOUT ANY WARRANTY; without even the implied warranty of
11 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12 // GNU General Public License for more details.
13 //
14 // You should have received a copy of the GNU General Public License
15 // along with Moodle.  If not, see <http://www.gnu.org/licenses/>.
17 /**
18  * The Cache renderer.
19  *
20  * This file is part of Moodle's cache API, affectionately called MUC.
21  *
22  * @package    core
23  * @category   cache
24  * @copyright  2012 Sam Hemelryk
25  * @license    http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
26  */
28 defined('MOODLE_INTERNAL') || die();
30 /**
31  * The cache renderer (mainly admin interfaces).
32  *
33  * @package    core
34  * @category   cache
35  * @copyright  2012 Sam Hemelryk
36  * @license    http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
37  */
38 class core_cache_renderer extends plugin_renderer_base {
40     /**
41      * Displays store summaries.
42      *
43      * @param array $storeinstancesummaries information about each store instance,
44      *      as returned by core_cache\administration_helper::get_store_instance_summaries().
45      * @param array $storepluginsummaries information about each store plugin as
46      *      returned by core_cache\administration_helper::get_store_plugin_summaries().
47      * @return string HTML
48      */
49     public function store_instance_summariers(array $storeinstancesummaries, array $storepluginsummaries) {
50         $table = new html_table();
51         $table->head = array(
52             get_string('storename', 'cache'),
53             get_string('plugin', 'cache'),
54             get_string('storeready', 'cache'),
55             get_string('mappings', 'cache'),
56             get_string('modes', 'cache'),
57             get_string('supports', 'cache'),
58             get_string('locking', 'cache') . ' ' . $this->output->help_icon('locking', 'cache'),
59             get_string('actions', 'cache'),
60         );
61         $table->colclasses = array(
62             'storename',
63             'plugin',
64             'storeready',
65             'mappings',
66             'modes',
67             'supports',
68             'locking',
69             'actions'
70         );
71         $table->data = array();
73         $defaultstoreactions = get_string('defaultstoreactions', 'cache');
75         foreach ($storeinstancesummaries as $name => $storesummary) {
76             $htmlactions = cache_factory::get_administration_display_helper()->get_store_instance_actions($name, $storesummary);
77             $modes = array();
78             foreach ($storesummary['modes'] as $mode => $enabled) {
79                 if ($enabled) {
80                     $modes[] = get_string('mode_'.$mode, 'cache');
81                 }
82             }
84             $supports = array();
85             foreach ($storesummary['supports'] as $support => $enabled) {
86                 if ($enabled) {
87                     $supports[] = get_string('supports_'.$support, 'cache');
88                 }
89             }
91             $info = '';
92             if (!empty($storesummary['default'])) {
93                 $info = $this->output->pix_icon('i/info', $defaultstoreactions, '', array('class' => 'icon'));
94             }
96             $isready = $storesummary['isready'] && $storesummary['requirementsmet'];
97             $readycell = new html_table_cell;
98             if ($isready) {
99                 $readycell->text = $this->output->pix_icon('i/valid', '1');
100             }
102             $storename = $storesummary['name'];
103             if (!empty($storesummary['default'])) {
104                 $storename = get_string('store_'.$storesummary['name'], 'cache');
105             }
106             if (!$isready && (int)$storesummary['mappings'] > 0) {
107                 $readycell->text = $this->output->help_icon('storerequiresattention', 'cache');
108                 $readycell->attributes['class'] = 'store-requires-attention';
109             }
111             $lock = $storesummary['lock']['name'];
112             if (!empty($storesummary['lock']['default'])) {
113                 $lock = get_string($storesummary['lock']['name'], 'cache');
114             }
116             $row = new html_table_row(array(
117                 $storename,
118                 get_string('pluginname', 'cachestore_'.$storesummary['plugin']),
119                 $readycell,
120                 $storesummary['mappings'],
121                 join(', ', $modes),
122                 join(', ', $supports),
123                 $lock,
124                 $info.join(', ', $htmlactions)
125             ));
126             $row->attributes['class'] = 'store-'.$name;
127             if ($storesummary['default']) {
128                 $row->attributes['class'] .= ' default-store';
129             }
130             $table->data[] = $row;
131         }
133         $html  = html_writer::start_tag('div', array('id' => 'core-cache-store-summaries'));
134         $html .= $this->output->heading(get_string('storesummaries', 'cache'), 3);
135         $html .= html_writer::table($table);
136         $html .= html_writer::end_tag('div');
137         return $html;
138     }
140     /**
141      * Displays plugin summaries.
142      *
143      * @param array $storepluginsummaries information about each store plugin as
144      *      returned by core_cache\administration_helper::get_store_plugin_summaries().
145      * @return string HTML
146      */
147     public function store_plugin_summaries(array $storepluginsummaries) {
148         $table = new html_table();
149         $table->head = array(
150             get_string('plugin', 'cache'),
151             get_string('storeready', 'cache'),
152             get_string('stores', 'cache'),
153             get_string('modes', 'cache'),
154             get_string('supports', 'cache'),
155             get_string('actions', 'cache'),
156         );
157         $table->colclasses = array(
158             'plugin',
159             'storeready',
160             'stores',
161             'modes',
162             'supports',
163             'actions'
164         );
165         $table->data = array();
167         foreach ($storepluginsummaries as $name => $plugin) {
168             $htmlactions = cache_factory::get_administration_display_helper()->get_store_plugin_actions($name, $plugin);
170             $modes = array();
171             foreach ($plugin['modes'] as $mode => $enabled) {
172                 if ($enabled) {
173                     $modes[] = get_string('mode_'.$mode, 'cache');
174                 }
175             }
177             $supports = array();
178             foreach ($plugin['supports'] as $support => $enabled) {
179                 if ($enabled) {
180                     $supports[] = get_string('supports_'.$support, 'cache');
181                 }
182             }
184             $row = new html_table_row(array(
185                 $plugin['name'],
186                 ($plugin['requirementsmet']) ? $this->output->pix_icon('i/valid', '1') : '',
187                 $plugin['instances'],
188                 join(', ', $modes),
189                 join(', ', $supports),
190                 join(', ', $htmlactions)
191             ));
193             $row->attributes['class'] = 'plugin-'.$name;
194             $table->data[] = $row;
195         }
197         $html  = html_writer::start_tag('div', array('id' => 'core-cache-plugin-summaries'));
198         $html .= $this->output->heading(get_string('pluginsummaries', 'cache'), 3);
199         $html .= html_writer::table($table);
200         $html .= html_writer::end_tag('div');
201         return $html;
202     }
204     /**
205      * Displays definition summaries.
206      *
207      * @param array $definitionsummaries information about each definition, as returned by
208      *      core_cache\administration_helper::get_definition_summaries().
209      * @param context $context the system context.
210      *
211      * @return string HTML.
212      */
213     public function definition_summaries(array $definitionsummaries, context $context) {
214         $table = new html_table();
215         $table->head = array(
216             get_string('definition', 'cache'),
217             get_string('mode', 'cache'),
218             get_string('component', 'cache'),
219             get_string('area', 'cache'),
220             get_string('mappings', 'cache'),
221             get_string('sharing', 'cache'),
222             get_string('canuselocalstore', 'cache'),
223             get_string('actions', 'cache')
224         );
225         $table->colclasses = array(
226             'definition',
227             'mode',
228             'component',
229             'area',
230             'mappings',
231             'sharing',
232             'canuselocalstore',
233             'actions'
234         );
235         $table->data = array();
237         core_collator::asort_array_of_arrays_by_key($definitionsummaries, 'name');
239         $none = new lang_string('none', 'cache');
240         foreach ($definitionsummaries as $id => $definition) {
241             $htmlactions = cache_factory::get_administration_display_helper()->get_definition_actions($context, $definition);
242             if (!empty($definition['mappings'])) {
243                 $mapping = join(', ', $definition['mappings']);
244             } else {
245                 $mapping = '<em>'.$none.'</em>';
246             }
248             $uselocalcachecol = get_string('no');
249             if ($definition['mode'] != cache_store::MODE_REQUEST) {
250                 if (isset($definition['canuselocalstore']) && $definition['canuselocalstore']) {
251                     $uselocalcachecol = get_string('yes');
252                 }
253             }
255             $row = new html_table_row(array(
256                 $definition['name'],
257                 get_string('mode_'.$definition['mode'], 'cache'),
258                 $definition['component'],
259                 $definition['area'],
260                 $mapping,
261                 join(', ', $definition['selectedsharingoption']),
262                 $uselocalcachecol,
263                 join(', ', $htmlactions)
264             ));
265             $row->attributes['class'] = 'definition-'.$definition['component'].'-'.$definition['area'];
266             $table->data[] = $row;
267         }
269         $html  = html_writer::start_tag('div', array('id' => 'core-cache-definition-summaries'));
270         $html .= $this->output->heading(get_string('definitionsummaries', 'cache'), 3);
271         $html .= html_writer::table($table);
273         $url = new moodle_url('/cache/admin.php', array('action' => 'rescandefinitions', 'sesskey' => sesskey()));
274         $link = html_writer::link($url, get_string('rescandefinitions', 'cache'));
275         $html .= html_writer::tag('div', $link, array('id' => 'core-cache-rescan-definitions'));
277         $html .= html_writer::end_tag('div');
278         return $html;
279     }
281     /**
282      * Displays mode mappings
283      *
284      * @param string $applicationstore
285      * @param string $sessionstore
286      * @param string $requeststore
287      * @param moodle_url $editurl
288      * @return string HTML
289      */
290     public function mode_mappings($applicationstore, $sessionstore, $requeststore, moodle_url $editurl) {
291         $table = new html_table();
292         $table->colclasses = array(
293             'mode',
294             'mapping',
295         );
296         $table->rowclasses = array(
297             'mode_application',
298             'mode_session',
299             'mode_request'
300         );
301         $table->head = array(
302             get_string('mode', 'cache'),
303             get_string('mappings', 'cache'),
304         );
305         $table->data = array(
306             array(get_string('mode_'.cache_store::MODE_APPLICATION, 'cache'), $applicationstore),
307             array(get_string('mode_'.cache_store::MODE_SESSION, 'cache'), $sessionstore),
308             array(get_string('mode_'.cache_store::MODE_REQUEST, 'cache'), $requeststore)
309         );
311         $html = html_writer::start_tag('div', array('id' => 'core-cache-mode-mappings'));
312         $html .= $this->output->heading(get_string('defaultmappings', 'cache'), 3);
313         $html .= html_writer::table($table);
314         $link = html_writer::link($editurl, get_string('editmappings', 'cache'));
315         $html .= html_writer::tag('div', $link, array('class' => 'edit-link'));
316         $html .= html_writer::end_tag('div');
317         return $html;
318     }
320     /**
321      * Display basic information about lock instances.
322      *
323      * @todo Add some actions so that people can configure lock instances.
324      *
325      * @param array $locks
326      * @return string
327      */
328     public function lock_summaries(array $locks) {
329         $table = new html_table();
330         $table->colclasses = array(
331             'name',
332             'type',
333             'default',
334             'uses',
335             'actions'
336         );
337         $table->rowclasses = array(
338             'lock_name',
339             'lock_type',
340             'lock_default',
341             'lock_uses',
342             'lock_actions',
343         );
344         $table->head = array(
345             get_string('lockname', 'cache'),
346             get_string('locktype', 'cache'),
347             get_string('lockdefault', 'cache'),
348             get_string('lockuses', 'cache'),
349             get_string('actions', 'cache')
350         );
351         $table->data = array();
352         $tick = $this->output->pix_icon('i/valid', '');
353         foreach ($locks as $lock) {
354             $actions = array();
355             if ($lock['uses'] === 0 && !$lock['default']) {
356                 $url = new moodle_url('/cache/admin.php', array('lock' => $lock['name'], 'action' => 'deletelock', 'sesskey' => sesskey()));
357                 $actions[] = html_writer::link($url, get_string('delete', 'cache'));
358             }
359             $table->data[] = new html_table_row(array(
360                 new html_table_cell($lock['name']),
361                 new html_table_cell($lock['type']),
362                 new html_table_cell($lock['default'] ? $tick : ''),
363                 new html_table_cell($lock['uses']),
364                 new html_table_cell(join(' ', $actions))
365             ));
366         }
368         $html = html_writer::start_tag('div', array('id' => 'core-cache-lock-summary'));
369         $html .= $this->output->heading(get_string('locksummary', 'cache'), 3);
370         $html .= html_writer::table($table);
371         $html .= html_writer::end_tag('div');
372         return $html;
373     }
375     /**
376      * Renders additional actions for locks, such as Add.
377      *
378      * @return string
379      */
380     public function additional_lock_actions() : string {
381         $url = new moodle_url('/cache/admin.php', array('action' => 'newlockinstance', 'sesskey' => sesskey()));
382         $select = new single_select($url, 'lock', cache_factory::get_administration_display_helper()->get_addable_lock_options());
383         $select->label = get_string('addnewlockinstance', 'cache');
385         $html = html_writer::start_tag('div', array('id' => 'core-cache-lock-additional-actions'));
386         $html .= html_writer::tag('div', $this->output->render($select), array('class' => 'new-instance'));
387         $html .= html_writer::end_tag('div');
388         return $html;
389     }
391     /**
392      * Renders an array of notifications for the cache configuration screen.
393      *
394      * Takes an array of notifications with the form:
395      * $notifications = array(
396      *     array('This is a success message', true),
397      *     array('This is a failure message', false),
398      * );
399      *
400      * @param array $notifications
401      * @return string
402      */
403     public function notifications(array $notifications = array()) {
404         if (count($notifications) === 0) {
405             // There are no notifications to render.
406             return '';
407         }
408         $html = html_writer::start_div('notifications');
409         foreach ($notifications as $notification) {
410             list($message, $notifysuccess) = $notification;
411             $html .= $this->notification($message, ($notifysuccess) ? 'notifysuccess' : 'notifyproblem');
412         }
413         $html .= html_writer::end_div();
414         return $html;
415     }