1<?php
2/**
3 * Mikio CSS/LESS Engine
4 *
5 * @link    http://dokuwiki.org/template:mikio
6 * @author  James Collins <james.collins@outlook.com.au>
7 * @license GPLv2 (http://www.gnu.org/licenses/gpl-2.0.html)
8 */
9
10require(dirname(__FILE__) . '/inc/polyfill-ctype.php');
11
12if(!class_exists('lessc')) {
13    require(dirname(__FILE__) . '/inc/stemmechanics/lesserphp/lessc.inc.php');
14}
15
16if(!function_exists('getallheaders')) {
17    function getallheaders() {
18        $headers = [];
19        foreach($_SERVER as $name => $value) {
20            if(substr($name, 0, 5) == 'HTTP_') {
21                $headers[str_replace(' ', '-', ucwords(strtolower(str_replace('_', ' ', substr($name, 5)))))] = $value;
22            }
23        }
24        return $headers;
25    }
26}
27
28if(!function_exists('platformSlashes')) {
29    function platformSlashes($path) {
30        return str_replace('/', DIRECTORY_SEPARATOR, $path);
31    }
32}
33
34try {
35    if(isset($_GET['css'])) {
36        $baseDir = platformSlashes(dirname(__FILE__) . '/');
37        $cssFile = platformSlashes(realpath($baseDir . $_GET['css']));
38
39        if(strpos($cssFile, $baseDir) === 0 && file_exists($cssFile)) {
40            $rawVars = Array();
41            $file = 'style.ini';
42            if(file_exists($file)) {
43                $rawVars = arrayDeepMerge($rawVars, parse_ini_file($file, TRUE));
44            }
45
46            $file = platformSlashes('../../../conf/tpl/mikio/style.ini');
47            if(file_exists($file)) {
48                $rawVars = arrayDeepMerge($rawVars, parse_ini_file($file, TRUE));
49            }
50
51            $file = ($_SERVER['DOCUMENT_ROOT'] . '/conf/tpl/mikio/style.ini');
52            if(file_exists($file)) {
53                $rawVars = arrayDeepMerge($rawVars, parse_ini_file($file, TRUE));
54            }
55
56            $css = file_get_contents($cssFile);
57
58            header('Content-Type: text/css; charset=utf-8');
59
60            $less = new lessc();
61            $less->setPreserveComments(false);
62
63            $vars = Array();
64            if(isset($rawVars['replacements'])) {
65                foreach($rawVars['replacements'] as $key=>$val) {
66                    if(substr($key, 0, 2) == '__' && substr($key, -2) == '__') {
67                        $vars['ini_' . substr($key, 2, -2)] = $val;
68                    }
69                }
70            }
71
72            if(count($vars) > 0) {
73                $less->setVariables($vars);
74            }
75
76            $css = $less->compile($css);
77            echo $css;
78        } else {
79            header('HTTP/1.1 404 Not Found');
80            echo "The requested file could not be found";
81        }
82    } else {
83        header('HTTP/1.1 404 Not Found');
84        echo "The requested file could not be found";
85    }
86}
87catch(Exception $e) {
88    header('Content-Type: text/css; charset=utf-8');
89    $cssFile = file_get_contents(dirname(__FILE__) . '/assets/mikio.css');
90    $exceptionComment = "\n\n/** An exception occurred in the Mikio Less engine:\n\n " . $e->getMessage() . "\n\n*/";
91
92    // Find the position of the first comment in the CSS file
93    $pos = strpos($cssFile, '*/');
94
95    // Insert the exception comment after the first comment
96    $modifiedCSSFile = substr_replace($cssFile, $exceptionComment, $pos + 2, 0);
97
98    echo $modifiedCSSFile;
99}
100
101function arrayDeepMerge($arr1, $arr2) {
102    foreach ($arr2 as $key => $value){
103        if(array_key_exists($key, $arr1)) {
104            $arr1[$key] = array_merge($arr1[$key], $value);
105        } else {
106            $arr1[$key] = $value;
107        }
108    }
109    return $arr1;
110}