1<?php
2/**
3 * Xoops Logger renderer
4 *
5 * You may not change or alter any portion of this comment or credits
6 * of supporting developers from this source code or any supporting source code
7 * which is considered copyrighted (c) material of the original comment or credit authors.
8 * This program is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
11 *
12 * @copyright       (c) 2000-2016 XOOPS Project (www.xoops.org)
13 * @license             GNU GPL 2 (http://www.gnu.org/licenses/gpl-2.0.html)
14 * @package             kernel
15 * @subpackage          logger
16 * @since               2.3.0
17 * @author              Skalpa Keo <skalpa@xoops.org>
18 * @author              Taiwen Jiang <phppp@users.sourceforge.net>
19 *
20 * @todo                Not well written, just keep as it is. Refactored in 3.0
21 */
22defined('XOOPS_ROOT_PATH') || exit('Restricted access');
23
24$ret = '';
25if ($mode === 'popup') {
26    $dump    = $this->dump('');
27    $content = '
28<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
29<head>
30    <meta http-equiv="content-language" content="' . _LANGCODE . '" />
31    <meta http-equiv="content-type" content="text/html; charset=' . _CHARSET . '" />
32    <title>' . $xoopsConfig['sitename'] . ' - ' . _LOGGER_DEBUG . ' </title>
33    <meta name="generator" content="XOOPS" />
34    <link rel="stylesheet" type="text/css" media="all" href="' . xoops_getcss($xoopsConfig['theme_set']) . '" />
35</head>
36<body>' . $dump . '
37    <div style="text-align:center;">
38        <input class="formButton" value="' . _CLOSE . '" type="button" onclick="window.close();" />
39    </div>
40';
41    $ret .= '
42<script type="text/javascript">
43    debug_window = openWithSelfMain("about:blank", "popup", 680, 450, true);
44    debug_window.document.clear();
45';
46    $lines = preg_split("/(\r\n|\r|\n)( *)/", $content);
47    foreach ($lines as $line) {
48        $ret .= "\n" . 'debug_window.document.writeln("' . str_replace(array('"', '</'), array('\"', '<\/'), $line) . '");';
49    }
50    $ret .= '
51    debug_window.focus();
52    debug_window.document.close();
53</script>
54';
55}
56
57$this->addExtra(_LOGGER_INCLUDED_FILES, sprintf(_LOGGER_FILES, count(get_included_files())));
58$memory = 0;
59
60if (function_exists('memory_get_usage')) {
61    $memory = memory_get_usage() . ' bytes';
62} else {
63    if (strtoupper(substr(PHP_OS, 0, 3)) === 'WIN') {
64        $out = array();
65        exec('tasklist /FI "PID eq ' . getmypid() . '" /FO LIST', $out);
66        if (isset($out[5])) {
67            $memory = sprintf(_LOGGER_MEM_ESTIMATED, substr($out[5], strpos($out[5], ':') + 1));
68        }
69    }
70}
71if ($memory) {
72    $this->addExtra(_LOGGER_MEM_USAGE, $memory);
73}
74
75if (empty($mode)) {
76    $views = array('errors', 'deprecated', 'queries', 'blocks', 'extra');
77    $ret .= "\n<div id=\"xo-logger-output\">\n<div id='xo-logger-tabs'>\n";
78    $ret .= "<a href='javascript:xoSetLoggerView(\"none\")'>" . _LOGGER_NONE . "</a>\n";
79    $ret .= "<a href='javascript:xoSetLoggerView(\"\")'>" . _LOGGER_ALL . "</a>\n";
80    foreach ($views as $view) {
81        $count = count($this->$view);
82        $ret .= "<a href='javascript:xoSetLoggerView(\"$view\")'>" . constant('_LOGGER_' . strtoupper($view)) . " ($count)</a>\n";
83    }
84    $count = count($this->logstart);
85    $ret .= "<a href='javascript:xoSetLoggerView(\"timers\")'>" . _LOGGER_TIMERS . "($count)</a>\n";
86    $ret .= "</div>\n";
87}
88
89if (empty($mode) || $mode === 'errors') {
90    $types = array(
91        E_USER_NOTICE  => _LOGGER_E_USER_NOTICE,
92        E_USER_WARNING => _LOGGER_E_USER_WARNING,
93        E_USER_ERROR   => _LOGGER_E_USER_ERROR,
94        E_NOTICE       => _LOGGER_E_NOTICE,
95        E_WARNING      => _LOGGER_E_WARNING,/*E_STRICT       => _LOGGER_E_STRICT*/);
96    $class = 'even';
97    $ret .= '<table id="xo-logger-errors" class="outer"><tr><th>' . _LOGGER_ERRORS . '</th></tr>';
98    foreach ($this->errors as $error) {
99        $ret .= "\n<tr><td class='$class'>";
100        $ret .= isset($types[$error['errno']]) ? $types[$error['errno']] : _LOGGER_UNKNOWN;
101        $ret .= ': ';
102        $ret .= sprintf(_LOGGER_FILELINE, $this->sanitizePath($error['errstr']), $this->sanitizePath($error['errfile']), $error['errline']);
103        $ret .= "<br>\n</td></tr>";
104        $class = ($class === 'odd') ? 'even' : 'odd';
105    }
106    $ret .= "\n</table>\n";
107}
108
109if (empty($mode) || $mode === 'deprecated') {
110    $class = 'even';
111    $ret .= '<table id="xo-logger-deprecated" class="outer"><tr><th>' . _LOGGER_DEPRECATED . '</th></tr>';
112    foreach ($this->deprecated as $message) {
113        $ret .= "\n<tr><td class='$class'>";
114        $ret .= $message;
115        $ret .= "<br>\n</td></tr>";
116        $class = ($class === 'odd') ? 'even' : 'odd';
117    }
118    $ret .= "\n</table>\n";
119}
120
121if (empty($mode) || $mode === 'queries') {
122    $class = 'even';
123    $ret .= '<table id="xo-logger-queries" class="outer"><tr><th>' . _LOGGER_QUERIES . '</th></tr>';
124    $xoopsDB = XoopsDatabaseFactory::getDatabaseConnection();
125    $pattern = '/\b' . preg_quote($xoopsDB->prefix()) . '\_/i';
126
127    foreach ($this->queries as $q) {
128        $sql        = preg_replace($pattern, '', $q['sql']);
129        $query_time = isset($q['query_time']) ? sprintf('%0.6f - ', $q['query_time']) : '';
130
131        if (isset($q['error'])) {
132            $ret .= '<tr class="' . $class . '"><td><span style="color:#ff0000;">' . $query_time . htmlentities($sql) . '<br><strong>Error number:</strong> ' . $q['errno'] . '<br><strong>Error message:</strong> ' . $q['error'] . '</span></td></tr>';
133        } else {
134            $ret .= '<tr class="' . $class . '"><td>' . $query_time . htmlentities($sql) . '</td></tr>';
135        }
136
137        $class = ($class === 'odd') ? 'even' : 'odd';
138    }
139    $ret .= '<tr class="foot"><td>' . _LOGGER_TOTAL . ': <span style="color:#ff0000;">' . count($this->queries) . '</span></td></tr></table>';
140}
141if (empty($mode) || $mode === 'blocks') {
142    $class = 'even';
143    $ret .= '<table id="xo-logger-blocks" class="outer"><tr><th colspan="2">' . _LOGGER_BLOCKS . '</th></tr>';
144    foreach ($this->blocks as $b) {
145        if ($b['cached']) {
146            $ret .= '<tr><td class="' . $class . '"><strong>' . $b['name'] . ':</strong> ' . sprintf(_LOGGER_CACHED, (int)$b['cachetime']) . '</td></tr>';
147        } else {
148            $ret .= '<tr><td class="' . $class . '"><strong>' . $b['name'] . ':</strong> ' . _LOGGER_NOT_CACHED . '</td></tr>';
149        }
150        $class = ($class === 'odd') ? 'even' : 'odd';
151    }
152    $ret .= '<tr class="foot"><td>' . _LOGGER_TOTAL . ': <span style="color:#ff0000;">' . count($this->blocks) . '</span></td></tr></table>';
153}
154if (empty($mode) || $mode === 'extra') {
155    $class = 'even';
156    $ret .= '<table id="xo-logger-extra" class="outer"><tr><th colspan="2">' . _LOGGER_EXTRA . '</th></tr>';
157    foreach ($this->extra as $ex) {
158        $ret .= '<tr><td class="' . $class . '"><strong>';
159        $ret .= htmlspecialchars($ex['name']) . ':</strong> ' . htmlspecialchars($ex['msg']);
160        $ret .= '</td></tr>';
161        $class = ($class === 'odd') ? 'even' : 'odd';
162    }
163    $ret .= '</table>';
164}
165if (empty($mode) || $mode === 'timers') {
166    $class = 'even';
167    $ret .= '<table id="xo-logger-timers" class="outer"><tr><th colspan="2">' . _LOGGER_TIMERS . '</th></tr>';
168    foreach ($this->logstart as $k => $v) {
169        $ret .= '<tr><td class="' . $class . '"><strong>';
170        $ret .= sprintf(_LOGGER_TIMETOLOAD, htmlspecialchars($k) . '</strong>', '<span style="color:#ff0000;">' . sprintf('%.03f', $this->dumpTime($k)) . '</span>');
171        $ret .= '</td></tr>';
172        $class = ($class === 'odd') ? 'even' : 'odd';
173    }
174    $ret .= '</table>';
175}
176
177if (empty($mode)) {
178    $ret .= <<<EOT
179</div>
180<script type="text/javascript">
181    function xoLogCreateCookie(name,value,days)
182    {
183        if (days) {
184            var date = new Date();
185            date.setTime(date.getTime()+(days*24*60*60*1000));
186            var expires = "; expires="+date.toGMTString();
187        } else var expires = "";
188        document.cookie = name+"="+value+expires+"; path=/";
189    }
190    function xoLogReadCookie(name)
191    {
192        var nameEQ = name + "=";
193        var ca = document.cookie.split(';');
194        for (var i=0;i < ca.length;i++) {
195            var c = ca[i];
196            while (c.charAt(0)==' ') c = c.substring(1,c.length);
197            if (c.indexOf(nameEQ) == 0) return c.substring(nameEQ.length,c.length);
198        }
199
200        return null;
201    }
202    function xoLogEraseCookie(name)
203    {
204        createCookie(name,"",-1);
205    }
206    function xoSetLoggerView( name )
207    {
208        var log = document.getElementById( "xo-logger-output" );
209        if ( !log ) return null;
210        var i, elt;
211        for (i=0; i!=log.childNodes.length; i++) {
212            elt = log.childNodes[i];
213            if ( elt.tagName && elt.tagName.toLowerCase() != 'script' && elt.id != "xo-logger-tabs" ) {
214                elt.style.display = ( !name || elt.id == "xo-logger-" + name ) ? "block" : "none";
215            }
216        }
217        xoLogCreateCookie( 'XOLOGGERVIEW', name, 1 );
218    }
219    xoSetLoggerView( xoLogReadCookie( 'XOLOGGERVIEW' ) );
220</script>
221
222EOT;
223}
224