xref: /plugin/renderrevisions/action/revisions.php (revision ab3c4129fda348db287dd95b116df414e354e3c9)
1*ab3c4129SAndreas Gohr<?php
2*ab3c4129SAndreas Gohr
3*ab3c4129SAndreas Gohruse dokuwiki\Extension\ActionPlugin;
4*ab3c4129SAndreas Gohruse dokuwiki\Extension\Event;
5*ab3c4129SAndreas Gohruse dokuwiki\Extension\EventHandler;
6*ab3c4129SAndreas Gohruse dokuwiki\Form\HTMLElement;
7*ab3c4129SAndreas Gohr
8*ab3c4129SAndreas Gohr/**
9*ab3c4129SAndreas Gohr * DokuWiki Plugin renderrevisions (Action Component)
10*ab3c4129SAndreas Gohr *
11*ab3c4129SAndreas Gohr * @license GPL 2 http://www.gnu.org/licenses/gpl-2.0.html
12*ab3c4129SAndreas Gohr * @author Andreas Gohr <dokuwiki@cosmocode.de>
13*ab3c4129SAndreas Gohr */
14*ab3c4129SAndreas Gohrclass action_plugin_renderrevisions_revisions extends ActionPlugin
15*ab3c4129SAndreas Gohr{
16*ab3c4129SAndreas Gohr    /** @inheritDoc */
17*ab3c4129SAndreas Gohr    public function register(EventHandler $controller)
18*ab3c4129SAndreas Gohr    {
19*ab3c4129SAndreas Gohr        if($this->getConf('store')) {
20*ab3c4129SAndreas Gohr            $controller->register_hook('FORM_REVISIONS_OUTPUT', 'BEFORE', $this, 'handleRevisions');
21*ab3c4129SAndreas Gohr            $controller->register_hook('ACTION_ACT_PREPROCESS', 'BEFORE', $this, 'handleActPreprocess');
22*ab3c4129SAndreas Gohr            $controller->register_hook('TPL_ACT_UNKNOWN', 'BEFORE', $this, 'handleActUnknown');
23*ab3c4129SAndreas Gohr        }
24*ab3c4129SAndreas Gohr    }
25*ab3c4129SAndreas Gohr
26*ab3c4129SAndreas Gohr    /**
27*ab3c4129SAndreas Gohr     * Event handler for FORM_REVISIONS_OUTPUT
28*ab3c4129SAndreas Gohr     *
29*ab3c4129SAndreas Gohr     * Link revisions to their rendered output when available
30*ab3c4129SAndreas Gohr     *
31*ab3c4129SAndreas Gohr     * @see https://www.dokuwiki.org/devel:events:FORM_REVISIONS_OUTPUT
32*ab3c4129SAndreas Gohr     * @param Event $event Event object
33*ab3c4129SAndreas Gohr     * @param mixed $param optional parameter passed when event was registered
34*ab3c4129SAndreas Gohr     * @return void
35*ab3c4129SAndreas Gohr     */
36*ab3c4129SAndreas Gohr    public function handleRevisions(Event $event, $param)
37*ab3c4129SAndreas Gohr    {
38*ab3c4129SAndreas Gohr        global $INFO;
39*ab3c4129SAndreas Gohr
40*ab3c4129SAndreas Gohr        /** @var dokuwiki\Form\Form $form */
41*ab3c4129SAndreas Gohr        $form = $event->data;
42*ab3c4129SAndreas Gohr
43*ab3c4129SAndreas Gohr        /** @var helper_plugin_renderrevisions_storage $storage */
44*ab3c4129SAndreas Gohr        $storage = plugin_load('helper', 'renderrevisions_storage');
45*ab3c4129SAndreas Gohr
46*ab3c4129SAndreas Gohr        $id = $INFO['id'];
47*ab3c4129SAndreas Gohr        $elementCount = $form->elementCount();
48*ab3c4129SAndreas Gohr
49*ab3c4129SAndreas Gohr        for ($i = 0; $i < $elementCount; $i++) {
50*ab3c4129SAndreas Gohr            $element = $form->getElementAt($i);
51*ab3c4129SAndreas Gohr            if (!$element instanceof HTMLElement) continue;
52*ab3c4129SAndreas Gohr            if (!preg_match('/\?rev=(\d+)/', $element->val(), $match)) continue;
53*ab3c4129SAndreas Gohr            $rev = (int)$match[1];
54*ab3c4129SAndreas Gohr            if (!$rev) continue;
55*ab3c4129SAndreas Gohr            if (!$storage->hasRevision($id, $rev)) continue;
56*ab3c4129SAndreas Gohr
57*ab3c4129SAndreas Gohr            $html = $element->val();
58*ab3c4129SAndreas Gohr            $html = preg_replace('/(\?rev=\d+)/', '\\1&amp;do=renderrevisions', $html);
59*ab3c4129SAndreas Gohr            $html = preg_replace('/class="wikilink1"/', 'class="wikilink1 renderrevisions"', $html);
60*ab3c4129SAndreas Gohr            $element->val($html);
61*ab3c4129SAndreas Gohr        }
62*ab3c4129SAndreas Gohr    }
63*ab3c4129SAndreas Gohr
64*ab3c4129SAndreas Gohr    /**
65*ab3c4129SAndreas Gohr     * Event handler for ACTION_ACT_PREPROCESS
66*ab3c4129SAndreas Gohr     *
67*ab3c4129SAndreas Gohr     * @see https://www.dokuwiki.org/devel:event:ACTION_ACT_PREPROCESS
68*ab3c4129SAndreas Gohr     * @param Event $event Event object
69*ab3c4129SAndreas Gohr     * @param mixed $param optional parameter passed when event was registered
70*ab3c4129SAndreas Gohr     * @return void
71*ab3c4129SAndreas Gohr     */
72*ab3c4129SAndreas Gohr    public function handleActPreprocess(Event $event, $param)
73*ab3c4129SAndreas Gohr    {
74*ab3c4129SAndreas Gohr        global $REV;
75*ab3c4129SAndreas Gohr        global $INFO;
76*ab3c4129SAndreas Gohr
77*ab3c4129SAndreas Gohr        // not our circus?
78*ab3c4129SAndreas Gohr        if ($event->data !== 'renderrevisions') return;
79*ab3c4129SAndreas Gohr
80*ab3c4129SAndreas Gohr        // no revision? show the page. id should always be set, but just in case
81*ab3c4129SAndreas Gohr        if (!$REV || !$INFO['id']) {
82*ab3c4129SAndreas Gohr            $event->data = 'show';
83*ab3c4129SAndreas Gohr            return;
84*ab3c4129SAndreas Gohr        }
85*ab3c4129SAndreas Gohr
86*ab3c4129SAndreas Gohr        // check permissions
87*ab3c4129SAndreas Gohr        if(auth_quickaclcheck($INFO['id']) < AUTH_READ) {
88*ab3c4129SAndreas Gohr            $event->data = 'denied';
89*ab3c4129SAndreas Gohr            return;
90*ab3c4129SAndreas Gohr        }
91*ab3c4129SAndreas Gohr
92*ab3c4129SAndreas Gohr        // no stored revision? show the page
93*ab3c4129SAndreas Gohr        /** @var helper_plugin_renderrevisions_storage $storage */
94*ab3c4129SAndreas Gohr        $storage = plugin_load('helper', 'renderrevisions_storage');
95*ab3c4129SAndreas Gohr        if (!$storage->hasRevision($INFO['id'], (int)$REV)) {
96*ab3c4129SAndreas Gohr            $event->data = 'show';
97*ab3c4129SAndreas Gohr            return;
98*ab3c4129SAndreas Gohr        }
99*ab3c4129SAndreas Gohr
100*ab3c4129SAndreas Gohr        // we can handle it!
101*ab3c4129SAndreas Gohr        $event->preventDefault();
102*ab3c4129SAndreas Gohr        $event->stopPropagation();
103*ab3c4129SAndreas Gohr    }
104*ab3c4129SAndreas Gohr
105*ab3c4129SAndreas Gohr
106*ab3c4129SAndreas Gohr    /**
107*ab3c4129SAndreas Gohr     * Event handler for TPL_ACT_UNKNOWN
108*ab3c4129SAndreas Gohr     *
109*ab3c4129SAndreas Gohr     * @see https://www.dokuwiki.org/devel:event:TPL_ACT_UNKNOWN
110*ab3c4129SAndreas Gohr     * @param Event $event Event object
111*ab3c4129SAndreas Gohr     * @param mixed $param optional parameter passed when event was registered
112*ab3c4129SAndreas Gohr     * @return void
113*ab3c4129SAndreas Gohr     */
114*ab3c4129SAndreas Gohr    public function handleActUnknown(Event $event, $param)
115*ab3c4129SAndreas Gohr    {
116*ab3c4129SAndreas Gohr        global $REV;
117*ab3c4129SAndreas Gohr        global $INFO;
118*ab3c4129SAndreas Gohr        global $ACT;
119*ab3c4129SAndreas Gohr
120*ab3c4129SAndreas Gohr        if ($event->data !== 'renderrevisions') return;
121*ab3c4129SAndreas Gohr        $event->preventDefault();
122*ab3c4129SAndreas Gohr        $event->stopPropagation();
123*ab3c4129SAndreas Gohr
124*ab3c4129SAndreas Gohr        /** @var helper_plugin_renderrevisions_storage $storage */
125*ab3c4129SAndreas Gohr        $storage = plugin_load('helper', 'renderrevisions_storage');
126*ab3c4129SAndreas Gohr        $content = $storage->getRevision($INFO['id'], (int)$REV);
127*ab3c4129SAndreas Gohr        $intro = sprintf(
128*ab3c4129SAndreas Gohr            $this->getLang('intro'),
129*ab3c4129SAndreas Gohr            dformat($REV),
130*ab3c4129SAndreas Gohr            '<a href="' . wl($INFO['id'], ['rev' => $REV]) . '">' . $this->getLang('rerender') . '</a>'
131*ab3c4129SAndreas Gohr        );
132*ab3c4129SAndreas Gohr
133*ab3c4129SAndreas Gohr        echo '<div class="renderrevisions">';
134*ab3c4129SAndreas Gohr        echo $intro;
135*ab3c4129SAndreas Gohr        echo '</div>';
136*ab3c4129SAndreas Gohr        echo $content;
137*ab3c4129SAndreas Gohr    }
138*ab3c4129SAndreas Gohr}
139