xref: /template/strap/action/cache.php (revision 37748cd8654635afbeca80942126742f0f4cc346)
1*37748cd8SNickeau<?php
2*37748cd8SNickeau
3*37748cd8SNickeauuse ComboStrap\CacheManager;
4*37748cd8SNickeauuse ComboStrap\Iso8601Date;
5*37748cd8SNickeauuse ComboStrap\PluginUtility;
6*37748cd8SNickeau
7*37748cd8SNickeaurequire_once(__DIR__ . '/../ComboStrap/PluginUtility.php');
8*37748cd8SNickeau
9*37748cd8SNickeau/**
10*37748cd8SNickeau * Can we use the parser cache
11*37748cd8SNickeau */
12*37748cd8SNickeauclass action_plugin_combo_cache extends DokuWiki_Action_Plugin
13*37748cd8SNickeau{
14*37748cd8SNickeau    const COMBO_CACHE_PREFIX = "combo:cache:";
15*37748cd8SNickeau
16*37748cd8SNickeau    /**
17*37748cd8SNickeau     * @param Doku_Event_Handler $controller
18*37748cd8SNickeau     */
19*37748cd8SNickeau    function register(Doku_Event_Handler $controller)
20*37748cd8SNickeau    {
21*37748cd8SNickeau
22*37748cd8SNickeau        /**
23*37748cd8SNickeau         * Log the cache usage and also
24*37748cd8SNickeau         */
25*37748cd8SNickeau        $controller->register_hook('PARSER_CACHE_USE', 'AFTER', $this, 'logCacheUsage', array());
26*37748cd8SNickeau
27*37748cd8SNickeau        $controller->register_hook('PARSER_CACHE_USE', 'BEFORE', $this, 'purgeIfNeeded', array());
28*37748cd8SNickeau
29*37748cd8SNickeau        /**
30*37748cd8SNickeau         * To add the cache result in the header
31*37748cd8SNickeau         */
32*37748cd8SNickeau        $controller->register_hook('TPL_METAHEADER_OUTPUT', 'BEFORE', $this, 'addMeta', array());
33*37748cd8SNickeau
34*37748cd8SNickeau        /**
35*37748cd8SNickeau         * To reset the cache manager
36*37748cd8SNickeau         * between two run in the test
37*37748cd8SNickeau         */
38*37748cd8SNickeau        $controller->register_hook('DOKUWIKI_DONE', 'BEFORE', $this, 'close', array());
39*37748cd8SNickeau
40*37748cd8SNickeau    }
41*37748cd8SNickeau
42*37748cd8SNickeau    /**
43*37748cd8SNickeau     *
44*37748cd8SNickeau     * @param Doku_Event $event
45*37748cd8SNickeau     * @param $params
46*37748cd8SNickeau     */
47*37748cd8SNickeau    function logCacheUsage(Doku_Event $event, $params)
48*37748cd8SNickeau    {
49*37748cd8SNickeau
50*37748cd8SNickeau        /**
51*37748cd8SNickeau         * To log the cache used by bar
52*37748cd8SNickeau         * @var \dokuwiki\Cache\CacheParser $data
53*37748cd8SNickeau         */
54*37748cd8SNickeau        $data = $event->data;
55*37748cd8SNickeau        $result = $event->result;
56*37748cd8SNickeau        $pageId = $data->page;
57*37748cd8SNickeau        $cacheManager = PluginUtility::getCacheManager();
58*37748cd8SNickeau        $cacheManager->addSlot($pageId, $result, $data);
59*37748cd8SNickeau
60*37748cd8SNickeau
61*37748cd8SNickeau    }
62*37748cd8SNickeau
63*37748cd8SNickeau    /**
64*37748cd8SNickeau     *
65*37748cd8SNickeau     * @param Doku_Event $event
66*37748cd8SNickeau     * @param $params
67*37748cd8SNickeau     */
68*37748cd8SNickeau    function purgeIfNeeded(Doku_Event $event, $params)
69*37748cd8SNickeau    {
70*37748cd8SNickeau
71*37748cd8SNickeau        /**
72*37748cd8SNickeau         * No cache for all mode
73*37748cd8SNickeau         * (ie xhtml, instruction)
74*37748cd8SNickeau         */
75*37748cd8SNickeau        $data = &$event->data;
76*37748cd8SNickeau        $pageId = $data->page;
77*37748cd8SNickeau        /**
78*37748cd8SNickeau         * Because of the recursive nature of rendering
79*37748cd8SNickeau         * inside dokuwiki, we just handle the first
80*37748cd8SNickeau         * rendering for a request.
81*37748cd8SNickeau         *
82*37748cd8SNickeau         * The first will be purged, the other one not
83*37748cd8SNickeau         * because they can use the first one
84*37748cd8SNickeau         */
85*37748cd8SNickeau        if (!PluginUtility::getCacheManager()->isCacheLogPresent($pageId, $data->mode)) {
86*37748cd8SNickeau            $expirationStringDate = p_get_metadata($pageId, CacheManager::DATE_CACHE_EXPIRATION_META_KEY, METADATA_DONT_RENDER);
87*37748cd8SNickeau            if ($expirationStringDate !== null) {
88*37748cd8SNickeau
89*37748cd8SNickeau                $expirationDate = Iso8601Date::create($expirationStringDate)->getDateTime();
90*37748cd8SNickeau                $actualDate = new DateTime();
91*37748cd8SNickeau                if ($expirationDate < $actualDate) {
92*37748cd8SNickeau                    /**
93*37748cd8SNickeau                     * As seen in {@link Cache::makeDefaultCacheDecision()}
94*37748cd8SNickeau                     * We request a purge
95*37748cd8SNickeau                     */
96*37748cd8SNickeau                    $data->depends["purge"] = true;
97*37748cd8SNickeau                }
98*37748cd8SNickeau            }
99*37748cd8SNickeau        }
100*37748cd8SNickeau
101*37748cd8SNickeau
102*37748cd8SNickeau    }
103*37748cd8SNickeau
104*37748cd8SNickeau    /**
105*37748cd8SNickeau     * Add HTML meta to be able to debug
106*37748cd8SNickeau     * @param Doku_Event $event
107*37748cd8SNickeau     * @param $params
108*37748cd8SNickeau     */
109*37748cd8SNickeau    function addMeta(Doku_Event $event, $params)
110*37748cd8SNickeau    {
111*37748cd8SNickeau
112*37748cd8SNickeau        $cacheManager = PluginUtility::getCacheManager();
113*37748cd8SNickeau        $slots = $cacheManager->getCacheSlotResults();
114*37748cd8SNickeau        foreach ($slots as $slotId => $modes) {
115*37748cd8SNickeau
116*37748cd8SNickeau            $cachedMode = [];
117*37748cd8SNickeau            foreach ($modes as $mode => $values) {
118*37748cd8SNickeau                if ($values[CacheManager::RESULT_STATUS] === true) {
119*37748cd8SNickeau                    $metaContentData = $mode;
120*37748cd8SNickeau                    if(!PluginUtility::isTest()){
121*37748cd8SNickeau                        /**
122*37748cd8SNickeau                         * @var DateTime $dateModified
123*37748cd8SNickeau                         */
124*37748cd8SNickeau                        $dateModified = $values[CacheManager::DATE_MODIFIED];
125*37748cd8SNickeau                        $metaContentData .= ":". $dateModified->format('Y-m-d\TH:i:s');
126*37748cd8SNickeau                    }
127*37748cd8SNickeau                    $cachedMode[] = $metaContentData;
128*37748cd8SNickeau                }
129*37748cd8SNickeau            }
130*37748cd8SNickeau
131*37748cd8SNickeau            if (sizeof($cachedMode) === 0) {
132*37748cd8SNickeau                $value = "nocache";
133*37748cd8SNickeau            } else {
134*37748cd8SNickeau                sort($cachedMode);
135*37748cd8SNickeau                $value = implode(",", $cachedMode);
136*37748cd8SNickeau            }
137*37748cd8SNickeau
138*37748cd8SNickeau            // Add cache information into the head meta
139*37748cd8SNickeau            // to test
140*37748cd8SNickeau            $event->data["meta"][] = array("name" => self::COMBO_CACHE_PREFIX . $slotId, "content" => hsc($value));
141*37748cd8SNickeau        }
142*37748cd8SNickeau
143*37748cd8SNickeau    }
144*37748cd8SNickeau
145*37748cd8SNickeau    function close(Doku_Event $event, $params)
146*37748cd8SNickeau    {
147*37748cd8SNickeau        CacheManager::close();
148*37748cd8SNickeau    }
149*37748cd8SNickeau
150*37748cd8SNickeau
151*37748cd8SNickeau}
152