xref: /plugin/statistics/admin.php (revision 211caa5d3906ac05d560e9ce5a3171926bbb603c)
11878f16fSAndreas Gohr<?php
2a8acb244SAndreas Gohr
3*211caa5dSAndreas Gohr// phpcs:disable PSR1.Methods.CamelCapsMethodName.NotCamelCaps
4a8acb244SAndreas Gohruse dokuwiki\Extension\AdminPlugin;
5a8acb244SAndreas Gohr
61878f16fSAndreas Gohr/**
71878f16fSAndreas Gohr * statistics plugin
81878f16fSAndreas Gohr *
91878f16fSAndreas Gohr * @license    GPL 2 (http://www.gnu.org/licenses/gpl.html)
106b6f8822SAndreas Gohr * @author     Andreas Gohr <gohr@splitbrain.org>
111878f16fSAndreas Gohr */
12a8acb244SAndreas Gohrclass admin_plugin_statistics extends AdminPlugin
13a8acb244SAndreas Gohr{
1433a136e5SAndreas Gohr    /** @var string the currently selected page */
15a901d721SAndreas Gohr    protected $opt = '';
1633a136e5SAndreas Gohr
1733a136e5SAndreas Gohr    /** @var string from date in YYYY-MM-DD */
18a901d721SAndreas Gohr    protected $from = '';
1933a136e5SAndreas Gohr    /** @var string to date in YYYY-MM-DD */
20a901d721SAndreas Gohr    protected $to = '';
2133a136e5SAndreas Gohr    /** @var int Offset to use when displaying paged data */
2233a136e5SAndreas Gohr    protected $start = 0;
2333a136e5SAndreas Gohr
2433a136e5SAndreas Gohr    /** @var helper_plugin_statistics */
2533a136e5SAndreas Gohr    protected $hlp;
2633a136e5SAndreas Gohr
27a901d721SAndreas Gohr    /**
28a901d721SAndreas Gohr     * Available statistic pages
29a901d721SAndreas Gohr     */
30483101d3SAndreas Gohr    protected $pages = [
31483101d3SAndreas Gohr        'dashboard' => 1,
32483101d3SAndreas Gohr        'content' => ['page', 'edits', 'images', 'downloads', 'history'],
33483101d3SAndreas Gohr        'users' => ['topuser', 'topeditor', 'topgroup', 'topgroupedit', 'seenusers'],
34483101d3SAndreas Gohr        'links' => ['referer', 'newreferer', 'outlinks'],
35483101d3SAndreas Gohr        'search' => ['searchengines', 'searchphrases', 'searchwords', 'internalsearchphrases', 'internalsearchwords'],
36483101d3SAndreas Gohr        'technology' => ['browsers', 'os', 'countries', 'resolution', 'viewport']
37483101d3SAndreas Gohr    ];
381878f16fSAndreas Gohr
3981ff4c3aSAndreas Gohr    /** @var array keeps a list of all real content pages, generated from above array */
40a8acb244SAndreas Gohr    protected $allowedpages = [];
4181ff4c3aSAndreas Gohr
421878f16fSAndreas Gohr    /**
436b6f8822SAndreas Gohr     * Initialize the helper
446b6f8822SAndreas Gohr     */
45a8acb244SAndreas Gohr    public function __construct()
46a8acb244SAndreas Gohr    {
476b6f8822SAndreas Gohr        $this->hlp = plugin_load('helper', 'statistics');
4881ff4c3aSAndreas Gohr
4981ff4c3aSAndreas Gohr        // build a list of pages
5081ff4c3aSAndreas Gohr        foreach ($this->pages as $key => $val) {
5181ff4c3aSAndreas Gohr            if (is_array($val)) {
5281ff4c3aSAndreas Gohr                $this->allowedpages = array_merge($this->allowedpages, $val);
5381ff4c3aSAndreas Gohr            } else {
5481ff4c3aSAndreas Gohr                $this->allowedpages[] = $key;
5581ff4c3aSAndreas Gohr            }
5681ff4c3aSAndreas Gohr        }
576b6f8822SAndreas Gohr    }
586b6f8822SAndreas Gohr
596b6f8822SAndreas Gohr    /**
601878f16fSAndreas Gohr     * Access for managers allowed
611878f16fSAndreas Gohr     */
62a8acb244SAndreas Gohr    public function forAdminOnly()
63a8acb244SAndreas Gohr    {
641878f16fSAndreas Gohr        return false;
651878f16fSAndreas Gohr    }
661878f16fSAndreas Gohr
671878f16fSAndreas Gohr    /**
681878f16fSAndreas Gohr     * return sort order for position in admin menu
691878f16fSAndreas Gohr     */
70a8acb244SAndreas Gohr    public function getMenuSort()
71a8acb244SAndreas Gohr    {
726b6f8822SAndreas Gohr        return 350;
731878f16fSAndreas Gohr    }
741878f16fSAndreas Gohr
751878f16fSAndreas Gohr    /**
761878f16fSAndreas Gohr     * handle user request
771878f16fSAndreas Gohr     */
78a8acb244SAndreas Gohr    public function handle()
79a8acb244SAndreas Gohr    {
80483101d3SAndreas Gohr        global $INPUT;
81483101d3SAndreas Gohr        $this->opt = preg_replace('/[^a-z]+/', '', $INPUT->str('opt'));
8281ff4c3aSAndreas Gohr        if (!in_array($this->opt, $this->allowedpages)) $this->opt = 'dashboard';
83a901d721SAndreas Gohr
84483101d3SAndreas Gohr        $this->start = $INPUT->int('s');
85483101d3SAndreas Gohr        $this->setTimeframe($INPUT->str('f', date('Y-m-d')), $INPUT->str('t', date('Y-m-d')));
86e8699bceSAndreas Gohr    }
8795eb68e6SAndreas Gohr
88e8699bceSAndreas Gohr    /**
89e8699bceSAndreas Gohr     * set limit clause
90e8699bceSAndreas Gohr     */
91a8acb244SAndreas Gohr    public function setTimeframe($from, $to)
92a8acb244SAndreas Gohr    {
93047fcb0fSAndreas Gohr        // swap if wrong order
94a8acb244SAndreas Gohr        if ($from > $to) [$from, $to] = [$to, $from];
95047fcb0fSAndreas Gohr
96*211caa5dSAndreas Gohr        $this->hlp->getQuery()->setTimeFrame($from, $to);
97e8699bceSAndreas Gohr        $this->from = $from;
98e8699bceSAndreas Gohr        $this->to = $to;
991878f16fSAndreas Gohr    }
1001878f16fSAndreas Gohr
1011878f16fSAndreas Gohr    /**
10279b4a855SAndreas Gohr     * Output the Statistics
1031878f16fSAndreas Gohr     */
104a8acb244SAndreas Gohr    public function html()
105a8acb244SAndreas Gohr    {
106b0cf2118SAnna Dabrowska        echo '<script src="' . DOKU_BASE . 'lib/plugins/statistics/lib/chart.js"></script>';
107b0cf2118SAnna Dabrowska        echo '<script src="' . DOKU_BASE . 'lib/plugins/statistics/lib/chartjs-plugin-datalabels.js"></script>';
108b0cf2118SAnna Dabrowska
1091d2d78ccSAndreas Gohr        echo '<div id="plugin__statistics">';
1100c3b1e44SAndreas Gohr        echo '<h1>' . $this->getLang('menu') . '</h1>';
111264f1744SAndreas Gohr        $this->html_timeselect();
112441bfb8eSAndreas Gohr        tpl_flush();
113264f1744SAndreas Gohr
11479b4a855SAndreas Gohr        $method = 'html_' . $this->opt;
11579b4a855SAndreas Gohr        if (method_exists($this, $method)) {
116a901d721SAndreas Gohr            echo '<div class="plg_stats_' . $this->opt . '">';
117a901d721SAndreas Gohr            echo '<h2>' . $this->getLang($this->opt) . '</h2>';
11879b4a855SAndreas Gohr            $this->$method();
119a901d721SAndreas Gohr            echo '</div>';
12014d99ec0SAndreas Gohr        }
1211d2d78ccSAndreas Gohr        echo '</div>';
12214d99ec0SAndreas Gohr    }
12314d99ec0SAndreas Gohr
1246b6f8822SAndreas Gohr    /**
1256b6f8822SAndreas Gohr     * Return the TOC
1266b6f8822SAndreas Gohr     *
1276b6f8822SAndreas Gohr     * @return array
1286b6f8822SAndreas Gohr     */
129a8acb244SAndreas Gohr    public function getTOC()
130a8acb244SAndreas Gohr    {
131a8acb244SAndreas Gohr        $toc = [];
13281ff4c3aSAndreas Gohr        foreach ($this->pages as $key => $info) {
13381ff4c3aSAndreas Gohr            if (is_array($info)) {
13481ff4c3aSAndreas Gohr                $toc[] = html_mktocitem(
13581ff4c3aSAndreas Gohr                    '',
13681ff4c3aSAndreas Gohr                    $this->getLang($key),
13781ff4c3aSAndreas Gohr                    1,
13881ff4c3aSAndreas Gohr                    ''
13947ffcf7dSAndreas Gohr                );
14081ff4c3aSAndreas Gohr
14181ff4c3aSAndreas Gohr                foreach ($info as $page) {
14281ff4c3aSAndreas Gohr                    $toc[] = html_mktocitem(
143*211caa5dSAndreas Gohr                        '?do=admin&amp;page=statistics&amp;opt=' . $page .
144*211caa5dSAndreas Gohr                        '&amp;f=' . $this->from .
145*211caa5dSAndreas Gohr                        '&amp;t=' . $this->to,
14681ff4c3aSAndreas Gohr                        $this->getLang($page),
14781ff4c3aSAndreas Gohr                        2,
14881ff4c3aSAndreas Gohr                        ''
14981ff4c3aSAndreas Gohr                    );
15081ff4c3aSAndreas Gohr                }
15181ff4c3aSAndreas Gohr            } else {
15281ff4c3aSAndreas Gohr                $toc[] = html_mktocitem(
153*211caa5dSAndreas Gohr                    '?do=admin&amp;page=statistics&amp;opt=' . $key .
154*211caa5dSAndreas Gohr                    '&amp;f=' . $this->from .
155*211caa5dSAndreas Gohr                    '&amp;t=' . $this->to,
15681ff4c3aSAndreas Gohr                    $this->getLang($key),
15781ff4c3aSAndreas Gohr                    1,
15881ff4c3aSAndreas Gohr                    ''
15981ff4c3aSAndreas Gohr                );
16081ff4c3aSAndreas Gohr            }
16147ffcf7dSAndreas Gohr        }
16247ffcf7dSAndreas Gohr        return $toc;
1639da6395dSAndreas Gohr    }
1649da6395dSAndreas Gohr
165a8acb244SAndreas Gohr    public function html_graph($name, $width, $height)
166a8acb244SAndreas Gohr    {
167*211caa5dSAndreas Gohr        $this->hlp->getGraph($this->from, $this->to, $width, $height)->$name();
168dc7b1e5eSAndreas Gohr    }
169dc7b1e5eSAndreas Gohr
1706b6f8822SAndreas Gohr    /**
1716b6f8822SAndreas Gohr     * Outputs pagination links
1726b6f8822SAndreas Gohr     *
17333a136e5SAndreas Gohr     * @param int $limit
17433a136e5SAndreas Gohr     * @param int $next
1756b6f8822SAndreas Gohr     */
176a8acb244SAndreas Gohr    public function html_pager($limit, $next)
177a8acb244SAndreas Gohr    {
178*211caa5dSAndreas Gohr        $params = [
179*211caa5dSAndreas Gohr            'do' => 'admin',
180*211caa5dSAndreas Gohr            'page' => 'statistics',
181*211caa5dSAndreas Gohr            'opt' => $this->opt,
182*211caa5dSAndreas Gohr            'f' => $this->from,
183*211caa5dSAndreas Gohr            't' => $this->to,
184*211caa5dSAndreas Gohr        ];
1852507f8e0SAndreas Gohr
186*211caa5dSAndreas Gohr        echo '<div class="plg_stats_pager">';
1872507f8e0SAndreas Gohr        if ($this->start > 0) {
1882507f8e0SAndreas Gohr            $go = max($this->start - $limit, 0);
189*211caa5dSAndreas Gohr            $params['s'] = $go;
190*211caa5dSAndreas Gohr            echo '<a href="?' . buildURLparams($params) . '" class="prev button">' . $this->getLang('prev') . '</a>';
1912507f8e0SAndreas Gohr        }
1922507f8e0SAndreas Gohr
1932507f8e0SAndreas Gohr        if ($next) {
1942507f8e0SAndreas Gohr            $go = $this->start + $limit;
195*211caa5dSAndreas Gohr            $params['s'] = $go;
196*211caa5dSAndreas Gohr            echo '<a href="?' . buildURLparams($params) . '" class="next button">' . $this->getLang('next') . '</a>';
1972507f8e0SAndreas Gohr        }
1982507f8e0SAndreas Gohr        echo '</div>';
1992507f8e0SAndreas Gohr    }
2002507f8e0SAndreas Gohr
201264f1744SAndreas Gohr    /**
202264f1744SAndreas Gohr     * Print the time selection menu
203264f1744SAndreas Gohr     */
204a8acb244SAndreas Gohr    public function html_timeselect()
205a8acb244SAndreas Gohr    {
206483101d3SAndreas Gohr        $quick = [
207483101d3SAndreas Gohr            'today' => date('Y-m-d'),
208483101d3SAndreas Gohr            'last1' => date('Y-m-d', time() - (60 * 60 * 24)),
209483101d3SAndreas Gohr            'last7' => date('Y-m-d', time() - (60 * 60 * 24 * 7)),
210483101d3SAndreas Gohr            'last30' => date('Y-m-d', time() - (60 * 60 * 24 * 30)),
211483101d3SAndreas Gohr        ];
212483101d3SAndreas Gohr
21314d99ec0SAndreas Gohr
214264f1744SAndreas Gohr        echo '<div class="plg_stats_timeselect">';
2156985b606SAndreas Gohr        echo '<span>' . $this->getLang('time_select') . '</span> ';
216264f1744SAndreas Gohr
217047fcb0fSAndreas Gohr        echo '<form action="' . DOKU_SCRIPT . '" method="get">';
218264f1744SAndreas Gohr        echo '<input type="hidden" name="do" value="admin" />';
219264f1744SAndreas Gohr        echo '<input type="hidden" name="page" value="statistics" />';
220264f1744SAndreas Gohr        echo '<input type="hidden" name="opt" value="' . $this->opt . '" />';
221483101d3SAndreas Gohr        echo '<input type="date" name="f" value="' . $this->from . '" class="edit" />';
222483101d3SAndreas Gohr        echo '<input type="date" name="t" value="' . $this->to . '" class="edit" />';
223264f1744SAndreas Gohr        echo '<input type="submit" value="go" class="button" />';
22414d99ec0SAndreas Gohr        echo '</form>';
225264f1744SAndreas Gohr
2266985b606SAndreas Gohr        echo '<ul>';
227483101d3SAndreas Gohr        foreach ($quick as $name => $time) {
228*211caa5dSAndreas Gohr            $url = buildURLparams([
229*211caa5dSAndreas Gohr                'do' => 'admin',
230*211caa5dSAndreas Gohr                'page' => 'statistics',
231*211caa5dSAndreas Gohr                'opt' => $this->opt,
232*211caa5dSAndreas Gohr                'f' => $time,
233*211caa5dSAndreas Gohr                't' => $quick['today'],
234*211caa5dSAndreas Gohr            ]);
235*211caa5dSAndreas Gohr
2366985b606SAndreas Gohr            echo '<li>';
237*211caa5dSAndreas Gohr            echo '<a href="?' . $url . '">';
238483101d3SAndreas Gohr            echo $this->getLang('time_' . $name);
2396985b606SAndreas Gohr            echo '</a>';
2406985b606SAndreas Gohr            echo '</li>';
2416985b606SAndreas Gohr        }
2426985b606SAndreas Gohr        echo '</ul>';
2436985b606SAndreas Gohr
244264f1744SAndreas Gohr        echo '</div>';
24514d99ec0SAndreas Gohr    }
24614d99ec0SAndreas Gohr
247f5f32cbfSAndreas Gohr    /**
248f5f32cbfSAndreas Gohr     * Print an introductionary screen
249f5f32cbfSAndreas Gohr     */
250a8acb244SAndreas Gohr    public function html_dashboard()
251a8acb244SAndreas Gohr    {
252878be5c9SAndreas Gohr        echo '<p>' . $this->getLang('intro_dashboard') . '</p>';
2532812a751SAndreas Gohr
2542812a751SAndreas Gohr        // general info
2552812a751SAndreas Gohr        echo '<div class="plg_stats_top">';
256*211caa5dSAndreas Gohr        $result = $this->hlp->getQuery()->aggregate();
2571d2d78ccSAndreas Gohr
2581d2d78ccSAndreas Gohr        echo '<ul class="left">';
259a8acb244SAndreas Gohr        foreach (['pageviews', 'sessions', 'visitors', 'users', 'logins', 'current'] as $name) {
260eabe0d07SAndreas Gohr            echo '<li><div class="li">' . sprintf($this->getLang('dash_' . $name), $result[$name]) . '</div></li>';
261eabe0d07SAndreas Gohr        }
2622812a751SAndreas Gohr        echo '</ul>';
2631d2d78ccSAndreas Gohr
2641d2d78ccSAndreas Gohr        echo '<ul class="left">';
265a8acb244SAndreas Gohr        foreach (['bouncerate', 'timespent', 'avgpages', 'newvisitors', 'registrations'] as $name) {
2661d2d78ccSAndreas Gohr            echo '<li><div class="li">' . sprintf($this->getLang('dash_' . $name), $result[$name]) . '</div></li>';
2671d2d78ccSAndreas Gohr        }
2681d2d78ccSAndreas Gohr        echo '</ul>';
2691d2d78ccSAndreas Gohr
27056f647ddSAndreas Gohr        echo '<br style="clear: left" />';
27156f647ddSAndreas Gohr
272259897e1SAndreas Gohr        $this->html_graph('dashboardviews', 700, 280);
273259897e1SAndreas Gohr        $this->html_graph('dashboardwiki', 700, 280);
2742812a751SAndreas Gohr        echo '</div>';
2752812a751SAndreas Gohr
276*211caa5dSAndreas Gohr        $quickgraphs = [
277*211caa5dSAndreas Gohr            ['lbl' => 'dash_mostpopular', 'query' => 'pages', 'opt' => 'page'],
278*211caa5dSAndreas Gohr            ['lbl' => 'dash_newincoming', 'query' => 'newreferer', 'opt' => 'newreferer'],
279*211caa5dSAndreas Gohr            ['lbl' => 'dash_topsearch', 'query' => 'searchphrases', 'opt' => 'internalsearchphrases'],
280*211caa5dSAndreas Gohr        ];
28187d5e44bSAndreas Gohr
282*211caa5dSAndreas Gohr        foreach ($quickgraphs as $graph) {
283*211caa5dSAndreas Gohr            $params = [
284*211caa5dSAndreas Gohr                'do' => 'admin',
285*211caa5dSAndreas Gohr                'page' => 'statistics',
286*211caa5dSAndreas Gohr                'f' => $this->from,
287*211caa5dSAndreas Gohr                't' => $this->to,
288*211caa5dSAndreas Gohr                'opt' => $graph['opt'],
289*211caa5dSAndreas Gohr            ];
29054f6c432SAndreas Gohr
291264f1744SAndreas Gohr            echo '<div>';
292*211caa5dSAndreas Gohr            echo '<h2>' . $this->getLang($graph['lbl']) . '</h2>';
293*211caa5dSAndreas Gohr            $result = call_user_func([$this->hlp->getQuery(), $graph['query']]);
29429dea504SAndreas Gohr            $this->html_resulttable($result);
295*211caa5dSAndreas Gohr            echo '<a href="?' . buildURLparams($params) . '" class="more button">' . $this->getLang('more') . '</a>';
296264f1744SAndreas Gohr            echo '</div>';
29714d99ec0SAndreas Gohr        }
298*211caa5dSAndreas Gohr    }
29914d99ec0SAndreas Gohr
300a8acb244SAndreas Gohr    public function html_history()
301a8acb244SAndreas Gohr    {
302cae4a1c5SAndreas Gohr        echo '<p>' . $this->getLang('intro_history') . '</p>';
303338987f5SAndreas Gohr        $this->html_graph('history_page_count', 600, 200);
304338987f5SAndreas Gohr        $this->html_graph('history_page_size', 600, 200);
305338987f5SAndreas Gohr        $this->html_graph('history_media_count', 600, 200);
306338987f5SAndreas Gohr        $this->html_graph('history_media_size', 600, 200);
307cae4a1c5SAndreas Gohr    }
308cae4a1c5SAndreas Gohr
309a8acb244SAndreas Gohr    public function html_countries()
310a8acb244SAndreas Gohr    {
311878be5c9SAndreas Gohr        echo '<p>' . $this->getLang('intro_countries') . '</p>';
3121d379254SAnna Dabrowska        $this->html_graph('countries', 300, 300);
313*211caa5dSAndreas Gohr        $result = $this->hlp->getQuery()->countries();
3142507f8e0SAndreas Gohr        $this->html_resulttable($result, '', 150);
3159da6395dSAndreas Gohr    }
3169da6395dSAndreas Gohr
317a8acb244SAndreas Gohr    public function html_page()
318a8acb244SAndreas Gohr    {
319878be5c9SAndreas Gohr        echo '<p>' . $this->getLang('intro_page') . '</p>';
320*211caa5dSAndreas Gohr        $result = $this->hlp->getQuery()->pages();
3212507f8e0SAndreas Gohr        $this->html_resulttable($result, '', 150);
3229da6395dSAndreas Gohr    }
3239da6395dSAndreas Gohr
324a8acb244SAndreas Gohr    public function html_edits()
325a8acb244SAndreas Gohr    {
3261664ba1dSAndreas Gohr        echo '<p>' . $this->getLang('intro_edits') . '</p>';
327*211caa5dSAndreas Gohr        $result = $this->hlp->getQuery()->edits();
3281664ba1dSAndreas Gohr        $this->html_resulttable($result, '', 150);
3291664ba1dSAndreas Gohr    }
3301664ba1dSAndreas Gohr
331a8acb244SAndreas Gohr    public function html_images()
332a8acb244SAndreas Gohr    {
3331664ba1dSAndreas Gohr        echo '<p>' . $this->getLang('intro_images') . '</p>';
334616c1e8bSAndreas Gohr
335*211caa5dSAndreas Gohr        $result = $this->hlp->getQuery()->imagessum();
336616c1e8bSAndreas Gohr        echo '<p>';
337616c1e8bSAndreas Gohr        echo sprintf($this->getLang('trafficsum'), $result[0]['cnt'], filesize_h($result[0]['filesize']));
338616c1e8bSAndreas Gohr        echo '</p>';
339616c1e8bSAndreas Gohr
340*211caa5dSAndreas Gohr        $result = $this->hlp->getQuery()->images();
3411664ba1dSAndreas Gohr        $this->html_resulttable($result, '', 150);
3421664ba1dSAndreas Gohr    }
3431664ba1dSAndreas Gohr
344a8acb244SAndreas Gohr    public function html_downloads()
345a8acb244SAndreas Gohr    {
3461664ba1dSAndreas Gohr        echo '<p>' . $this->getLang('intro_downloads') . '</p>';
347616c1e8bSAndreas Gohr
348*211caa5dSAndreas Gohr        $result = $this->hlp->getQuery()->downloadssum();
349616c1e8bSAndreas Gohr        echo '<p>';
350616c1e8bSAndreas Gohr        echo sprintf($this->getLang('trafficsum'), $result[0]['cnt'], filesize_h($result[0]['filesize']));
351616c1e8bSAndreas Gohr        echo '</p>';
352616c1e8bSAndreas Gohr
353*211caa5dSAndreas Gohr        $result = $this->hlp->getQuery()->downloads();
3541664ba1dSAndreas Gohr        $this->html_resulttable($result, '', 150);
3551664ba1dSAndreas Gohr    }
3561664ba1dSAndreas Gohr
357a8acb244SAndreas Gohr    public function html_browsers()
358a8acb244SAndreas Gohr    {
359878be5c9SAndreas Gohr        echo '<p>' . $this->getLang('intro_browsers') . '</p>';
3601d379254SAnna Dabrowska        $this->html_graph('browsers', 300, 300);
361*211caa5dSAndreas Gohr        $result = $this->hlp->getQuery()->browsers(false);
3622507f8e0SAndreas Gohr        $this->html_resulttable($result, '', 150);
36375fa767dSAndreas Gohr    }
36475fa767dSAndreas Gohr
365a8acb244SAndreas Gohr    public function html_topuser()
366a8acb244SAndreas Gohr    {
36781ff4c3aSAndreas Gohr        echo '<p>' . $this->getLang('intro_topuser') . '</p>';
3681d379254SAnna Dabrowska        $this->html_graph('topuser', 300, 300);
369*211caa5dSAndreas Gohr        $result = $this->hlp->getQuery()->topuser();
37081ff4c3aSAndreas Gohr        $this->html_resulttable($result, '', 150);
37181ff4c3aSAndreas Gohr    }
37281ff4c3aSAndreas Gohr
373a8acb244SAndreas Gohr    public function html_topeditor()
374a8acb244SAndreas Gohr    {
37581ff4c3aSAndreas Gohr        echo '<p>' . $this->getLang('intro_topeditor') . '</p>';
3761d379254SAnna Dabrowska        $this->html_graph('topeditor', 300, 300);
377*211caa5dSAndreas Gohr        $result = $this->hlp->getQuery()->topeditor();
37881ff4c3aSAndreas Gohr        $this->html_resulttable($result, '', 150);
37981ff4c3aSAndreas Gohr    }
38081ff4c3aSAndreas Gohr
381a8acb244SAndreas Gohr    public function html_topgroup()
382a8acb244SAndreas Gohr    {
38381ff4c3aSAndreas Gohr        echo '<p>' . $this->getLang('intro_topgroup') . '</p>';
3841d379254SAnna Dabrowska        $this->html_graph('topgroup', 300, 300);
385*211caa5dSAndreas Gohr        $result = $this->hlp->getQuery()->topgroup();
38681ff4c3aSAndreas Gohr        $this->html_resulttable($result, '', 150);
38781ff4c3aSAndreas Gohr    }
38881ff4c3aSAndreas Gohr
389a8acb244SAndreas Gohr    public function html_topgroupedit()
390a8acb244SAndreas Gohr    {
39181ff4c3aSAndreas Gohr        echo '<p>' . $this->getLang('intro_topgroupedit') . '</p>';
3921d379254SAnna Dabrowska        $this->html_graph('topgroupedit', 300, 300);
393*211caa5dSAndreas Gohr        $result = $this->hlp->getQuery()->topgroupedit();
39481ff4c3aSAndreas Gohr        $this->html_resulttable($result, '', 150);
39581ff4c3aSAndreas Gohr    }
39681ff4c3aSAndreas Gohr
397a8acb244SAndreas Gohr    public function html_os()
398a8acb244SAndreas Gohr    {
399878be5c9SAndreas Gohr        echo '<p>' . $this->getLang('intro_os') . '</p>';
4001d379254SAnna Dabrowska        $this->html_graph('os', 300, 300);
401*211caa5dSAndreas Gohr        $result = $this->hlp->getQuery()->os();
4022507f8e0SAndreas Gohr        $this->html_resulttable($result, '', 150);
403bd4217d3SAndreas Gohr    }
404bd4217d3SAndreas Gohr
405a8acb244SAndreas Gohr    public function html_referer()
406a8acb244SAndreas Gohr    {
407*211caa5dSAndreas Gohr        $result = $this->hlp->getQuery()->aggregate();
4082812a751SAndreas Gohr
4092812a751SAndreas Gohr        $all = $result['search'] + $result['external'] + $result['direct'];
4102812a751SAndreas Gohr
41194023548SAndreas Gohr        if ($all) {
4120863c19cSAndreas Gohr            printf(
4130863c19cSAndreas Gohr                '<p>' . $this->getLang('intro_referer') . '</p>',
414a8acb244SAndreas Gohr                $all,
415a8acb244SAndreas Gohr                $result['direct'],
416a8acb244SAndreas Gohr                (100 * $result['direct'] / $all),
417a8acb244SAndreas Gohr                $result['search'],
418a8acb244SAndreas Gohr                (100 * $result['search'] / $all),
419a8acb244SAndreas Gohr                $result['external'],
4200863c19cSAndreas Gohr                (100 * $result['external'] / $all)
4210863c19cSAndreas Gohr            );
42294023548SAndreas Gohr        }
4232812a751SAndreas Gohr
424*211caa5dSAndreas Gohr        $result = $this->hlp->getQuery()->referer();
4252507f8e0SAndreas Gohr        $this->html_resulttable($result, '', 150);
4269da6395dSAndreas Gohr    }
4279da6395dSAndreas Gohr
428a8acb244SAndreas Gohr    public function html_newreferer()
429a8acb244SAndreas Gohr    {
430878be5c9SAndreas Gohr        echo '<p>' . $this->getLang('intro_newreferer') . '</p>';
431e7a2f1e0SAndreas Gohr
432*211caa5dSAndreas Gohr        $result = $this->hlp->getQuery()->newreferer();
4332507f8e0SAndreas Gohr        $this->html_resulttable($result, '', 150);
434e7a2f1e0SAndreas Gohr    }
435e7a2f1e0SAndreas Gohr
436a8acb244SAndreas Gohr    public function html_outlinks()
437a8acb244SAndreas Gohr    {
438878be5c9SAndreas Gohr        echo '<p>' . $this->getLang('intro_outlinks') . '</p>';
439*211caa5dSAndreas Gohr        $result = $this->hlp->getQuery()->outlinks();
440e25286daSAndreas Gohr        $this->html_resulttable($result, '', 150);
441e25286daSAndreas Gohr    }
442e25286daSAndreas Gohr
443a8acb244SAndreas Gohr    public function html_searchphrases()
444a8acb244SAndreas Gohr    {
445878be5c9SAndreas Gohr        echo '<p>' . $this->getLang('intro_searchphrases') . '</p>';
446*211caa5dSAndreas Gohr        $result = $this->hlp->getQuery()->searchphrases(true);
44712dcdeccSAndreas Gohr        $this->html_resulttable($result, '', 150);
44812dcdeccSAndreas Gohr    }
44912dcdeccSAndreas Gohr
450a8acb244SAndreas Gohr    public function html_searchwords()
451a8acb244SAndreas Gohr    {
452878be5c9SAndreas Gohr        echo '<p>' . $this->getLang('intro_searchwords') . '</p>';
453*211caa5dSAndreas Gohr        $result = $this->hlp->getQuery()->searchwords(true);
4545bccfe87SAndreas Gohr        $this->html_resulttable($result, '', 150);
4555bccfe87SAndreas Gohr    }
4565bccfe87SAndreas Gohr
457a8acb244SAndreas Gohr    public function html_internalsearchphrases()
458a8acb244SAndreas Gohr    {
459878be5c9SAndreas Gohr        echo '<p>' . $this->getLang('intro_internalsearchphrases') . '</p>';
460*211caa5dSAndreas Gohr        $result = $this->hlp->getQuery()->searchphrases(false);
4615bccfe87SAndreas Gohr        $this->html_resulttable($result, '', 150);
4625bccfe87SAndreas Gohr    }
4635bccfe87SAndreas Gohr
464a8acb244SAndreas Gohr    public function html_internalsearchwords()
465a8acb244SAndreas Gohr    {
466878be5c9SAndreas Gohr        echo '<p>' . $this->getLang('intro_internalsearchwords') . '</p>';
467*211caa5dSAndreas Gohr        $result = $this->hlp->getQuery()->searchwords(false);
46812dcdeccSAndreas Gohr        $this->html_resulttable($result, '', 150);
46912dcdeccSAndreas Gohr    }
47012dcdeccSAndreas Gohr
471a8acb244SAndreas Gohr    public function html_searchengines()
472a8acb244SAndreas Gohr    {
473878be5c9SAndreas Gohr        echo '<p>' . $this->getLang('intro_searchengines') . '</p>';
47425b71d4bSAndreas Gohr        $this->html_graph('searchengines', 400, 200);
475*211caa5dSAndreas Gohr        $result = $this->hlp->getQuery()->searchengines();
47612dcdeccSAndreas Gohr        $this->html_resulttable($result, '', 150);
47712dcdeccSAndreas Gohr    }
47812dcdeccSAndreas Gohr
479a8acb244SAndreas Gohr    public function html_resolution()
480a8acb244SAndreas Gohr    {
48125446aa2SAndreas Gohr        echo '<p>' . $this->getLang('intro_resolution') . '</p>';
48225446aa2SAndreas Gohr        $this->html_graph('resolution', 650, 490);
483*211caa5dSAndreas Gohr        $result = $this->hlp->getQuery()->resolution();
484307baf3fSAndreas Gohr        $this->html_resulttable($result, '', 150);
48525446aa2SAndreas Gohr    }
486307baf3fSAndreas Gohr
487a8acb244SAndreas Gohr    public function html_viewport()
488a8acb244SAndreas Gohr    {
48925446aa2SAndreas Gohr        echo '<p>' . $this->getLang('intro_viewport') . '</p>';
49025446aa2SAndreas Gohr        $this->html_graph('viewport', 650, 490);
491*211caa5dSAndreas Gohr        $result = $this->hlp->getQuery()->viewport();
49225446aa2SAndreas Gohr        $this->html_resulttable($result, '', 150);
493c73e16f1SAndreas Gohr    }
4949da6395dSAndreas Gohr
495a8acb244SAndreas Gohr    public function html_seenusers()
496a8acb244SAndreas Gohr    {
49733a136e5SAndreas Gohr        echo '<p>' . $this->getLang('intro_seenusers') . '</p>';
498*211caa5dSAndreas Gohr        $result = $this->hlp->getQuery()->seenusers();
49933a136e5SAndreas Gohr        $this->html_resulttable($result, '', 150);
50033a136e5SAndreas Gohr    }
50133a136e5SAndreas Gohr
50214d99ec0SAndreas Gohr    /**
50314d99ec0SAndreas Gohr     * Display a result in a HTML table
50414d99ec0SAndreas Gohr     */
505a8acb244SAndreas Gohr    public function html_resulttable($result, $header = '', $pager = 0)
506a8acb244SAndreas Gohr    {
50756f647ddSAndreas Gohr        echo '<table class="inline">';
5082812a751SAndreas Gohr        if (is_array($header)) {
50914d99ec0SAndreas Gohr            echo '<tr>';
51014d99ec0SAndreas Gohr            foreach ($header as $h) {
51114d99ec0SAndreas Gohr                echo '<th>' . hsc($h) . '</th>';
51214d99ec0SAndreas Gohr            }
51314d99ec0SAndreas Gohr            echo '</tr>';
5142812a751SAndreas Gohr        }
51514d99ec0SAndreas Gohr
5162507f8e0SAndreas Gohr        $count = 0;
5172ee939eeSAndreas Gohr        if (is_array($result)) foreach ($result as $row) {
51814d99ec0SAndreas Gohr            echo '<tr>';
51914d99ec0SAndreas Gohr            foreach ($row as $k => $v) {
520f3818071SAndreas Gohr                if ($k == 'res_x') continue;
521f3818071SAndreas Gohr                if ($k == 'res_y') continue;
522f3818071SAndreas Gohr
5232812a751SAndreas Gohr                echo '<td class="plg_stats_X' . $k . '">';
52414d99ec0SAndreas Gohr                if ($k == 'page') {
52514d99ec0SAndreas Gohr                    echo '<a href="' . wl($v) . '" class="wikilink1">';
52614d99ec0SAndreas Gohr                    echo hsc($v);
52714d99ec0SAndreas Gohr                    echo '</a>';
5281664ba1dSAndreas Gohr                } elseif ($k == 'media') {
5291664ba1dSAndreas Gohr                    echo '<a href="' . ml($v) . '" class="wikilink1">';
5301664ba1dSAndreas Gohr                    echo hsc($v);
5311664ba1dSAndreas Gohr                    echo '</a>';
5321664ba1dSAndreas Gohr                } elseif ($k == 'filesize') {
5331664ba1dSAndreas Gohr                    echo filesize_h($v);
53414d99ec0SAndreas Gohr                } elseif ($k == 'url') {
53554f6c432SAndreas Gohr                    $url = hsc($v);
53683b63546SAndreas Gohr                    $url = preg_replace('/^https?:\/\/(www\.)?/', '', $url);
5372812a751SAndreas Gohr                    if (strlen($url) > 45) {
5382812a751SAndreas Gohr                        $url = substr($url, 0, 30) . ' &hellip; ' . substr($url, -15);
53954f6c432SAndreas Gohr                    }
54014d99ec0SAndreas Gohr                    echo '<a href="' . $v . '" class="urlextern">';
54154f6c432SAndreas Gohr                    echo $url;
54214d99ec0SAndreas Gohr                    echo '</a>';
5435bccfe87SAndreas Gohr                } elseif ($k == 'ilookup') {
544a8acb244SAndreas Gohr                    echo '<a href="' . wl('', ['id' => $v, 'do' => 'search']) . '">Search</a>';
54529dea504SAndreas Gohr                } elseif ($k == 'lookup') {
54629dea504SAndreas Gohr                    echo '<a href="http://www.google.com/search?q=' . rawurlencode($v) . '">';
547*211caa5dSAndreas Gohr                    echo '<img src="' . DOKU_BASE . 'lib/plugins/statistics/ico/search/google.png" alt="Google" />';
54829dea504SAndreas Gohr                    echo '</a> ';
54929dea504SAndreas Gohr
55029dea504SAndreas Gohr                    echo '<a href="http://search.yahoo.com/search?p=' . rawurlencode($v) . '">';
551*211caa5dSAndreas Gohr                    echo '<img src="' . DOKU_BASE . 'lib/plugins/statistics/ico/search/yahoo.png" alt="Yahoo!" />';
55229dea504SAndreas Gohr                    echo '</a> ';
55329dea504SAndreas Gohr
55413a86c14SAndreas Gohr                    echo '<a href="http://www.bing.com/search?q=' . rawurlencode($v) . '">';
555*211caa5dSAndreas Gohr                    echo '<img src="' . DOKU_BASE . 'lib/plugins/statistics/ico/search/bing.png" alt="Bing" />';
55629dea504SAndreas Gohr                    echo '</a> ';
55712dcdeccSAndreas Gohr                } elseif ($k == 'engine') {
558*211caa5dSAndreas Gohr                    // FIXME thhis is not correct anymore
55913a86c14SAndreas Gohr                    if (isset($SEARCHENGINEINFO[$v])) {
56013a86c14SAndreas Gohr                        echo '<a href="' . $SEARCHENGINEINFO[$v][1] . '">' . $SEARCHENGINEINFO[$v][0] . '</a>';
56113a86c14SAndreas Gohr                    } else {
56213a86c14SAndreas Gohr                        echo hsc(ucwords($v));
56313a86c14SAndreas Gohr                    }
56413a86c14SAndreas Gohr                } elseif ($k == 'eflag') {
56513a86c14SAndreas Gohr                    $this->html_icon('search', $v);
56675fa767dSAndreas Gohr                } elseif ($k == 'bflag') {
56713a86c14SAndreas Gohr                    $this->html_icon('browser', $v);
568bd4217d3SAndreas Gohr                } elseif ($k == 'osflag') {
56913a86c14SAndreas Gohr                    $this->html_icon('os', $v);
57075fa767dSAndreas Gohr                } elseif ($k == 'cflag') {
57113a86c14SAndreas Gohr                    $this->html_icon('flags', $v);
57214d99ec0SAndreas Gohr                } elseif ($k == 'html') {
57314d99ec0SAndreas Gohr                    echo $v;
57414d99ec0SAndreas Gohr                } else {
57514d99ec0SAndreas Gohr                    echo hsc($v);
57614d99ec0SAndreas Gohr                }
57714d99ec0SAndreas Gohr                echo '</td>';
57814d99ec0SAndreas Gohr            }
57914d99ec0SAndreas Gohr            echo '</tr>';
5802507f8e0SAndreas Gohr
5812507f8e0SAndreas Gohr            if ($pager && ($count == $pager)) break;
5822507f8e0SAndreas Gohr            $count++;
58314d99ec0SAndreas Gohr        }
58414d99ec0SAndreas Gohr        echo '</table>';
5852507f8e0SAndreas Gohr
5862507f8e0SAndreas Gohr        if ($pager) $this->html_pager($pager, count($result) > $pager);
5871878f16fSAndreas Gohr    }
5881878f16fSAndreas Gohr
589a8acb244SAndreas Gohr    public function html_icon($type, $value)
590a8acb244SAndreas Gohr    {
59113a86c14SAndreas Gohr        $value = strtolower(preg_replace('/[^\w]+/', '', $value));
5929bb008afSAndreas Gohr        $value = str_replace(' ', '_', $value);
593a8acb244SAndreas Gohr
59413a86c14SAndreas Gohr        $file = 'lib/plugins/statistics/ico/' . $type . '/' . $value . '.png';
595dffb869bSAndreas Gohr        if ($type == 'flags') {
596dffb869bSAndreas Gohr            $w = 18;
597dffb869bSAndreas Gohr            $h = 12;
598dffb869bSAndreas Gohr        } else {
599dffb869bSAndreas Gohr            $w = 16;
600dffb869bSAndreas Gohr            $h = 16;
601dffb869bSAndreas Gohr        }
602*211caa5dSAndreas Gohr        if (!file_exists(DOKU_INC . $file)) return;
603*211caa5dSAndreas Gohr
604dffb869bSAndreas Gohr        echo '<img src="' . DOKU_BASE . $file . '" alt="' . hsc($value) . '" width="' . $w . '" height="' . $h . '" />';
60513a86c14SAndreas Gohr    }
60613a86c14SAndreas Gohr}
607