1<?php 2 3 4use ComboStrap\PluginUtility; 5 6if (!defined('DOKU_INC')) die(); 7 8/** 9 * Class action_plugin_combo_css 10 * Delete Backend CSS for front-end 11 * 12 * Bug: 13 * * https://datacadamia.comlighthouse - no interwiki 14 * 15 * A call to /lib/exe/css.php?t=template&tseed=time() 16 * 17 * * t is the template 18 * 19 * * tseed is md5 of modified time of the below config file set at {@link tpl_metaheaders()} 20 * 21 * * conf/dokuwiki.php 22 * * conf/local.php 23 * * conf/local.protected.php 24 * * conf/tpl/strap/style.ini 25 * 26 */ 27class action_plugin_combo_css extends DokuWiki_Action_Plugin 28{ 29 30 /** 31 * Conf 32 */ 33 const CONF_ENABLE_MINIMAL_FRONTEND_STYLESHEET = 'enableMinimalFrontEndStylesheet'; 34 const CONF_DISABLE_DOKUWIKI_STYLESHEET = 'disableDokuwikiStylesheet'; 35 36 /** 37 * Front end or backend 38 */ 39 const WHICH_END_KEY = 'end'; 40 const VALUE_FRONT = 'front'; 41 const VALUE_BACK = 'back'; 42 43 /** 44 * List of excluded plugin 45 */ 46 const EXCLUDED_PLUGINS = array( 47 "acl", 48 "authplain", 49 "changes", 50 "config", 51 "extension", 52 "info", 53 "move", 54 "popularity", 55 "revert", 56 "safefnrecode", 57 "searchindex", 58 "sqlite", 59 "upgrade", 60 "usermanager" 61 ); 62 63 /** 64 * Registers a callback function for a given event 65 * 66 * @param Doku_Event_Handler $controller DokuWiki's event controller object 67 * @return void 68 * 69 * To fire this event 70 * * Ctrl+Shift+R to disable browser cache 71 * 72 */ 73 public function register(Doku_Event_Handler $controller) 74 { 75 76 77 /** 78 * Delete the all.css file due to `group` class 79 */ 80 $controller->register_hook('CSS_STYLES_INCLUDED', 'BEFORE', $this, 'handle_css_styles'); 81 82 /** 83 * For front-end/public only 84 */ 85 $urlPropertyValue = PluginUtility::getPropertyValue(self::WHICH_END_KEY, self::VALUE_BACK); 86 if (PluginUtility::getRequestScript() == "css.php" && $urlPropertyValue == self::VALUE_FRONT) { 87 /** 88 * The process follows the following steps: 89 * * With CSS_STYLES_INCLUDED, you choose the file that you want 90 * * then with CSS_CACHE_USE, you can change the cache key name 91 */ 92 $controller->register_hook('CSS_STYLES_INCLUDED', 'BEFORE', $this, 'handle_front_css_styles'); 93 $controller->register_hook('CSS_CACHE_USE', 'BEFORE', $this, 'handle_css_cache'); 94 } 95 96 /** 97 * Add a property to the URL to create two CSS file: 98 * * one public 99 * * one private (logged in) 100 */ 101 if (PluginUtility::getRequestScript() == "doku.php") { 102 $controller->register_hook('TPL_METAHEADER_OUTPUT', 'BEFORE', $this, 'handle_css_metaheader'); 103 } 104 105 } 106 107 /** 108 * @param Doku_Event $event 109 * @param $param 110 * 111 * Add query parameter to the CSS header call. ie 112 * <link rel="preload" href="/lib/exe/css.php?t=template&tseed=8e31090353c8fcf80aa6ff0ea9bf3746" as="style"> 113 * to indicate if the page that calls the css is from a user that is logged in or not: 114 * * public vs private 115 * * ie frontend vs backend 116 */ 117 public function handle_css_metaheader(Doku_Event &$event, $param) 118 { 119 $disableDokuwikiStylesheet = $this->getConf(self::CONF_DISABLE_DOKUWIKI_STYLESHEET, false); 120 $enableMinimalFrontEnd = $this->getConf(self::CONF_ENABLE_MINIMAL_FRONTEND_STYLESHEET, false); 121 122 if (empty($_SERVER['REMOTE_USER']) && ($disableDokuwikiStylesheet || $enableMinimalFrontEnd)) { 123 $links = &$event->data['link']; 124 foreach ($links as $key => &$link) { 125 $pos = strpos($link['href'], 'css.php'); 126 if ($pos !== false) { 127 128 if ($disableDokuwikiStylesheet) { 129 unset($links[$key]); 130 return; 131 } 132 133 if ($enableMinimalFrontEnd) { 134 $link['href'] .= '&' . self::WHICH_END_KEY . '=' . self::VALUE_FRONT . ''; 135 return; 136 } 137 138 } 139 } 140 } 141 142 } 143 144 /** 145 * 146 * @param Doku_Event $event event object by reference 147 * @param mixed $param [the parameters passed as fifth argument to register_hook() when this 148 * handler was registered] 149 * @return void 150 * 151 * Change the key of the cache. 152 * 153 * The default key can be seen in the {@link css_out()} function 154 * when a new cache is created (ie new cache(key,ext) 155 * 156 * This is only called when this is a front call, see {@link register()} 157 * 158 * @see <a href="https://github.com/i-net-software/dokuwiki-plugin-lightweightcss/blob/master/action.php#L122">Credits</a> 159 */ 160 public function handle_css_cache(Doku_Event &$event, $param) 161 { 162 163 $enableMinimalFrontEnd = $this->getConf(self::CONF_ENABLE_MINIMAL_FRONTEND_STYLESHEET, false); 164 if ($enableMinimalFrontEnd) { 165 $propertyValue = PluginUtility::getPropertyValue(self::WHICH_END_KEY); 166 if ($propertyValue == self::VALUE_FRONT) { 167 $event->data->key .= self::VALUE_FRONT; 168 $event->data->cache = getCacheName($event->data->key, $event->data->ext); 169 } 170 } 171 172 } 173 174 /** 175 * Handle the front CSS script list. The script would be fit to do even more stuff / types 176 * but handles only admin and default currently. 177 * 178 * @param Doku_Event $event event object by reference 179 * @param mixed $param [the parameters passed as fifth argument to register_hook() when this 180 * handler was registered] 181 * @return void 182 */ 183 public function handle_front_css_styles(Doku_Event &$event, $param) 184 { 185 /** 186 * Trick to be able to test 187 * The {@link register()} function is called only once when a test 188 * is started 189 * we change the value to see if the payload is less big 190 */ 191 $propertyValue = PluginUtility::getPropertyValue(self::WHICH_END_KEY); 192 if ($propertyValue == self::VALUE_BACK) { 193 return; 194 } 195 196 197 /** 198 * There is one call by: 199 * * mediatype (ie scree, all, print, speech) 200 * * and one call for the dokuwiki default 201 */ 202 switch ($event->data['mediatype']) { 203 204 case 'print': 205 case 'screen': 206 case 'all': 207 $filteredDataFiles = array(); 208 $files = $event->data['files']; 209 foreach ($files as $file => $fileDirectory) { 210 // lib styles 211 if (strpos($fileDirectory, 'lib/styles')) { 212 // Geshi (syntax highlighting) and basic style of doku, we keep. 213 $filteredDataFiles[$file] = $fileDirectory; 214 continue; 215 } 216 // No Css from lib scripts 217 // Jquery is here 218 if (strpos($fileDirectory, 'lib/scripts')) { 219 continue; 220 } 221 // Excluded 222 $isExcluded = false; 223 foreach (self::EXCLUDED_PLUGINS as $plugin) { 224 if (strpos($file, 'lib/plugins/' . $plugin)) { 225 $isExcluded = true; 226 break; 227 } 228 } 229 if (!$isExcluded) { 230 $filteredDataFiles[$file] = $fileDirectory; 231 } 232 } 233 234 $event->data['files'] = $filteredDataFiles; 235 236 break; 237 238 case 'speech': 239 $event->preventDefault(); 240 break; 241 case 'DW_DEFAULT': 242 // Interwiki styles are here, we keep (in the lib/css.php file) 243 break; 244 245 } 246 } 247 248 /** 249 * Handle all CSS script list. 250 * 251 * @param Doku_Event $event event object by reference 252 * @param mixed $param [the parameters passed as fifth argument to register_hook() when this 253 * handler was registered] 254 * @return void 255 */ 256 public function handle_css_styles(Doku_Event &$event, $param) 257 { 258 259 /** 260 * There is one call by: 261 * * mediatype (ie scree, all, print, speech) 262 * * and one call for the dokuwiki default 263 */ 264 switch ($event->data['mediatype']) { 265 266 case 'print': 267 case 'screen': 268 case 'all': 269 /** 270 * Get the file by reference 271 */ 272 $files = &$event->data['files']; 273 /** 274 * Strap has a copy of 275 * the all.css without the group clear fix 276 */ 277 global $conf; 278 if ($conf['template'] == PluginUtility::TEMPLATE_STRAP_NAME) { 279 foreach ($files as $file => $dir) { 280 if (strpos($file, 'lib/styles/all.css')) { 281 unset($files[$file]); 282 } 283 } 284 } 285 break; 286 } 287 } 288} 289 290 291