Passed
Push — multiproject/requestforms ( 675fe5 )
by Simon
08:58 queued 04:51
created

PageRequestFormManagement::view()   A

Complexity

Conditions 3
Paths 3

Size

Total Lines 28
Code Lines 15

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 0
CRAP Score 12

Importance

Changes 1
Bugs 0 Features 0
Metric Value
eloc 15
c 1
b 0
f 0
dl 0
loc 28
ccs 0
cts 20
cp 0
rs 9.7666
cc 3
nc 3
nop 0
crap 12
1
<?php
2
/******************************************************************************
3
 * Wikipedia Account Creation Assistance tool                                 *
4
 *                                                                            *
5
 * All code in this file is released into the public domain by the ACC        *
6
 * Development Team. Please see team.json for a list of contributors.         *
7
 ******************************************************************************/
8
9
namespace Waca\Pages;
10
11
use Waca\DataObjects\Domain;
12
use Waca\DataObjects\RequestForm;
13
use Waca\DataObjects\RequestQueue;
14
use Waca\DataObjects\User;
15
use Waca\Exceptions\AccessDeniedException;
16
use Waca\Exceptions\ApplicationLogicException;
17
use Waca\Helpers\Logger;
18
use Waca\Helpers\MarkdownRenderingHelper;
19
use Waca\SessionAlert;
20
use Waca\Tasks\InternalPageBase;
21
use Waca\WebRequest;
22
23
class PageRequestFormManagement extends InternalPageBase
24
{
25
    protected function main()
26
    {
27
        $this->setHtmlTitle('Request Form Management');
28
29
        $database = $this->getDatabase();
30
        $domainId = Domain::getCurrent($database)->getId();
31
        $forms = RequestForm::getAllForms($database, $domainId);
32
        $this->assign('forms', $forms);
33
34
        $queues = [];
35
        foreach ($forms as $f) {
36
            $queueId = $f->getOverrideQueue();
37
            if ($queueId !== null) {
38
                if (!isset($queues[$queueId])) {
39
                    /** @var RequestQueue $queue */
40
                    $queue = RequestQueue::getById($queueId, $this->getDatabase());
41
42
                    if ($queue->getDomain() == $domainId) {
43
                        $queues[$queueId] = $queue;
44
                    }
45
                }
46
            }
47
        }
48
49
        $this->assign('queues', $queues);
50
51
        $user = User::getCurrent($database);
52
        $this->assign('canCreate', $this->barrierTest('create', $user));
53
        $this->assign('canEdit', $this->barrierTest('edit', $user));
54
        $this->assign('canView', $this->barrierTest('view', $user));
55
56
        $this->setTemplate('form-management/main.tpl');
57
    }
58
59
    protected function preview() {
60
        $previewContent = WebRequest::getSessionContext('preview');
61
62
        $renderer = new MarkdownRenderingHelper();
63
        $this->assign('renderedContent', $renderer->doRender($previewContent['main']));
64
        $this->assign('username', $renderer->doRenderInline($previewContent['username']));
65
        $this->assign('email', $renderer->doRenderInline($previewContent['email']));
66
        $this->assign('comment', $renderer->doRenderInline($previewContent['comment']));
67
68
        $this->setTemplate('form-management/preview.tpl');
69
    }
70
71
    protected function create()
72
    {
73
        if (WebRequest::wasPosted()) {
74
            $this->validateCSRFToken();
75
            $database = $this->getDatabase();
76
            $domainId = Domain::getCurrent($database)->getId();
77
78
            $form = new RequestForm();
79
80
            $form->setDatabase($database);
81
            $form->setDomain($domainId);
82
83
            $this->setupObjectFromPost($form);
84
            $form->setPublicEndpoint(WebRequest::postString('endpoint'));
0 ignored issues
show
Bug introduced by
It seems like Waca\WebRequest::postString('endpoint') can also be of type null; however, parameter $publicEndpoint of Waca\DataObjects\RequestForm::setPublicEndpoint() does only seem to accept string, maybe add an additional type check? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

84
            $form->setPublicEndpoint(/** @scrutinizer ignore-type */ WebRequest::postString('endpoint'));
Loading history...
85
86
            if (WebRequest::postString("preview") === "preview") {
87
                $this->populateFromObject($form);
88
89
                WebRequest::setSessionContext('preview', [
90
                    'main' => $form->getFormContent(),
91
                    'username' => $form->getUsernameHelp(),
92
                    'email' => $form->getEmailHelp(),
93
                    'comment' => $form->getCommentHelp(),
94
                ]);
95
96
                $this->assign('createMode', true);
97
                $this->setTemplate('form-management/edit.tpl');
98
99
                return;
100
            }
101
102
            $proceed = true;
103
104
            if (RequestForm::getByPublicEndpoint($database, $form->getPublicEndpoint(), $domainId) !== false) {
105
                SessionAlert::error("The chosen public endpoint is already in use. Please choose another.");
106
                $proceed = false;
107
            }
108
109
            if (preg_match('/^[A-Za-z][a-zA-Z0-9-]*$/', $form->getPublicEndpoint()) !== 1) {
110
                SessionAlert::error("The chosen public endpoint contains invalid characters");
111
                $proceed = false;
112
            }
113
114
            if (RequestForm::getByName($database, $form->getName(), $domainId) !== false) {
115
                SessionAlert::error("The chosen name is already in use. Please choose another.");
116
                $proceed = false;
117
            }
118
119
            if ($form->getOverrideQueue() !== null) {
120
                /** @var RequestQueue|bool $queue */
121
                $queue = RequestQueue::getById($form->getOverrideQueue(), $database);
122
                if ($queue === false || $queue->getDomain() !== $domainId || !$queue->isEnabled()) {
123
                    SessionAlert::error("The chosen queue does not exist or is disabled.");
124
                    $proceed = false;
125
                }
126
            }
127
128
            if ($proceed) {
129
                $form->save();
130
                Logger::requestFormCreated($database, $form);
131
                $this->redirect('requestFormManagement');
132
            }
133
            else {
134
                $this->populateFromObject($form);
135
                WebRequest::setSessionContext('preview', [
136
                    'main' => $form->getFormContent(),
137
                    'username' => $form->getUsernameHelp(),
138
                    'email' => $form->getEmailHelp(),
139
                    'comment' => $form->getCommentHelp(),
140
                ]);
141
142
                $this->assign('createMode', true);
143
                $this->setTemplate('form-management/edit.tpl');
144
            }
145
        }
146
        else {
147
            $this->populateFromObject(new RequestForm());
148
            WebRequest::setSessionContext('preview', null);
149
            $this->assign('hidePreview', true);
150
151
            $this->assignCSRFToken();
152
            $this->assign('createMode', true);
153
            $this->setTemplate('form-management/edit.tpl');
154
        }
155
    }
156
157
    protected function view()
158
    {
159
        $database = $this->getDatabase();
160
161
        /** @var RequestForm $form */
162
        $form = RequestForm::getById(WebRequest::getInt('form'), $database);
163
164
        if ($form->getDomain() !== Domain::getCurrent($database)->getId()) {
165
            throw new AccessDeniedException();
0 ignored issues
show
Bug introduced by
The call to Waca\Exceptions\AccessDe...xception::__construct() has too few arguments starting with securityManager. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

165
            throw /** @scrutinizer ignore-call */ new AccessDeniedException();

This check compares calls to functions or methods with their respective definitions. If the call has less arguments than are defined, it raises an issue.

If a function is defined several times with a different number of parameters, the check may pick up the wrong definition and report false positives. One codebase where this has been known to happen is Wordpress. Please note the @ignore annotation hint above.

Loading history...
166
        }
167
168
        $this->populateFromObject($form);
169
170
        if ($form->getOverrideQueue() !== null) {
171
            $this->assign('queueObject', RequestQueue::getById($form->getOverrideQueue(), $database));
172
        }
173
174
        WebRequest::setSessionContext('preview', [
175
            'main' => $form->getFormContent(),
176
            'username' => $form->getUsernameHelp(),
177
            'email' => $form->getEmailHelp(),
178
            'comment' => $form->getCommentHelp(),
179
        ]);
180
181
        $renderer = new MarkdownRenderingHelper();
182
        $this->assign('renderedContent', $renderer->doRender($form->getFormContent()));
183
184
        $this->setTemplate('form-management/view.tpl');
185
    }
186
187
    protected function edit()
188
    {
189
        $database = $this->getDatabase();
190
191
        /** @var RequestForm $form */
192
        $form = RequestForm::getById(WebRequest::getInt('form'), $database);
193
194
        if ($form->getDomain() !== Domain::getCurrent($database)->getId()) {
195
            throw new AccessDeniedException();
0 ignored issues
show
Bug introduced by
The call to Waca\Exceptions\AccessDe...xception::__construct() has too few arguments starting with securityManager. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

195
            throw /** @scrutinizer ignore-call */ new AccessDeniedException();

This check compares calls to functions or methods with their respective definitions. If the call has less arguments than are defined, it raises an issue.

If a function is defined several times with a different number of parameters, the check may pick up the wrong definition and report false positives. One codebase where this has been known to happen is Wordpress. Please note the @ignore annotation hint above.

Loading history...
196
        }
197
198
        if (WebRequest::wasPosted()) {
199
            $this->validateCSRFToken();
200
201
            $this->setupObjectFromPost($form);
202
203
            if (WebRequest::postString("preview") === "preview") {
204
                $this->populateFromObject($form);
205
206
                WebRequest::setSessionContext('preview', [
207
                    'main' => $form->getFormContent(),
208
                    'username' => $form->getUsernameHelp(),
209
                    'email' => $form->getEmailHelp(),
210
                    'comment' => $form->getCommentHelp(),
211
                ]);
212
213
                $this->assign('createMode', false);
214
                $this->setTemplate('form-management/edit.tpl');
215
216
                return;
217
            }
218
219
            $proceed = true;
220
221
            $foundForm = RequestForm::getByName($database, $form->getName(), $form->getDomain());
222
            if ($foundForm !== false && $foundForm->getId() !== $form->getId()) {
223
                SessionAlert::error("The chosen name is already in use. Please choose another.");
224
                $proceed = false;
225
            }
226
227
            if ($form->getOverrideQueue() !== null) {
228
                /** @var RequestQueue $queue */
229
                $queue = RequestQueue::getById($form->getOverrideQueue(), $database);
230
                if ($queue === false || $queue->getDomain() !== $form->getDomain() || !$queue->isEnabled()) {
231
                    SessionAlert::error("The chosen queue does not exist or is disabled.");
232
                    $proceed = false;
233
                }
234
            }
235
236
            if ($proceed) {
237
                Logger::requestFormEdited($database, $form);
238
                $form->save();
239
                $this->redirect('requestFormManagement');
240
            }
241
            else {
242
                $this->populateFromObject($form);
243
                WebRequest::setSessionContext('preview', [
244
                    'main' => $form->getFormContent(),
245
                    'username' => $form->getUsernameHelp(),
246
                    'email' => $form->getEmailHelp(),
247
                    'comment' => $form->getCommentHelp(),
248
                ]);
249
250
                $this->assign('createMode', false);
251
                $this->setTemplate('form-management/edit.tpl');
252
            }
253
        }
254
        else {
255
            $this->populateFromObject($form);
256
            WebRequest::setSessionContext('preview', [
257
                'main' => $form->getFormContent(),
258
                'username' => $form->getUsernameHelp(),
259
                'email' => $form->getEmailHelp(),
260
                'comment' => $form->getCommentHelp(),
261
            ]);
262
263
            $this->assign('createMode', false);
264
            $this->setTemplate('form-management/edit.tpl');
265
        }
266
    }
267
268
    /**
269
     * @param RequestForm $form
270
     */
271
    protected function populateFromObject(RequestForm $form): void
272
    {
273
        $this->assignCSRFToken();
274
275
        $this->assign('name', $form->getName());
276
        $this->assign('enabled', $form->isEnabled());
277
        $this->assign('endpoint', $form->getPublicEndpoint());
278
        $this->assign('queue', $form->getOverrideQueue());
279
        $this->assign('content', $form->getFormContent());
280
        $this->assign('username', $form->getUsernameHelp());
281
        $this->assign('email', $form->getEmailHelp());
282
        $this->assign('comment', $form->getCommentHelp());
283
284
        $this->assign('domain', $form->getDomainObject());
285
286
        $this->assign('availableQueues', RequestQueue::getEnabledQueues($this->getDatabase()));
287
    }
288
289
    /**
290
     * @param RequestForm $form
291
     *
292
     * @return void
293
     * @throws ApplicationLogicException
294
     */
295
    protected function setupObjectFromPost(RequestForm $form): void
296
    {
297
        if (WebRequest::postString('content') === null
298
            || WebRequest::postString('username') === null
299
            || WebRequest::postString('email') === null
300
            || WebRequest::postString('comment') === null
301
        ) {
302
            throw new ApplicationLogicException("Form content, username help, email help, and comment help are all required fields.");
303
        }
304
305
        $form->setName(WebRequest::postString('name'));
0 ignored issues
show
Bug introduced by
It seems like Waca\WebRequest::postString('name') can also be of type null; however, parameter $name of Waca\DataObjects\RequestForm::setName() does only seem to accept string, maybe add an additional type check? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

305
        $form->setName(/** @scrutinizer ignore-type */ WebRequest::postString('name'));
Loading history...
306
        $form->setEnabled(WebRequest::postBoolean('enabled'));
307
        $form->setFormContent(WebRequest::postString('content'));
0 ignored issues
show
Bug introduced by
It seems like Waca\WebRequest::postString('content') can also be of type null; however, parameter $formContent of Waca\DataObjects\RequestForm::setFormContent() does only seem to accept string, maybe add an additional type check? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

307
        $form->setFormContent(/** @scrutinizer ignore-type */ WebRequest::postString('content'));
Loading history...
308
        $form->setOverrideQueue(WebRequest::postInt('queue'));
309
        $form->setUsernameHelp(WebRequest::postString('username'));
0 ignored issues
show
Bug introduced by
It seems like Waca\WebRequest::postString('username') can also be of type null; however, parameter $usernamehelp of Waca\DataObjects\RequestForm::setUsernameHelp() does only seem to accept string, maybe add an additional type check? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

309
        $form->setUsernameHelp(/** @scrutinizer ignore-type */ WebRequest::postString('username'));
Loading history...
310
        $form->setEmailHelp(WebRequest::postString('email'));
0 ignored issues
show
Bug introduced by
It seems like Waca\WebRequest::postString('email') can also be of type null; however, parameter $emailhelp of Waca\DataObjects\RequestForm::setEmailHelp() does only seem to accept string, maybe add an additional type check? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

310
        $form->setEmailHelp(/** @scrutinizer ignore-type */ WebRequest::postString('email'));
Loading history...
311
        $form->setCommentHelp(WebRequest::postString('comment'));
0 ignored issues
show
Bug introduced by
It seems like Waca\WebRequest::postString('comment') can also be of type null; however, parameter $commenthelp of Waca\DataObjects\RequestForm::setCommentHelp() does only seem to accept string, maybe add an additional type check? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

311
        $form->setCommentHelp(/** @scrutinizer ignore-type */ WebRequest::postString('comment'));
Loading history...
312
    }
313
}
314