Passed
Push — dependabot/composer/newinterna... ( 13eb18 )
by
unknown
04:37
created
includes/Helpers/IrcNotificationHelper.php 2 patches
Indentation   +449 added lines, -449 removed lines patch added patch discarded remove patch
@@ -26,455 +26,455 @@
 block discarded – undo
26 26
  */
27 27
 class IrcNotificationHelper
28 28
 {
29
-    /** @var PdoDatabase $notificationsDatabase */
30
-    private $notificationsDatabase;
31
-    /** @var PdoDatabase $primaryDatabase */
32
-    private $primaryDatabase;
33
-    /** @var bool $notificationsEnabled */
34
-    private $notificationsEnabled;
35
-    /** @var int $notificationType */
36
-    private $notificationType;
37
-    /** @var User $currentUser */
38
-    private $currentUser;
39
-    /** @var string $instanceName */
40
-    private $instanceName;
41
-    /** @var string */
42
-    private $baseUrl;
43
-    /** @var array */
44
-    private $requestStates;
45
-
46
-    /**
47
-     * IrcNotificationHelper constructor.
48
-     *
49
-     * @param SiteConfiguration $siteConfiguration
50
-     * @param PdoDatabase       $primaryDatabase
51
-     * @param PdoDatabase       $notificationsDatabase
52
-     */
53
-    public function __construct(
54
-        SiteConfiguration $siteConfiguration,
55
-        PdoDatabase $primaryDatabase,
56
-        PdoDatabase $notificationsDatabase = null
57
-    ) {
58
-        $this->primaryDatabase = $primaryDatabase;
59
-
60
-        if ($this->notificationsDatabase !== null) {
61
-            $this->notificationsDatabase = $notificationsDatabase;
62
-            $this->notificationsEnabled = $siteConfiguration->getIrcNotificationsEnabled();
63
-        }
64
-        else {
65
-            $this->notificationsEnabled = false;
66
-        }
67
-
68
-        $this->notificationType = $siteConfiguration->getIrcNotificationType();
69
-        $this->instanceName = $siteConfiguration->getIrcNotificationsInstance();
70
-        $this->baseUrl = $siteConfiguration->getBaseUrl();
71
-        $this->requestStates = $siteConfiguration->getRequestStates();
72
-
73
-        $this->currentUser = User::getCurrent($primaryDatabase);
74
-    }
75
-
76
-    /**
77
-     * Send a notification
78
-     *
79
-     * @param string $message The text to send
80
-     */
81
-    protected function send($message)
82
-    {
83
-        $instanceName = $this->instanceName;
84
-
85
-        if (!$this->notificationsEnabled) {
86
-            return;
87
-        }
88
-
89
-        $blacklist = array("DCC", "CCTP", "PRIVMSG");
90
-        $message = str_replace($blacklist, "(IRC Blacklist)", $message); // Lets stop DCC etc
91
-
92
-        $msg = IrcColourCode::RESET . IrcColourCode::BOLD . "[$instanceName]" . IrcColourCode::RESET . ": $message";
93
-
94
-        try {
95
-            $notification = new Notification();
96
-            $notification->setDatabase($this->notificationsDatabase);
97
-            $notification->setType($this->notificationType);
98
-            $notification->setText($msg);
99
-
100
-            $notification->save();
101
-        }
102
-        catch (Exception $ex) {
103
-            // OK, so we failed to send the notification - that db might be down?
104
-            // This is non-critical, so silently fail.
105
-
106
-            // Disable notifications for remainder of request.
107
-            $this->notificationsEnabled = false;
108
-        }
109
-    }
110
-
111
-    #region user management
112
-
113
-    /**
114
-     * send a new user notification
115
-     *
116
-     * @param User $user
117
-     */
118
-    public function userNew(User $user)
119
-    {
120
-        $this->send("New user: {$user->getUsername()}");
121
-    }
122
-
123
-    /**
124
-     * send an approved notification
125
-     *
126
-     * @param User $user
127
-     */
128
-    public function userApproved(User $user)
129
-    {
130
-        $this->send("{$user->getUsername()} approved by " . $this->currentUser->getUsername());
131
-    }
132
-
133
-    /**
134
-     * send a promoted notification
135
-     *
136
-     * @param User $user
137
-     */
138
-    public function userPromoted(User $user)
139
-    {
140
-        $this->send("{$user->getUsername()} promoted to tool admin by " . $this->currentUser->getUsername());
141
-    }
142
-
143
-    /**
144
-     * send a declined notification
145
-     *
146
-     * @param User   $user
147
-     * @param string $reason the reason the user was declined
148
-     */
149
-    public function userDeclined(User $user, $reason)
150
-    {
151
-        $this->send("{$user->getUsername()} declined by " . $this->currentUser->getUsername() . " ($reason)");
152
-    }
153
-
154
-    /**
155
-     * send a demotion notification
156
-     *
157
-     * @param User   $user
158
-     * @param string $reason the reason the user was demoted
159
-     */
160
-    public function userDemoted(User $user, $reason)
161
-    {
162
-        $this->send("{$user->getUsername()} demoted by " . $this->currentUser->getUsername() . " ($reason)");
163
-    }
164
-
165
-    /**
166
-     * send a suspended notification
167
-     *
168
-     * @param User   $user
169
-     * @param string $reason The reason the user has been suspended
170
-     */
171
-    public function userSuspended(User $user, $reason)
172
-    {
173
-        $this->send("{$user->getUsername()} suspended by " . $this->currentUser->getUsername() . " ($reason)");
174
-    }
175
-
176
-    /**
177
-     * Send a preference change notification
178
-     *
179
-     * @param User $user
180
-     */
181
-    public function userPrefChange(User $user)
182
-    {
183
-        $this->send("{$user->getUsername()}'s preferences were changed by " . $this->currentUser->getUsername());
184
-    }
185
-
186
-    /**
187
-     * Send a user renamed notification
188
-     *
189
-     * @param User   $user
190
-     * @param string $old
191
-     */
192
-    public function userRenamed(User $user, $old)
193
-    {
194
-        $this->send($this->currentUser->getUsername() . " renamed $old to {$user->getUsername()}");
195
-    }
196
-
197
-    /**
198
-     * @param User   $user
199
-     * @param string $reason
200
-     */
201
-    public function userRolesEdited(User $user, $reason)
202
-    {
203
-        $currentUser = $this->currentUser->getUsername();
204
-        $this->send("Active roles for {$user->getUsername()} changed by " . $currentUser . " ($reason)");
205
-    }
206
-
207
-    #endregion
208
-
209
-    #region Site Notice
210
-
211
-    /**
212
-     * Summary of siteNoticeEdited
213
-     */
214
-    public function siteNoticeEdited()
215
-    {
216
-        $this->send("Site notice edited by " . $this->currentUser->getUsername());
217
-    }
218
-    #endregion
219
-
220
-    #region Welcome Templates
221
-    /**
222
-     * Summary of welcomeTemplateCreated
223
-     *
224
-     * @param WelcomeTemplate $template
225
-     */
226
-    public function welcomeTemplateCreated(WelcomeTemplate $template)
227
-    {
228
-        $this->send("Welcome template {$template->getId()} created by " . $this->currentUser->getUsername());
229
-    }
230
-
231
-    /**
232
-     * Summary of welcomeTemplateDeleted
233
-     *
234
-     * @param int $templateid
235
-     */
236
-    public function welcomeTemplateDeleted($templateid)
237
-    {
238
-        $this->send("Welcome template {$templateid} deleted by " . $this->currentUser->getUsername());
239
-    }
240
-
241
-    /**
242
-     * Summary of welcomeTemplateEdited
243
-     *
244
-     * @param WelcomeTemplate $template
245
-     */
246
-    public function welcomeTemplateEdited(WelcomeTemplate $template)
247
-    {
248
-        $this->send("Welcome template {$template->getId()} edited by " . $this->currentUser->getUsername());
249
-    }
250
-
251
-    #endregion
252
-
253
-    #region bans
254
-    /**
255
-     * Summary of banned
256
-     *
257
-     * @param Ban $ban
258
-     */
259
-    public function banned(Ban $ban)
260
-    {
261
-        if ($ban->getDuration() == -1) {
262
-            $duration = "indefinitely";
263
-        }
264
-        else {
265
-            $duration = "until " . date("F j, Y, g:i a", $ban->getDuration());
266
-        }
267
-
268
-        $username = $this->currentUser->getUsername();
269
-
270
-        $this->send("{$ban->getTarget()} banned by {$username} for '{$ban->getReason()}' {$duration}");
271
-    }
272
-
273
-    /**
274
-     * Summary of unbanned
275
-     *
276
-     * @param Ban    $ban
277
-     * @param string $unbanreason
278
-     */
279
-    public function unbanned(Ban $ban, $unbanreason)
280
-    {
281
-        $this->send($ban->getTarget() . " unbanned by " . $this->currentUser
282
-                ->getUsername() . " (" . $unbanreason . ")");
283
-    }
284
-
285
-    #endregion
286
-
287
-    #region request management
288
-
289
-    /**
290
-     * Summary of requestReceived
291
-     *
292
-     * @param Request $request
293
-     */
294
-    public function requestReceived(Request $request)
295
-    {
296
-        $this->send(
297
-            IrcColourCode::DARK_GREY . "[["
298
-            . IrcColourCode::DARK_GREEN . "acc:"
299
-            . IrcColourCode::ORANGE . $request->getId()
300
-            . IrcColourCode::DARK_GREY . "]]"
301
-            . IrcColourCode::RED . " N "
302
-            . IrcColourCode::DARK_BLUE . $this->baseUrl . "/internal.php/viewRequest?id={$request->getId()} "
303
-            . IrcColourCode::DARK_RED . "* "
304
-            . IrcColourCode::DARK_GREEN . $request->getName()
305
-            . IrcColourCode::DARK_RED . " * "
306
-            . IrcColourCode::RESET
307
-        );
308
-    }
309
-
310
-    /**
311
-     * Summary of requestDeferred
312
-     *
313
-     * @param Request $request
314
-     */
315
-    public function requestDeferred(Request $request)
316
-    {
317
-        $availableRequestStates = $this->requestStates;
318
-
319
-        $deferTo = $availableRequestStates[$request->getStatus()]['deferto'];
320
-        $username = $this->currentUser->getUsername();
321
-
322
-        $this->send("Request {$request->getId()} ({$request->getName()}) deferred to {$deferTo} by {$username}");
323
-    }
324
-
325
-    /**
326
-     *
327
-     * Summary of requestDeferredWithMail
328
-     *
329
-     * @param Request $request
330
-     */
331
-    public function requestDeferredWithMail(Request $request)
332
-    {
333
-        $availableRequestStates = $this->requestStates;
334
-
335
-        $deferTo = $availableRequestStates[$request->getStatus()]['deferto'];
336
-        $username = $this->currentUser->getUsername();
337
-        $id = $request->getId();
338
-        $name = $request->getName();
339
-
340
-        $this->send("Request {$id} ({$name}) deferred to {$deferTo} with an email by {$username}");
341
-    }
342
-
343
-    /**
344
-     * Summary of requestClosed
345
-     *
346
-     * @param Request $request
347
-     * @param string  $closetype
348
-     */
349
-    public function requestClosed(Request $request, $closetype)
350
-    {
351
-        $username = $this->currentUser->getUsername();
352
-
353
-        $this->send("Request {$request->getId()} ({$request->getName()}) closed ($closetype) by {$username}");
354
-    }
355
-
356
-    /**
357
-     * Summary of sentMail
358
-     *
359
-     * @param Request $request
360
-     */
361
-    public function sentMail(Request $request)
362
-    {
363
-        $this->send($this->currentUser->getUsername()
364
-            . " sent an email related to Request {$request->getId()} ({$request->getName()})");
365
-    }
366
-
367
-    #endregion
368
-
369
-    #region reservations
370
-
371
-    /**
372
-     * Summary of requestReserved
373
-     *
374
-     * @param Request $request
375
-     */
376
-    public function requestReserved(Request $request)
377
-    {
378
-        $username = $this->currentUser->getUsername();
379
-
380
-        $this->send("Request {$request->getId()} ({$request->getName()}) reserved by {$username}");
381
-    }
382
-
383
-    /**
384
-     * Summary of requestReserveBroken
385
-     *
386
-     * @param Request $request
387
-     */
388
-    public function requestReserveBroken(Request $request)
389
-    {
390
-        $username = $this->currentUser->getUsername();
391
-
392
-        $this->send("Reservation on request {$request->getId()} ({$request->getName()}) broken by {$username}");
393
-    }
394
-
395
-    /**
396
-     * Summary of requestUnreserved
397
-     *
398
-     * @param Request $request
399
-     */
400
-    public function requestUnreserved(Request $request)
401
-    {
402
-        $this->send("Request {$request->getId()} ({$request->getName()}) is no longer being handled.");
403
-    }
404
-
405
-    /**
406
-     * Summary of requestReservationSent
407
-     *
408
-     * @param Request $request
409
-     * @param User    $target
410
-     */
411
-    public function requestReservationSent(Request $request, User $target)
412
-    {
413
-        $username = $this->currentUser->getUsername();
414
-
415
-        $this->send(
416
-            "Reservation of request {$request->getId()} ({$request->getName()}) sent to {$target->getUsername()} by "
417
-            . $username);
418
-    }
419
-
420
-    #endregion
421
-
422
-    #region comments
423
-
424
-    /**
425
-     * Summary of commentCreated
426
-     *
427
-     * @param Comment $comment
428
-     * @param Request $request
429
-     */
430
-    public function commentCreated(Comment $comment, Request $request)
431
-    {
432
-        $username = $this->currentUser->getUsername();
433
-        $visibility = ($comment->getVisibility() == "admin" ? "private " : "");
434
-
435
-        $this->send("{$username} posted a {$visibility}comment on request {$request->getId()} ({$request->getName()})");
436
-    }
437
-
438
-    /**
439
-     * Summary of commentEdited
440
-     *
441
-     * @param Comment $comment
442
-     * @param Request $request
443
-     */
444
-    public function commentEdited(Comment $comment, Request $request)
445
-    {
446
-        $username = $this->currentUser->getUsername();
447
-
448
-        $this->send(<<<TAG
29
+	/** @var PdoDatabase $notificationsDatabase */
30
+	private $notificationsDatabase;
31
+	/** @var PdoDatabase $primaryDatabase */
32
+	private $primaryDatabase;
33
+	/** @var bool $notificationsEnabled */
34
+	private $notificationsEnabled;
35
+	/** @var int $notificationType */
36
+	private $notificationType;
37
+	/** @var User $currentUser */
38
+	private $currentUser;
39
+	/** @var string $instanceName */
40
+	private $instanceName;
41
+	/** @var string */
42
+	private $baseUrl;
43
+	/** @var array */
44
+	private $requestStates;
45
+
46
+	/**
47
+	 * IrcNotificationHelper constructor.
48
+	 *
49
+	 * @param SiteConfiguration $siteConfiguration
50
+	 * @param PdoDatabase       $primaryDatabase
51
+	 * @param PdoDatabase       $notificationsDatabase
52
+	 */
53
+	public function __construct(
54
+		SiteConfiguration $siteConfiguration,
55
+		PdoDatabase $primaryDatabase,
56
+		PdoDatabase $notificationsDatabase = null
57
+	) {
58
+		$this->primaryDatabase = $primaryDatabase;
59
+
60
+		if ($this->notificationsDatabase !== null) {
61
+			$this->notificationsDatabase = $notificationsDatabase;
62
+			$this->notificationsEnabled = $siteConfiguration->getIrcNotificationsEnabled();
63
+		}
64
+		else {
65
+			$this->notificationsEnabled = false;
66
+		}
67
+
68
+		$this->notificationType = $siteConfiguration->getIrcNotificationType();
69
+		$this->instanceName = $siteConfiguration->getIrcNotificationsInstance();
70
+		$this->baseUrl = $siteConfiguration->getBaseUrl();
71
+		$this->requestStates = $siteConfiguration->getRequestStates();
72
+
73
+		$this->currentUser = User::getCurrent($primaryDatabase);
74
+	}
75
+
76
+	/**
77
+	 * Send a notification
78
+	 *
79
+	 * @param string $message The text to send
80
+	 */
81
+	protected function send($message)
82
+	{
83
+		$instanceName = $this->instanceName;
84
+
85
+		if (!$this->notificationsEnabled) {
86
+			return;
87
+		}
88
+
89
+		$blacklist = array("DCC", "CCTP", "PRIVMSG");
90
+		$message = str_replace($blacklist, "(IRC Blacklist)", $message); // Lets stop DCC etc
91
+
92
+		$msg = IrcColourCode::RESET . IrcColourCode::BOLD . "[$instanceName]" . IrcColourCode::RESET . ": $message";
93
+
94
+		try {
95
+			$notification = new Notification();
96
+			$notification->setDatabase($this->notificationsDatabase);
97
+			$notification->setType($this->notificationType);
98
+			$notification->setText($msg);
99
+
100
+			$notification->save();
101
+		}
102
+		catch (Exception $ex) {
103
+			// OK, so we failed to send the notification - that db might be down?
104
+			// This is non-critical, so silently fail.
105
+
106
+			// Disable notifications for remainder of request.
107
+			$this->notificationsEnabled = false;
108
+		}
109
+	}
110
+
111
+	#region user management
112
+
113
+	/**
114
+	 * send a new user notification
115
+	 *
116
+	 * @param User $user
117
+	 */
118
+	public function userNew(User $user)
119
+	{
120
+		$this->send("New user: {$user->getUsername()}");
121
+	}
122
+
123
+	/**
124
+	 * send an approved notification
125
+	 *
126
+	 * @param User $user
127
+	 */
128
+	public function userApproved(User $user)
129
+	{
130
+		$this->send("{$user->getUsername()} approved by " . $this->currentUser->getUsername());
131
+	}
132
+
133
+	/**
134
+	 * send a promoted notification
135
+	 *
136
+	 * @param User $user
137
+	 */
138
+	public function userPromoted(User $user)
139
+	{
140
+		$this->send("{$user->getUsername()} promoted to tool admin by " . $this->currentUser->getUsername());
141
+	}
142
+
143
+	/**
144
+	 * send a declined notification
145
+	 *
146
+	 * @param User   $user
147
+	 * @param string $reason the reason the user was declined
148
+	 */
149
+	public function userDeclined(User $user, $reason)
150
+	{
151
+		$this->send("{$user->getUsername()} declined by " . $this->currentUser->getUsername() . " ($reason)");
152
+	}
153
+
154
+	/**
155
+	 * send a demotion notification
156
+	 *
157
+	 * @param User   $user
158
+	 * @param string $reason the reason the user was demoted
159
+	 */
160
+	public function userDemoted(User $user, $reason)
161
+	{
162
+		$this->send("{$user->getUsername()} demoted by " . $this->currentUser->getUsername() . " ($reason)");
163
+	}
164
+
165
+	/**
166
+	 * send a suspended notification
167
+	 *
168
+	 * @param User   $user
169
+	 * @param string $reason The reason the user has been suspended
170
+	 */
171
+	public function userSuspended(User $user, $reason)
172
+	{
173
+		$this->send("{$user->getUsername()} suspended by " . $this->currentUser->getUsername() . " ($reason)");
174
+	}
175
+
176
+	/**
177
+	 * Send a preference change notification
178
+	 *
179
+	 * @param User $user
180
+	 */
181
+	public function userPrefChange(User $user)
182
+	{
183
+		$this->send("{$user->getUsername()}'s preferences were changed by " . $this->currentUser->getUsername());
184
+	}
185
+
186
+	/**
187
+	 * Send a user renamed notification
188
+	 *
189
+	 * @param User   $user
190
+	 * @param string $old
191
+	 */
192
+	public function userRenamed(User $user, $old)
193
+	{
194
+		$this->send($this->currentUser->getUsername() . " renamed $old to {$user->getUsername()}");
195
+	}
196
+
197
+	/**
198
+	 * @param User   $user
199
+	 * @param string $reason
200
+	 */
201
+	public function userRolesEdited(User $user, $reason)
202
+	{
203
+		$currentUser = $this->currentUser->getUsername();
204
+		$this->send("Active roles for {$user->getUsername()} changed by " . $currentUser . " ($reason)");
205
+	}
206
+
207
+	#endregion
208
+
209
+	#region Site Notice
210
+
211
+	/**
212
+	 * Summary of siteNoticeEdited
213
+	 */
214
+	public function siteNoticeEdited()
215
+	{
216
+		$this->send("Site notice edited by " . $this->currentUser->getUsername());
217
+	}
218
+	#endregion
219
+
220
+	#region Welcome Templates
221
+	/**
222
+	 * Summary of welcomeTemplateCreated
223
+	 *
224
+	 * @param WelcomeTemplate $template
225
+	 */
226
+	public function welcomeTemplateCreated(WelcomeTemplate $template)
227
+	{
228
+		$this->send("Welcome template {$template->getId()} created by " . $this->currentUser->getUsername());
229
+	}
230
+
231
+	/**
232
+	 * Summary of welcomeTemplateDeleted
233
+	 *
234
+	 * @param int $templateid
235
+	 */
236
+	public function welcomeTemplateDeleted($templateid)
237
+	{
238
+		$this->send("Welcome template {$templateid} deleted by " . $this->currentUser->getUsername());
239
+	}
240
+
241
+	/**
242
+	 * Summary of welcomeTemplateEdited
243
+	 *
244
+	 * @param WelcomeTemplate $template
245
+	 */
246
+	public function welcomeTemplateEdited(WelcomeTemplate $template)
247
+	{
248
+		$this->send("Welcome template {$template->getId()} edited by " . $this->currentUser->getUsername());
249
+	}
250
+
251
+	#endregion
252
+
253
+	#region bans
254
+	/**
255
+	 * Summary of banned
256
+	 *
257
+	 * @param Ban $ban
258
+	 */
259
+	public function banned(Ban $ban)
260
+	{
261
+		if ($ban->getDuration() == -1) {
262
+			$duration = "indefinitely";
263
+		}
264
+		else {
265
+			$duration = "until " . date("F j, Y, g:i a", $ban->getDuration());
266
+		}
267
+
268
+		$username = $this->currentUser->getUsername();
269
+
270
+		$this->send("{$ban->getTarget()} banned by {$username} for '{$ban->getReason()}' {$duration}");
271
+	}
272
+
273
+	/**
274
+	 * Summary of unbanned
275
+	 *
276
+	 * @param Ban    $ban
277
+	 * @param string $unbanreason
278
+	 */
279
+	public function unbanned(Ban $ban, $unbanreason)
280
+	{
281
+		$this->send($ban->getTarget() . " unbanned by " . $this->currentUser
282
+				->getUsername() . " (" . $unbanreason . ")");
283
+	}
284
+
285
+	#endregion
286
+
287
+	#region request management
288
+
289
+	/**
290
+	 * Summary of requestReceived
291
+	 *
292
+	 * @param Request $request
293
+	 */
294
+	public function requestReceived(Request $request)
295
+	{
296
+		$this->send(
297
+			IrcColourCode::DARK_GREY . "[["
298
+			. IrcColourCode::DARK_GREEN . "acc:"
299
+			. IrcColourCode::ORANGE . $request->getId()
300
+			. IrcColourCode::DARK_GREY . "]]"
301
+			. IrcColourCode::RED . " N "
302
+			. IrcColourCode::DARK_BLUE . $this->baseUrl . "/internal.php/viewRequest?id={$request->getId()} "
303
+			. IrcColourCode::DARK_RED . "* "
304
+			. IrcColourCode::DARK_GREEN . $request->getName()
305
+			. IrcColourCode::DARK_RED . " * "
306
+			. IrcColourCode::RESET
307
+		);
308
+	}
309
+
310
+	/**
311
+	 * Summary of requestDeferred
312
+	 *
313
+	 * @param Request $request
314
+	 */
315
+	public function requestDeferred(Request $request)
316
+	{
317
+		$availableRequestStates = $this->requestStates;
318
+
319
+		$deferTo = $availableRequestStates[$request->getStatus()]['deferto'];
320
+		$username = $this->currentUser->getUsername();
321
+
322
+		$this->send("Request {$request->getId()} ({$request->getName()}) deferred to {$deferTo} by {$username}");
323
+	}
324
+
325
+	/**
326
+	 *
327
+	 * Summary of requestDeferredWithMail
328
+	 *
329
+	 * @param Request $request
330
+	 */
331
+	public function requestDeferredWithMail(Request $request)
332
+	{
333
+		$availableRequestStates = $this->requestStates;
334
+
335
+		$deferTo = $availableRequestStates[$request->getStatus()]['deferto'];
336
+		$username = $this->currentUser->getUsername();
337
+		$id = $request->getId();
338
+		$name = $request->getName();
339
+
340
+		$this->send("Request {$id} ({$name}) deferred to {$deferTo} with an email by {$username}");
341
+	}
342
+
343
+	/**
344
+	 * Summary of requestClosed
345
+	 *
346
+	 * @param Request $request
347
+	 * @param string  $closetype
348
+	 */
349
+	public function requestClosed(Request $request, $closetype)
350
+	{
351
+		$username = $this->currentUser->getUsername();
352
+
353
+		$this->send("Request {$request->getId()} ({$request->getName()}) closed ($closetype) by {$username}");
354
+	}
355
+
356
+	/**
357
+	 * Summary of sentMail
358
+	 *
359
+	 * @param Request $request
360
+	 */
361
+	public function sentMail(Request $request)
362
+	{
363
+		$this->send($this->currentUser->getUsername()
364
+			. " sent an email related to Request {$request->getId()} ({$request->getName()})");
365
+	}
366
+
367
+	#endregion
368
+
369
+	#region reservations
370
+
371
+	/**
372
+	 * Summary of requestReserved
373
+	 *
374
+	 * @param Request $request
375
+	 */
376
+	public function requestReserved(Request $request)
377
+	{
378
+		$username = $this->currentUser->getUsername();
379
+
380
+		$this->send("Request {$request->getId()} ({$request->getName()}) reserved by {$username}");
381
+	}
382
+
383
+	/**
384
+	 * Summary of requestReserveBroken
385
+	 *
386
+	 * @param Request $request
387
+	 */
388
+	public function requestReserveBroken(Request $request)
389
+	{
390
+		$username = $this->currentUser->getUsername();
391
+
392
+		$this->send("Reservation on request {$request->getId()} ({$request->getName()}) broken by {$username}");
393
+	}
394
+
395
+	/**
396
+	 * Summary of requestUnreserved
397
+	 *
398
+	 * @param Request $request
399
+	 */
400
+	public function requestUnreserved(Request $request)
401
+	{
402
+		$this->send("Request {$request->getId()} ({$request->getName()}) is no longer being handled.");
403
+	}
404
+
405
+	/**
406
+	 * Summary of requestReservationSent
407
+	 *
408
+	 * @param Request $request
409
+	 * @param User    $target
410
+	 */
411
+	public function requestReservationSent(Request $request, User $target)
412
+	{
413
+		$username = $this->currentUser->getUsername();
414
+
415
+		$this->send(
416
+			"Reservation of request {$request->getId()} ({$request->getName()}) sent to {$target->getUsername()} by "
417
+			. $username);
418
+	}
419
+
420
+	#endregion
421
+
422
+	#region comments
423
+
424
+	/**
425
+	 * Summary of commentCreated
426
+	 *
427
+	 * @param Comment $comment
428
+	 * @param Request $request
429
+	 */
430
+	public function commentCreated(Comment $comment, Request $request)
431
+	{
432
+		$username = $this->currentUser->getUsername();
433
+		$visibility = ($comment->getVisibility() == "admin" ? "private " : "");
434
+
435
+		$this->send("{$username} posted a {$visibility}comment on request {$request->getId()} ({$request->getName()})");
436
+	}
437
+
438
+	/**
439
+	 * Summary of commentEdited
440
+	 *
441
+	 * @param Comment $comment
442
+	 * @param Request $request
443
+	 */
444
+	public function commentEdited(Comment $comment, Request $request)
445
+	{
446
+		$username = $this->currentUser->getUsername();
447
+
448
+		$this->send(<<<TAG
449 449
 Comment {$comment->getId()} on request {$request->getId()} ({$request->getName()}) edited by {$username}
450 450
 TAG
451
-        );
452
-    }
453
-
454
-    #endregion
455
-
456
-    #region email management (close reasons)
457
-
458
-    /**
459
-     * Summary of emailCreated
460
-     *
461
-     * @param EmailTemplate $template
462
-     */
463
-    public function emailCreated(EmailTemplate $template)
464
-    {
465
-        $username = $this->currentUser->getUsername();
466
-        $this->send("Email {$template->getId()} ({$template->getName()}) created by " . $username);
467
-    }
468
-
469
-    /**
470
-     * Summary of emailEdited
471
-     *
472
-     * @param EmailTemplate $template
473
-     */
474
-    public function emailEdited(EmailTemplate $template)
475
-    {
476
-        $username = $this->currentUser->getUsername();
477
-        $this->send("Email {$template->getId()} ({$template->getName()}) edited by " . $username);
478
-    }
479
-    #endregion
451
+		);
452
+	}
453
+
454
+	#endregion
455
+
456
+	#region email management (close reasons)
457
+
458
+	/**
459
+	 * Summary of emailCreated
460
+	 *
461
+	 * @param EmailTemplate $template
462
+	 */
463
+	public function emailCreated(EmailTemplate $template)
464
+	{
465
+		$username = $this->currentUser->getUsername();
466
+		$this->send("Email {$template->getId()} ({$template->getName()}) created by " . $username);
467
+	}
468
+
469
+	/**
470
+	 * Summary of emailEdited
471
+	 *
472
+	 * @param EmailTemplate $template
473
+	 */
474
+	public function emailEdited(EmailTemplate $template)
475
+	{
476
+		$username = $this->currentUser->getUsername();
477
+		$this->send("Email {$template->getId()} ({$template->getName()}) edited by " . $username);
478
+	}
479
+	#endregion
480 480
 }
Please login to merge, or discard this patch.
Braces   +2 added lines, -4 removed lines patch added patch discarded remove patch
@@ -60,8 +60,7 @@  discard block
 block discarded – undo
60 60
         if ($this->notificationsDatabase !== null) {
61 61
             $this->notificationsDatabase = $notificationsDatabase;
62 62
             $this->notificationsEnabled = $siteConfiguration->getIrcNotificationsEnabled();
63
-        }
64
-        else {
63
+        } else {
65 64
             $this->notificationsEnabled = false;
66 65
         }
67 66
 
@@ -260,8 +259,7 @@  discard block
 block discarded – undo
260 259
     {
261 260
         if ($ban->getDuration() == -1) {
262 261
             $duration = "indefinitely";
263
-        }
264
-        else {
262
+        } else {
265 263
             $duration = "until " . date("F j, Y, g:i a", $ban->getDuration());
266 264
         }
267 265
 
Please login to merge, or discard this patch.
includes/Helpers/HttpHelper.php 1 patch
Indentation   +99 added lines, -99 removed lines patch added patch discarded remove patch
@@ -12,103 +12,103 @@
 block discarded – undo
12 12
 
13 13
 class HttpHelper
14 14
 {
15
-    private $curlHandle;
16
-
17
-    /**
18
-     * HttpHelper constructor.
19
-     *
20
-     * @param string  $userAgent
21
-     * @param boolean $disableVerifyPeer
22
-     */
23
-    public function __construct($userAgent, $disableVerifyPeer)
24
-    {
25
-        $this->curlHandle = curl_init();
26
-
27
-        curl_setopt($this->curlHandle, CURLOPT_RETURNTRANSFER, true);
28
-        curl_setopt($this->curlHandle, CURLOPT_USERAGENT, $userAgent);
29
-        curl_setopt($this->curlHandle, CURLOPT_FAILONERROR, true);
30
-
31
-        if ($disableVerifyPeer) {
32
-            curl_setopt($this->curlHandle, CURLOPT_SSL_VERIFYPEER, false);
33
-        }
34
-    }
35
-
36
-    public function __destruct()
37
-    {
38
-        curl_close($this->curlHandle);
39
-    }
40
-
41
-    /**
42
-     * Fetches the content of a URL, with an optional parameter set.
43
-     *
44
-     * @param string     $url        The URL to fetch.
45
-     * @param null|array $parameters Key/value pair of GET parameters to add to the request.
46
-     *                               Null lets you handle it yourself.
47
-     *
48
-     * @param array      $headers
49
-     *
50
-     * @return string
51
-     * @throws CurlException
52
-     */
53
-    public function get($url, $parameters = null, $headers = array())
54
-    {
55
-        if ($parameters !== null && is_array($parameters)) {
56
-            $getString = '?' . http_build_query($parameters);
57
-            $url .= $getString;
58
-        }
59
-
60
-        curl_setopt($this->curlHandle, CURLOPT_URL, $url);
61
-
62
-        // Make sure we're doing a GET
63
-        curl_setopt($this->curlHandle, CURLOPT_POST, false);
64
-
65
-        curl_setopt($this->curlHandle, CURLOPT_HTTPHEADER, $headers);
66
-
67
-        $result = curl_exec($this->curlHandle);
68
-
69
-        if ($result === false) {
70
-            $error = curl_error($this->curlHandle);
71
-            throw new CurlException('Remote request failed with error ' . $error);
72
-        }
73
-
74
-        return $result;
75
-    }
76
-
77
-    /**
78
-     * Posts data to a URL
79
-     *
80
-     * @param string $url        The URL to fetch.
81
-     * @param array  $parameters Key/value pair of POST parameters to add to the request.
82
-     * @param array  $headers
83
-     *
84
-     * @return string
85
-     * @throws CurlException
86
-     */
87
-    public function post($url, $parameters, $headers = array())
88
-    {
89
-        curl_setopt($this->curlHandle, CURLOPT_URL, $url);
90
-
91
-        // Make sure we're doing a POST
92
-        curl_setopt($this->curlHandle, CURLOPT_POST, true);
93
-        curl_setopt($this->curlHandle, CURLOPT_POSTFIELDS, http_build_query($parameters));
94
-
95
-        curl_setopt($this->curlHandle, CURLOPT_HTTPHEADER, $headers);
96
-
97
-        $result = curl_exec($this->curlHandle);
98
-
99
-        if ($result === false) {
100
-            $error = curl_error($this->curlHandle);
101
-            throw new CurlException('Remote request failed with error ' . $error);
102
-        }
103
-
104
-        return $result;
105
-    }
106
-
107
-    /**
108
-     * @return string
109
-     */
110
-    public function getError()
111
-    {
112
-        return curl_error($this->curlHandle);
113
-    }
15
+	private $curlHandle;
16
+
17
+	/**
18
+	 * HttpHelper constructor.
19
+	 *
20
+	 * @param string  $userAgent
21
+	 * @param boolean $disableVerifyPeer
22
+	 */
23
+	public function __construct($userAgent, $disableVerifyPeer)
24
+	{
25
+		$this->curlHandle = curl_init();
26
+
27
+		curl_setopt($this->curlHandle, CURLOPT_RETURNTRANSFER, true);
28
+		curl_setopt($this->curlHandle, CURLOPT_USERAGENT, $userAgent);
29
+		curl_setopt($this->curlHandle, CURLOPT_FAILONERROR, true);
30
+
31
+		if ($disableVerifyPeer) {
32
+			curl_setopt($this->curlHandle, CURLOPT_SSL_VERIFYPEER, false);
33
+		}
34
+	}
35
+
36
+	public function __destruct()
37
+	{
38
+		curl_close($this->curlHandle);
39
+	}
40
+
41
+	/**
42
+	 * Fetches the content of a URL, with an optional parameter set.
43
+	 *
44
+	 * @param string     $url        The URL to fetch.
45
+	 * @param null|array $parameters Key/value pair of GET parameters to add to the request.
46
+	 *                               Null lets you handle it yourself.
47
+	 *
48
+	 * @param array      $headers
49
+	 *
50
+	 * @return string
51
+	 * @throws CurlException
52
+	 */
53
+	public function get($url, $parameters = null, $headers = array())
54
+	{
55
+		if ($parameters !== null && is_array($parameters)) {
56
+			$getString = '?' . http_build_query($parameters);
57
+			$url .= $getString;
58
+		}
59
+
60
+		curl_setopt($this->curlHandle, CURLOPT_URL, $url);
61
+
62
+		// Make sure we're doing a GET
63
+		curl_setopt($this->curlHandle, CURLOPT_POST, false);
64
+
65
+		curl_setopt($this->curlHandle, CURLOPT_HTTPHEADER, $headers);
66
+
67
+		$result = curl_exec($this->curlHandle);
68
+
69
+		if ($result === false) {
70
+			$error = curl_error($this->curlHandle);
71
+			throw new CurlException('Remote request failed with error ' . $error);
72
+		}
73
+
74
+		return $result;
75
+	}
76
+
77
+	/**
78
+	 * Posts data to a URL
79
+	 *
80
+	 * @param string $url        The URL to fetch.
81
+	 * @param array  $parameters Key/value pair of POST parameters to add to the request.
82
+	 * @param array  $headers
83
+	 *
84
+	 * @return string
85
+	 * @throws CurlException
86
+	 */
87
+	public function post($url, $parameters, $headers = array())
88
+	{
89
+		curl_setopt($this->curlHandle, CURLOPT_URL, $url);
90
+
91
+		// Make sure we're doing a POST
92
+		curl_setopt($this->curlHandle, CURLOPT_POST, true);
93
+		curl_setopt($this->curlHandle, CURLOPT_POSTFIELDS, http_build_query($parameters));
94
+
95
+		curl_setopt($this->curlHandle, CURLOPT_HTTPHEADER, $headers);
96
+
97
+		$result = curl_exec($this->curlHandle);
98
+
99
+		if ($result === false) {
100
+			$error = curl_error($this->curlHandle);
101
+			throw new CurlException('Remote request failed with error ' . $error);
102
+		}
103
+
104
+		return $result;
105
+	}
106
+
107
+	/**
108
+	 * @return string
109
+	 */
110
+	public function getError()
111
+	{
112
+		return curl_error($this->curlHandle);
113
+	}
114 114
 }
115 115
\ No newline at end of file
Please login to merge, or discard this patch.
includes/Environment.php 1 patch
Indentation   +15 added lines, -15 removed lines patch added patch discarded remove patch
@@ -13,21 +13,21 @@
 block discarded – undo
13 13
  */
14 14
 class Environment
15 15
 {
16
-    /**
17
-     * @var string Cached copy of the tool version
18
-     */
19
-    private static $toolVersion = null;
16
+	/**
17
+	 * @var string Cached copy of the tool version
18
+	 */
19
+	private static $toolVersion = null;
20 20
 
21
-    /**
22
-     * Gets the tool version, using cached data if available.
23
-     * @return string
24
-     */
25
-    public static function getToolVersion()
26
-    {
27
-        if (self::$toolVersion === null) {
28
-            self::$toolVersion = exec("git describe --always --dirty");
29
-        }
21
+	/**
22
+	 * Gets the tool version, using cached data if available.
23
+	 * @return string
24
+	 */
25
+	public static function getToolVersion()
26
+	{
27
+		if (self::$toolVersion === null) {
28
+			self::$toolVersion = exec("git describe --always --dirty");
29
+		}
30 30
 
31
-        return self::$toolVersion;
32
-    }
31
+		return self::$toolVersion;
32
+	}
33 33
 }
Please login to merge, or discard this patch.
includes/Security/SecurityManager.php 3 patches
Indentation   +196 added lines, -196 removed lines patch added patch discarded remove patch
@@ -14,200 +14,200 @@
 block discarded – undo
14 14
 
15 15
 final class SecurityManager
16 16
 {
17
-    const ALLOWED = 1;
18
-    const ERROR_NOT_IDENTIFIED = 2;
19
-    const ERROR_DENIED = 3;
20
-    /** @var IdentificationVerifier */
21
-    private $identificationVerifier;
22
-    /**
23
-     * @var RoleConfiguration
24
-     */
25
-    private $roleConfiguration;
26
-
27
-    /**
28
-     * SecurityManager constructor.
29
-     *
30
-     * @param IdentificationVerifier $identificationVerifier
31
-     * @param RoleConfiguration      $roleConfiguration
32
-     */
33
-    public function __construct(
34
-        IdentificationVerifier $identificationVerifier,
35
-        RoleConfiguration $roleConfiguration
36
-    ) {
37
-        $this->identificationVerifier = $identificationVerifier;
38
-        $this->roleConfiguration = $roleConfiguration;
39
-    }
40
-
41
-    /**
42
-     * Tests if a user is allowed to perform an action.
43
-     *
44
-     * This method should form a hard, deterministic security barrier, and only return true if it is absolutely sure
45
-     * that a user should have access to something.
46
-     *
47
-     * @param string $page
48
-     * @param string $route
49
-     * @param User   $user
50
-     *
51
-     * @return int
52
-     *
53
-     * @category Security-Critical
54
-     */
55
-    public function allows($page, $route, User $user)
56
-    {
57
-        $this->getActiveRoles($user, $activeRoles, $inactiveRoles);
58
-
59
-        $availableRights = $this->flattenRoles($activeRoles);
60
-        $testResult = $this->findResult($availableRights, $page, $route);
61
-
62
-        if ($testResult !== null) {
63
-            // We got a firm result here, so just return it.
64
-            return $testResult;
65
-        }
66
-
67
-        // No firm result yet, so continue testing the inactive roles so we can give a better error.
68
-        $inactiveRights = $this->flattenRoles($inactiveRoles);
69
-        $testResult = $this->findResult($inactiveRights, $page, $route);
70
-
71
-        if ($testResult === self::ALLOWED) {
72
-            // The user is allowed to access this, but their role is inactive.
73
-            return self::ERROR_NOT_IDENTIFIED;
74
-        }
75
-
76
-        // Other options from the secondary test are denied and inconclusive, which at this point defaults to denied.
77
-        return self::ERROR_DENIED;
78
-    }
79
-
80
-    /**
81
-     * @param array  $pseudoRole The role (flattened) to check
82
-     * @param string $page       The page class to check
83
-     * @param string $route      The page route to check
84
-     *
85
-     * @return int|null
86
-     */
87
-    private function findResult($pseudoRole, $page, $route)
88
-    {
89
-        if (isset($pseudoRole[$page])) {
90
-            // check for deny on catch-all route
91
-            if (isset($pseudoRole[$page][RoleConfiguration::ALL])) {
92
-                if ($pseudoRole[$page][RoleConfiguration::ALL] === RoleConfiguration::ACCESS_DENY) {
93
-                    return self::ERROR_DENIED;
94
-                }
95
-            }
96
-
97
-            // check normal route
98
-            if (isset($pseudoRole[$page][$route])) {
99
-                if ($pseudoRole[$page][$route] === RoleConfiguration::ACCESS_DENY) {
100
-                    return self::ERROR_DENIED;
101
-                }
102
-
103
-                if ($pseudoRole[$page][$route] === RoleConfiguration::ACCESS_ALLOW) {
104
-                    return self::ALLOWED;
105
-                }
106
-            }
107
-
108
-            // check for allowed on catch-all route
109
-            if (isset($pseudoRole[$page][RoleConfiguration::ALL])) {
110
-                if ($pseudoRole[$page][RoleConfiguration::ALL] === RoleConfiguration::ACCESS_ALLOW) {
111
-                    return self::ALLOWED;
112
-                }
113
-            }
114
-        }
115
-
116
-        // return indeterminate result
117
-        return null;
118
-    }
119
-
120
-    /**
121
-     * Takes an array of roles and flattens the values to a single set.
122
-     *
123
-     * @param array $activeRoles
124
-     *
125
-     * @return array
126
-     */
127
-    private function flattenRoles($activeRoles)
128
-    {
129
-        $result = array();
130
-
131
-        $roleConfig = $this->roleConfiguration->getApplicableRoles($activeRoles);
132
-
133
-        // Iterate over every page in every role
134
-        foreach ($roleConfig as $role) {
135
-            foreach ($role as $page => $pageRights) {
136
-                // Create holder in result for this page
137
-                if (!isset($result[$page])) {
138
-                    $result[$page] = array();
139
-                }
140
-
141
-                foreach ($pageRights as $action => $permission) {
142
-                    // Deny takes precedence, so if it's set, don't change it.
143
-                    if (isset($result[$page][$action])) {
144
-                        if ($result[$page][$action] === RoleConfiguration::ACCESS_DENY) {
145
-                            continue;
146
-                        }
147
-                    }
148
-
149
-                    if ($permission === RoleConfiguration::ACCESS_DEFAULT) {
150
-                        // Configured to do precisely nothing.
151
-                        continue;
152
-                    }
153
-
154
-                    $result[$page][$action] = $permission;
155
-                }
156
-            }
157
-        }
158
-
159
-        return $result;
160
-    }
161
-
162
-    /**
163
-     * @param User  $user
164
-     * @param array $activeRoles
165
-     * @param array $inactiveRoles
166
-     */
167
-    public function getActiveRoles(User $user, &$activeRoles, &$inactiveRoles)
168
-    {
169
-        // Default to the community user here, because the main user is logged out
170
-        $identified = false;
171
-        $userRoles = array('public');
172
-
173
-        // if we're not the community user, get our real rights.
174
-        if (!$user->isCommunityUser()) {
175
-            // Check the user's status - only active users are allowed the effects of roles
176
-
177
-            $userRoles[] = 'loggedIn';
178
-
179
-            if ($user->isActive()) {
180
-                $ur = UserRole::getForUser($user->getId(), $user->getDatabase());
181
-
182
-                // NOTE: public is still in this array.
183
-                foreach ($ur as $r) {
184
-                    $userRoles[] = $r->getRole();
185
-                }
186
-
187
-                $identified = $user->isIdentified($this->identificationVerifier);
188
-            }
189
-        }
190
-
191
-        $activeRoles = array();
192
-        $inactiveRoles = array();
193
-
194
-        /** @var string $v */
195
-        foreach ($userRoles as $v) {
196
-            if ($this->roleConfiguration->roleNeedsIdentification($v)) {
197
-                if ($identified) {
198
-                    $activeRoles[] = $v;
199
-                }
200
-                else {
201
-                    $inactiveRoles[] = $v;
202
-                }
203
-            }
204
-            else {
205
-                $activeRoles[] = $v;
206
-            }
207
-        }
208
-    }
209
-
210
-    public function getRoleConfiguration(){
211
-        return $this->roleConfiguration;
212
-    }
17
+	const ALLOWED = 1;
18
+	const ERROR_NOT_IDENTIFIED = 2;
19
+	const ERROR_DENIED = 3;
20
+	/** @var IdentificationVerifier */
21
+	private $identificationVerifier;
22
+	/**
23
+	 * @var RoleConfiguration
24
+	 */
25
+	private $roleConfiguration;
26
+
27
+	/**
28
+	 * SecurityManager constructor.
29
+	 *
30
+	 * @param IdentificationVerifier $identificationVerifier
31
+	 * @param RoleConfiguration      $roleConfiguration
32
+	 */
33
+	public function __construct(
34
+		IdentificationVerifier $identificationVerifier,
35
+		RoleConfiguration $roleConfiguration
36
+	) {
37
+		$this->identificationVerifier = $identificationVerifier;
38
+		$this->roleConfiguration = $roleConfiguration;
39
+	}
40
+
41
+	/**
42
+	 * Tests if a user is allowed to perform an action.
43
+	 *
44
+	 * This method should form a hard, deterministic security barrier, and only return true if it is absolutely sure
45
+	 * that a user should have access to something.
46
+	 *
47
+	 * @param string $page
48
+	 * @param string $route
49
+	 * @param User   $user
50
+	 *
51
+	 * @return int
52
+	 *
53
+	 * @category Security-Critical
54
+	 */
55
+	public function allows($page, $route, User $user)
56
+	{
57
+		$this->getActiveRoles($user, $activeRoles, $inactiveRoles);
58
+
59
+		$availableRights = $this->flattenRoles($activeRoles);
60
+		$testResult = $this->findResult($availableRights, $page, $route);
61
+
62
+		if ($testResult !== null) {
63
+			// We got a firm result here, so just return it.
64
+			return $testResult;
65
+		}
66
+
67
+		// No firm result yet, so continue testing the inactive roles so we can give a better error.
68
+		$inactiveRights = $this->flattenRoles($inactiveRoles);
69
+		$testResult = $this->findResult($inactiveRights, $page, $route);
70
+
71
+		if ($testResult === self::ALLOWED) {
72
+			// The user is allowed to access this, but their role is inactive.
73
+			return self::ERROR_NOT_IDENTIFIED;
74
+		}
75
+
76
+		// Other options from the secondary test are denied and inconclusive, which at this point defaults to denied.
77
+		return self::ERROR_DENIED;
78
+	}
79
+
80
+	/**
81
+	 * @param array  $pseudoRole The role (flattened) to check
82
+	 * @param string $page       The page class to check
83
+	 * @param string $route      The page route to check
84
+	 *
85
+	 * @return int|null
86
+	 */
87
+	private function findResult($pseudoRole, $page, $route)
88
+	{
89
+		if (isset($pseudoRole[$page])) {
90
+			// check for deny on catch-all route
91
+			if (isset($pseudoRole[$page][RoleConfiguration::ALL])) {
92
+				if ($pseudoRole[$page][RoleConfiguration::ALL] === RoleConfiguration::ACCESS_DENY) {
93
+					return self::ERROR_DENIED;
94
+				}
95
+			}
96
+
97
+			// check normal route
98
+			if (isset($pseudoRole[$page][$route])) {
99
+				if ($pseudoRole[$page][$route] === RoleConfiguration::ACCESS_DENY) {
100
+					return self::ERROR_DENIED;
101
+				}
102
+
103
+				if ($pseudoRole[$page][$route] === RoleConfiguration::ACCESS_ALLOW) {
104
+					return self::ALLOWED;
105
+				}
106
+			}
107
+
108
+			// check for allowed on catch-all route
109
+			if (isset($pseudoRole[$page][RoleConfiguration::ALL])) {
110
+				if ($pseudoRole[$page][RoleConfiguration::ALL] === RoleConfiguration::ACCESS_ALLOW) {
111
+					return self::ALLOWED;
112
+				}
113
+			}
114
+		}
115
+
116
+		// return indeterminate result
117
+		return null;
118
+	}
119
+
120
+	/**
121
+	 * Takes an array of roles and flattens the values to a single set.
122
+	 *
123
+	 * @param array $activeRoles
124
+	 *
125
+	 * @return array
126
+	 */
127
+	private function flattenRoles($activeRoles)
128
+	{
129
+		$result = array();
130
+
131
+		$roleConfig = $this->roleConfiguration->getApplicableRoles($activeRoles);
132
+
133
+		// Iterate over every page in every role
134
+		foreach ($roleConfig as $role) {
135
+			foreach ($role as $page => $pageRights) {
136
+				// Create holder in result for this page
137
+				if (!isset($result[$page])) {
138
+					$result[$page] = array();
139
+				}
140
+
141
+				foreach ($pageRights as $action => $permission) {
142
+					// Deny takes precedence, so if it's set, don't change it.
143
+					if (isset($result[$page][$action])) {
144
+						if ($result[$page][$action] === RoleConfiguration::ACCESS_DENY) {
145
+							continue;
146
+						}
147
+					}
148
+
149
+					if ($permission === RoleConfiguration::ACCESS_DEFAULT) {
150
+						// Configured to do precisely nothing.
151
+						continue;
152
+					}
153
+
154
+					$result[$page][$action] = $permission;
155
+				}
156
+			}
157
+		}
158
+
159
+		return $result;
160
+	}
161
+
162
+	/**
163
+	 * @param User  $user
164
+	 * @param array $activeRoles
165
+	 * @param array $inactiveRoles
166
+	 */
167
+	public function getActiveRoles(User $user, &$activeRoles, &$inactiveRoles)
168
+	{
169
+		// Default to the community user here, because the main user is logged out
170
+		$identified = false;
171
+		$userRoles = array('public');
172
+
173
+		// if we're not the community user, get our real rights.
174
+		if (!$user->isCommunityUser()) {
175
+			// Check the user's status - only active users are allowed the effects of roles
176
+
177
+			$userRoles[] = 'loggedIn';
178
+
179
+			if ($user->isActive()) {
180
+				$ur = UserRole::getForUser($user->getId(), $user->getDatabase());
181
+
182
+				// NOTE: public is still in this array.
183
+				foreach ($ur as $r) {
184
+					$userRoles[] = $r->getRole();
185
+				}
186
+
187
+				$identified = $user->isIdentified($this->identificationVerifier);
188
+			}
189
+		}
190
+
191
+		$activeRoles = array();
192
+		$inactiveRoles = array();
193
+
194
+		/** @var string $v */
195
+		foreach ($userRoles as $v) {
196
+			if ($this->roleConfiguration->roleNeedsIdentification($v)) {
197
+				if ($identified) {
198
+					$activeRoles[] = $v;
199
+				}
200
+				else {
201
+					$inactiveRoles[] = $v;
202
+				}
203
+			}
204
+			else {
205
+				$activeRoles[] = $v;
206
+			}
207
+		}
208
+	}
209
+
210
+	public function getRoleConfiguration(){
211
+		return $this->roleConfiguration;
212
+	}
213 213
 }
Please login to merge, or discard this patch.
Spacing   +1 added lines, -1 removed lines patch added patch discarded remove patch
@@ -207,7 +207,7 @@
 block discarded – undo
207 207
         }
208 208
     }
209 209
 
210
-    public function getRoleConfiguration(){
210
+    public function getRoleConfiguration() {
211 211
         return $this->roleConfiguration;
212 212
     }
213 213
 }
Please login to merge, or discard this patch.
Braces   +4 added lines, -5 removed lines patch added patch discarded remove patch
@@ -196,18 +196,17 @@
 block discarded – undo
196 196
             if ($this->roleConfiguration->roleNeedsIdentification($v)) {
197 197
                 if ($identified) {
198 198
                     $activeRoles[] = $v;
199
-                }
200
-                else {
199
+                } else {
201 200
                     $inactiveRoles[] = $v;
202 201
                 }
203
-            }
204
-            else {
202
+            } else {
205 203
                 $activeRoles[] = $v;
206 204
             }
207 205
         }
208 206
     }
209 207
 
210
-    public function getRoleConfiguration(){
208
+    public function getRoleConfiguration()
209
+    {
211 210
         return $this->roleConfiguration;
212 211
     }
213 212
 }
Please login to merge, or discard this patch.
includes/Security/RoleConfiguration.php 1 patch
Indentation   +307 added lines, -307 removed lines patch added patch discarded remove patch
@@ -41,338 +41,338 @@
 block discarded – undo
41 41
 
42 42
 class RoleConfiguration
43 43
 {
44
-    const ACCESS_ALLOW = 1;
45
-    const ACCESS_DENY = -1;
46
-    const ACCESS_DEFAULT = 0;
47
-    const MAIN = 'main';
48
-    const ALL = '*';
49
-    /**
50
-     * A map of roles to rights
51
-     *
52
-     * For example:
53
-     *
54
-     * array(
55
-     *   'myrole' => array(
56
-     *       PageMyPage::class => array(
57
-     *           'edit' => self::ACCESS_ALLOW,
58
-     *           'create' => self::ACCESS_DENY,
59
-     *       )
60
-     *   )
61
-     * )
62
-     *
63
-     * Note that DENY takes precedence over everything else when roles are combined, followed by ALLOW, followed by
64
-     * DEFAULT. Thus, if you have the following ([A]llow, [D]eny, [-] (default)) grants in different roles, this should
65
-     * be the expected result:
66
-     *
67
-     * - (-,-,-) = - (default because nothing to explicitly say allowed or denied equates to a denial)
68
-     * - (A,-,-) = A
69
-     * - (D,-,-) = D
70
-     * - (A,D,-) = D (deny takes precedence over allow)
71
-     * - (A,A,A) = A (repetition has no effect)
72
-     *
73
-     * The public role is special, and is applied to all users automatically. Avoid using deny on this role.
74
-     *
75
-     * @var array
76
-     */
77
-    private $roleConfig = array(
78
-        'public'            => array(
79
-            /*
44
+	const ACCESS_ALLOW = 1;
45
+	const ACCESS_DENY = -1;
46
+	const ACCESS_DEFAULT = 0;
47
+	const MAIN = 'main';
48
+	const ALL = '*';
49
+	/**
50
+	 * A map of roles to rights
51
+	 *
52
+	 * For example:
53
+	 *
54
+	 * array(
55
+	 *   'myrole' => array(
56
+	 *       PageMyPage::class => array(
57
+	 *           'edit' => self::ACCESS_ALLOW,
58
+	 *           'create' => self::ACCESS_DENY,
59
+	 *       )
60
+	 *   )
61
+	 * )
62
+	 *
63
+	 * Note that DENY takes precedence over everything else when roles are combined, followed by ALLOW, followed by
64
+	 * DEFAULT. Thus, if you have the following ([A]llow, [D]eny, [-] (default)) grants in different roles, this should
65
+	 * be the expected result:
66
+	 *
67
+	 * - (-,-,-) = - (default because nothing to explicitly say allowed or denied equates to a denial)
68
+	 * - (A,-,-) = A
69
+	 * - (D,-,-) = D
70
+	 * - (A,D,-) = D (deny takes precedence over allow)
71
+	 * - (A,A,A) = A (repetition has no effect)
72
+	 *
73
+	 * The public role is special, and is applied to all users automatically. Avoid using deny on this role.
74
+	 *
75
+	 * @var array
76
+	 */
77
+	private $roleConfig = array(
78
+		'public'            => array(
79
+			/*
80 80
              * THIS ROLE IS GRANTED TO ALL LOGGED *OUT* USERS IMPLICITLY.
81 81
              *
82 82
              * USERS IN THIS ROLE DO NOT HAVE TO BE IDENTIFIED TO GET THE RIGHTS CONFERRED HERE.
83 83
              * DO NOT ADD ANY SECURITY-SENSITIVE RIGHTS HERE.
84 84
              */
85
-            '_childRoles'    => array(
86
-                'publicStats',
87
-            ),
88
-            PageOAuth::class => array(
89
-                'callback' => self::ACCESS_ALLOW,
90
-            ),
91
-            PageTeam::class  => array(
92
-                self::MAIN => self::ACCESS_ALLOW,
93
-            ),
94
-        ),
95
-        'loggedIn'            => array(
96
-            /*
85
+			'_childRoles'    => array(
86
+				'publicStats',
87
+			),
88
+			PageOAuth::class => array(
89
+				'callback' => self::ACCESS_ALLOW,
90
+			),
91
+			PageTeam::class  => array(
92
+				self::MAIN => self::ACCESS_ALLOW,
93
+			),
94
+		),
95
+		'loggedIn'            => array(
96
+			/*
97 97
              * THIS ROLE IS GRANTED TO ALL LOGGED IN USERS IMPLICITLY.
98 98
              *
99 99
              * USERS IN THIS ROLE DO NOT HAVE TO BE IDENTIFIED TO GET THE RIGHTS CONFERRED HERE.
100 100
              * DO NOT ADD ANY SECURITY-SENSITIVE RIGHTS HERE.
101 101
              */
102
-            '_childRoles'    => array(
103
-                'public',
104
-            ),
105
-            PagePreferences::class               => array(
106
-                self::MAIN       => self::ACCESS_ALLOW,
107
-                'changePassword' => self::ACCESS_ALLOW,
108
-            ),
109
-            PageOAuth::class                     => array(
110
-                'attach' => self::ACCESS_ALLOW,
111
-                'detach' => self::ACCESS_ALLOW,
112
-            ),
113
-        ),
114
-        'user'              => array(
115
-            '_description' => 'A standard tool user.',
116
-            '_editableBy' => array('admin', 'toolRoot'),
117
-            '_childRoles'                        => array(
118
-                'internalStats',
119
-            ),
120
-            PageMain::class                      => array(
121
-                self::MAIN => self::ACCESS_ALLOW,
122
-            ),
123
-            PageBan::class                       => array(
124
-                self::MAIN => self::ACCESS_ALLOW,
125
-            ),
126
-            PageEditComment::class               => array(
127
-                self::MAIN => self::ACCESS_ALLOW,
128
-            ),
129
-            PageEmailManagement::class           => array(
130
-                self::MAIN => self::ACCESS_ALLOW,
131
-                'view'     => self::ACCESS_ALLOW,
132
-            ),
133
-            PageExpandedRequestList::class       => array(
134
-                self::MAIN => self::ACCESS_ALLOW,
135
-            ),
136
-            PageLog::class                       => array(
137
-                self::MAIN => self::ACCESS_ALLOW,
138
-            ),
139
-            PageSearch::class                    => array(
140
-                self::MAIN => self::ACCESS_ALLOW,
141
-            ),
142
-            PageWelcomeTemplateManagement::class => array(
143
-                self::MAIN => self::ACCESS_ALLOW,
144
-                'select'   => self::ACCESS_ALLOW,
145
-                'view'     => self::ACCESS_ALLOW,
146
-            ),
147
-            PageViewRequest::class               => array(
148
-                self::MAIN => self::ACCESS_ALLOW,
149
-            ),
150
-            'RequestData'                        => array(
151
-                'seePrivateDataWhenReserved' => self::ACCESS_ALLOW,
152
-                'seePrivateDataWithHash'     => self::ACCESS_ALLOW,
153
-            ),
154
-            PageCustomClose::class               => array(
155
-                self::MAIN => self::ACCESS_ALLOW,
156
-            ),
157
-            PageComment::class                   => array(
158
-                self::MAIN => self::ACCESS_ALLOW,
159
-            ),
160
-            PageCloseRequest::class              => array(
161
-                self::MAIN => self::ACCESS_ALLOW,
162
-            ),
163
-            PageDeferRequest::class              => array(
164
-                self::MAIN => self::ACCESS_ALLOW,
165
-            ),
166
-            PageDropRequest::class               => array(
167
-                self::MAIN => self::ACCESS_ALLOW,
168
-            ),
169
-            PageReservation::class               => array(
170
-                self::MAIN => self::ACCESS_ALLOW,
171
-            ),
172
-            PageSendToUser::class                => array(
173
-                self::MAIN => self::ACCESS_ALLOW,
174
-            ),
175
-            PageBreakReservation::class          => array(
176
-                self::MAIN => self::ACCESS_ALLOW,
177
-            ),
102
+			'_childRoles'    => array(
103
+				'public',
104
+			),
105
+			PagePreferences::class               => array(
106
+				self::MAIN       => self::ACCESS_ALLOW,
107
+				'changePassword' => self::ACCESS_ALLOW,
108
+			),
109
+			PageOAuth::class                     => array(
110
+				'attach' => self::ACCESS_ALLOW,
111
+				'detach' => self::ACCESS_ALLOW,
112
+			),
113
+		),
114
+		'user'              => array(
115
+			'_description' => 'A standard tool user.',
116
+			'_editableBy' => array('admin', 'toolRoot'),
117
+			'_childRoles'                        => array(
118
+				'internalStats',
119
+			),
120
+			PageMain::class                      => array(
121
+				self::MAIN => self::ACCESS_ALLOW,
122
+			),
123
+			PageBan::class                       => array(
124
+				self::MAIN => self::ACCESS_ALLOW,
125
+			),
126
+			PageEditComment::class               => array(
127
+				self::MAIN => self::ACCESS_ALLOW,
128
+			),
129
+			PageEmailManagement::class           => array(
130
+				self::MAIN => self::ACCESS_ALLOW,
131
+				'view'     => self::ACCESS_ALLOW,
132
+			),
133
+			PageExpandedRequestList::class       => array(
134
+				self::MAIN => self::ACCESS_ALLOW,
135
+			),
136
+			PageLog::class                       => array(
137
+				self::MAIN => self::ACCESS_ALLOW,
138
+			),
139
+			PageSearch::class                    => array(
140
+				self::MAIN => self::ACCESS_ALLOW,
141
+			),
142
+			PageWelcomeTemplateManagement::class => array(
143
+				self::MAIN => self::ACCESS_ALLOW,
144
+				'select'   => self::ACCESS_ALLOW,
145
+				'view'     => self::ACCESS_ALLOW,
146
+			),
147
+			PageViewRequest::class               => array(
148
+				self::MAIN => self::ACCESS_ALLOW,
149
+			),
150
+			'RequestData'                        => array(
151
+				'seePrivateDataWhenReserved' => self::ACCESS_ALLOW,
152
+				'seePrivateDataWithHash'     => self::ACCESS_ALLOW,
153
+			),
154
+			PageCustomClose::class               => array(
155
+				self::MAIN => self::ACCESS_ALLOW,
156
+			),
157
+			PageComment::class                   => array(
158
+				self::MAIN => self::ACCESS_ALLOW,
159
+			),
160
+			PageCloseRequest::class              => array(
161
+				self::MAIN => self::ACCESS_ALLOW,
162
+			),
163
+			PageDeferRequest::class              => array(
164
+				self::MAIN => self::ACCESS_ALLOW,
165
+			),
166
+			PageDropRequest::class               => array(
167
+				self::MAIN => self::ACCESS_ALLOW,
168
+			),
169
+			PageReservation::class               => array(
170
+				self::MAIN => self::ACCESS_ALLOW,
171
+			),
172
+			PageSendToUser::class                => array(
173
+				self::MAIN => self::ACCESS_ALLOW,
174
+			),
175
+			PageBreakReservation::class          => array(
176
+				self::MAIN => self::ACCESS_ALLOW,
177
+			),
178 178
 
179
-        ),
180
-        'admin'             => array(
181
-            '_description' => 'A tool administrator.',
182
-            '_editableBy' => array('admin', 'toolRoot'),
183
-            '_childRoles'                        => array(
184
-                'user', 'requestAdminTools',
185
-            ),
186
-            PageEmailManagement::class           => array(
187
-                'edit'   => self::ACCESS_ALLOW,
188
-                'create' => self::ACCESS_ALLOW,
189
-            ),
190
-            PageSiteNotice::class                => array(
191
-                self::MAIN => self::ACCESS_ALLOW,
192
-            ),
193
-            PageUserManagement::class            => array(
194
-                self::MAIN  => self::ACCESS_ALLOW,
195
-                'approve'   => self::ACCESS_ALLOW,
196
-                'decline'   => self::ACCESS_ALLOW,
197
-                'rename'    => self::ACCESS_ALLOW,
198
-                'editUser'  => self::ACCESS_ALLOW,
199
-                'suspend'   => self::ACCESS_ALLOW,
200
-                'editRoles' => self::ACCESS_ALLOW,
201
-            ),
202
-            PageWelcomeTemplateManagement::class => array(
203
-                'edit'   => self::ACCESS_ALLOW,
204
-                'delete' => self::ACCESS_ALLOW,
205
-                'add'    => self::ACCESS_ALLOW,
206
-            ),
207
-        ),
208
-        'checkuser'         => array(
209
-            '_description' => 'A user with CheckUser access',
210
-            '_editableBy' => array('checkuser', 'toolRoot'),
211
-            '_childRoles'             => array(
212
-                'user', 'requestAdminTools',
213
-            ),
214
-            PageUserManagement::class => array(
215
-                self::MAIN  => self::ACCESS_ALLOW,
216
-                'suspend'   => self::ACCESS_ALLOW,
217
-                'editRoles' => self::ACCESS_ALLOW,
218
-            ),
219
-            'RequestData'             => array(
220
-                'seeUserAgentData' => self::ACCESS_ALLOW,
221
-            ),
222
-        ),
223
-        'toolRoot'         => array(
224
-            '_description' => 'A user with shell access to the servers running the tool',
225
-            '_editableBy' => array('toolRoot'),
226
-            '_childRoles'             => array(
227
-                'admin', 'checkuser',
228
-            ),
229
-        ),
179
+		),
180
+		'admin'             => array(
181
+			'_description' => 'A tool administrator.',
182
+			'_editableBy' => array('admin', 'toolRoot'),
183
+			'_childRoles'                        => array(
184
+				'user', 'requestAdminTools',
185
+			),
186
+			PageEmailManagement::class           => array(
187
+				'edit'   => self::ACCESS_ALLOW,
188
+				'create' => self::ACCESS_ALLOW,
189
+			),
190
+			PageSiteNotice::class                => array(
191
+				self::MAIN => self::ACCESS_ALLOW,
192
+			),
193
+			PageUserManagement::class            => array(
194
+				self::MAIN  => self::ACCESS_ALLOW,
195
+				'approve'   => self::ACCESS_ALLOW,
196
+				'decline'   => self::ACCESS_ALLOW,
197
+				'rename'    => self::ACCESS_ALLOW,
198
+				'editUser'  => self::ACCESS_ALLOW,
199
+				'suspend'   => self::ACCESS_ALLOW,
200
+				'editRoles' => self::ACCESS_ALLOW,
201
+			),
202
+			PageWelcomeTemplateManagement::class => array(
203
+				'edit'   => self::ACCESS_ALLOW,
204
+				'delete' => self::ACCESS_ALLOW,
205
+				'add'    => self::ACCESS_ALLOW,
206
+			),
207
+		),
208
+		'checkuser'         => array(
209
+			'_description' => 'A user with CheckUser access',
210
+			'_editableBy' => array('checkuser', 'toolRoot'),
211
+			'_childRoles'             => array(
212
+				'user', 'requestAdminTools',
213
+			),
214
+			PageUserManagement::class => array(
215
+				self::MAIN  => self::ACCESS_ALLOW,
216
+				'suspend'   => self::ACCESS_ALLOW,
217
+				'editRoles' => self::ACCESS_ALLOW,
218
+			),
219
+			'RequestData'             => array(
220
+				'seeUserAgentData' => self::ACCESS_ALLOW,
221
+			),
222
+		),
223
+		'toolRoot'         => array(
224
+			'_description' => 'A user with shell access to the servers running the tool',
225
+			'_editableBy' => array('toolRoot'),
226
+			'_childRoles'             => array(
227
+				'admin', 'checkuser',
228
+			),
229
+		),
230 230
 
231
-        // Child roles go below this point
232
-        'publicStats'       => array(
233
-            '_hidden'               => true,
234
-            StatsUsers::class       => array(
235
-                self::MAIN => self::ACCESS_ALLOW,
236
-                'detail'   => self::ACCESS_ALLOW,
237
-            ),
238
-            StatsTopCreators::class => array(
239
-                self::MAIN => self::ACCESS_ALLOW,
240
-            ),
241
-        ),
242
-        'internalStats'     => array(
243
-            '_hidden'                    => true,
244
-            StatsMain::class             => array(
245
-                self::MAIN => self::ACCESS_ALLOW,
246
-            ),
247
-            StatsFastCloses::class       => array(
248
-                self::MAIN => self::ACCESS_ALLOW,
249
-            ),
250
-            StatsInactiveUsers::class    => array(
251
-                self::MAIN => self::ACCESS_ALLOW,
252
-            ),
253
-            StatsMonthlyStats::class     => array(
254
-                self::MAIN => self::ACCESS_ALLOW,
255
-            ),
256
-            StatsReservedRequests::class => array(
257
-                self::MAIN => self::ACCESS_ALLOW,
258
-            ),
259
-            StatsTemplateStats::class    => array(
260
-                self::MAIN => self::ACCESS_ALLOW,
261
-            ),
262
-        ),
263
-        'requestAdminTools' => array(
264
-            '_hidden'                   => true,
265
-            PageBan::class              => array(
266
-                self::MAIN => self::ACCESS_ALLOW,
267
-                'set'      => self::ACCESS_ALLOW,
268
-                'remove'   => self::ACCESS_ALLOW,
269
-            ),
270
-            PageEditComment::class      => array(
271
-                'editOthers' => self::ACCESS_ALLOW,
272
-            ),
273
-            PageBreakReservation::class => array(
274
-                'force' => self::ACCESS_ALLOW,
275
-            ),
276
-            PageCustomClose::class      => array(
277
-                'skipCcMailingList' => self::ACCESS_ALLOW,
278
-            ),
279
-            'RequestData'               => array(
280
-                'reopenOldRequest'      => self::ACCESS_ALLOW,
281
-                'alwaysSeePrivateData'  => self::ACCESS_ALLOW,
282
-                'alwaysSeeHash'         => self::ACCESS_ALLOW,
283
-                'seeRestrictedComments' => self::ACCESS_ALLOW,
284
-            ),
285
-        ),
286
-    );
287
-    /** @var array
288
-     * List of roles which are *exempt* from the identification requirements
289
-     *
290
-     * Think twice about adding roles to this list.
291
-     *
292
-     * @category Security-Critical
293
-     */
294
-    private $identificationExempt = array('public', 'loggedIn');
231
+		// Child roles go below this point
232
+		'publicStats'       => array(
233
+			'_hidden'               => true,
234
+			StatsUsers::class       => array(
235
+				self::MAIN => self::ACCESS_ALLOW,
236
+				'detail'   => self::ACCESS_ALLOW,
237
+			),
238
+			StatsTopCreators::class => array(
239
+				self::MAIN => self::ACCESS_ALLOW,
240
+			),
241
+		),
242
+		'internalStats'     => array(
243
+			'_hidden'                    => true,
244
+			StatsMain::class             => array(
245
+				self::MAIN => self::ACCESS_ALLOW,
246
+			),
247
+			StatsFastCloses::class       => array(
248
+				self::MAIN => self::ACCESS_ALLOW,
249
+			),
250
+			StatsInactiveUsers::class    => array(
251
+				self::MAIN => self::ACCESS_ALLOW,
252
+			),
253
+			StatsMonthlyStats::class     => array(
254
+				self::MAIN => self::ACCESS_ALLOW,
255
+			),
256
+			StatsReservedRequests::class => array(
257
+				self::MAIN => self::ACCESS_ALLOW,
258
+			),
259
+			StatsTemplateStats::class    => array(
260
+				self::MAIN => self::ACCESS_ALLOW,
261
+			),
262
+		),
263
+		'requestAdminTools' => array(
264
+			'_hidden'                   => true,
265
+			PageBan::class              => array(
266
+				self::MAIN => self::ACCESS_ALLOW,
267
+				'set'      => self::ACCESS_ALLOW,
268
+				'remove'   => self::ACCESS_ALLOW,
269
+			),
270
+			PageEditComment::class      => array(
271
+				'editOthers' => self::ACCESS_ALLOW,
272
+			),
273
+			PageBreakReservation::class => array(
274
+				'force' => self::ACCESS_ALLOW,
275
+			),
276
+			PageCustomClose::class      => array(
277
+				'skipCcMailingList' => self::ACCESS_ALLOW,
278
+			),
279
+			'RequestData'               => array(
280
+				'reopenOldRequest'      => self::ACCESS_ALLOW,
281
+				'alwaysSeePrivateData'  => self::ACCESS_ALLOW,
282
+				'alwaysSeeHash'         => self::ACCESS_ALLOW,
283
+				'seeRestrictedComments' => self::ACCESS_ALLOW,
284
+			),
285
+		),
286
+	);
287
+	/** @var array
288
+	 * List of roles which are *exempt* from the identification requirements
289
+	 *
290
+	 * Think twice about adding roles to this list.
291
+	 *
292
+	 * @category Security-Critical
293
+	 */
294
+	private $identificationExempt = array('public', 'loggedIn');
295 295
 
296
-    /**
297
-     * RoleConfiguration constructor.
298
-     *
299
-     * @param array $roleConfig           Set to non-null to override the default configuration.
300
-     * @param array $identificationExempt Set to non-null to override the default configuration.
301
-     */
302
-    public function __construct(array $roleConfig = null, array $identificationExempt = null)
303
-    {
304
-        if ($roleConfig !== null) {
305
-            $this->roleConfig = $roleConfig;
306
-        }
296
+	/**
297
+	 * RoleConfiguration constructor.
298
+	 *
299
+	 * @param array $roleConfig           Set to non-null to override the default configuration.
300
+	 * @param array $identificationExempt Set to non-null to override the default configuration.
301
+	 */
302
+	public function __construct(array $roleConfig = null, array $identificationExempt = null)
303
+	{
304
+		if ($roleConfig !== null) {
305
+			$this->roleConfig = $roleConfig;
306
+		}
307 307
 
308
-        if ($identificationExempt !== null) {
309
-            $this->identificationExempt = $identificationExempt;
310
-        }
311
-    }
308
+		if ($identificationExempt !== null) {
309
+			$this->identificationExempt = $identificationExempt;
310
+		}
311
+	}
312 312
 
313
-    /**
314
-     * @param array $roles The roles to check
315
-     *
316
-     * @return array
317
-     */
318
-    public function getApplicableRoles(array $roles)
319
-    {
320
-        $available = array();
313
+	/**
314
+	 * @param array $roles The roles to check
315
+	 *
316
+	 * @return array
317
+	 */
318
+	public function getApplicableRoles(array $roles)
319
+	{
320
+		$available = array();
321 321
 
322
-        foreach ($roles as $role) {
323
-            if (!isset($this->roleConfig[$role])) {
324
-                // wat
325
-                continue;
326
-            }
322
+		foreach ($roles as $role) {
323
+			if (!isset($this->roleConfig[$role])) {
324
+				// wat
325
+				continue;
326
+			}
327 327
 
328
-            $available[$role] = $this->roleConfig[$role];
328
+			$available[$role] = $this->roleConfig[$role];
329 329
 
330
-            if (isset($available[$role]['_childRoles'])) {
331
-                $childRoles = self::getApplicableRoles($available[$role]['_childRoles']);
332
-                $available = array_merge($available, $childRoles);
330
+			if (isset($available[$role]['_childRoles'])) {
331
+				$childRoles = self::getApplicableRoles($available[$role]['_childRoles']);
332
+				$available = array_merge($available, $childRoles);
333 333
 
334
-                unset($available[$role]['_childRoles']);
335
-            }
334
+				unset($available[$role]['_childRoles']);
335
+			}
336 336
 
337
-            foreach (array('_hidden', '_editableBy', '_description') as $item) {
338
-                if (isset($available[$role][$item])) {
339
-                    unset($available[$role][$item]);
340
-                }
341
-            }
342
-        }
337
+			foreach (array('_hidden', '_editableBy', '_description') as $item) {
338
+				if (isset($available[$role][$item])) {
339
+					unset($available[$role][$item]);
340
+				}
341
+			}
342
+		}
343 343
 
344
-        return $available;
345
-    }
344
+		return $available;
345
+	}
346 346
 
347
-    public function getAvailableRoles()
348
-    {
349
-        $possible = array_diff(array_keys($this->roleConfig), array('public', 'loggedIn'));
347
+	public function getAvailableRoles()
348
+	{
349
+		$possible = array_diff(array_keys($this->roleConfig), array('public', 'loggedIn'));
350 350
 
351
-        $actual = array();
351
+		$actual = array();
352 352
 
353
-        foreach ($possible as $role) {
354
-            if (!isset($this->roleConfig[$role]['_hidden'])) {
355
-                $actual[$role] = array(
356
-                    'description' => $this->roleConfig[$role]['_description'],
357
-                    'editableBy'  => $this->roleConfig[$role]['_editableBy'],
358
-                );
359
-            }
360
-        }
353
+		foreach ($possible as $role) {
354
+			if (!isset($this->roleConfig[$role]['_hidden'])) {
355
+				$actual[$role] = array(
356
+					'description' => $this->roleConfig[$role]['_description'],
357
+					'editableBy'  => $this->roleConfig[$role]['_editableBy'],
358
+				);
359
+			}
360
+		}
361 361
 
362
-        return $actual;
363
-    }
362
+		return $actual;
363
+	}
364 364
 
365
-    /**
366
-     * @param string $role
367
-     *
368
-     * @return bool
369
-     */
370
-    public function roleNeedsIdentification($role)
371
-    {
372
-        if (in_array($role, $this->identificationExempt)) {
373
-            return false;
374
-        }
365
+	/**
366
+	 * @param string $role
367
+	 *
368
+	 * @return bool
369
+	 */
370
+	public function roleNeedsIdentification($role)
371
+	{
372
+		if (in_array($role, $this->identificationExempt)) {
373
+			return false;
374
+		}
375 375
 
376
-        return true;
377
-    }
376
+		return true;
377
+	}
378 378
 }
Please login to merge, or discard this patch.
includes/Security/Token.php 1 patch
Indentation   +69 added lines, -69 removed lines patch added patch discarded remove patch
@@ -12,80 +12,80 @@
 block discarded – undo
12 12
 
13 13
 class Token
14 14
 {
15
-    /** @var string */
16
-    private $tokenData;
17
-    /** @var string */
18
-    private $context;
19
-    /** @var DateTimeImmutable */
20
-    private $generationTimestamp;
21
-    /** @var DateTimeImmutable */
22
-    private $usageTimestamp;
23
-    /** @var bool */
24
-    private $used;
15
+	/** @var string */
16
+	private $tokenData;
17
+	/** @var string */
18
+	private $context;
19
+	/** @var DateTimeImmutable */
20
+	private $generationTimestamp;
21
+	/** @var DateTimeImmutable */
22
+	private $usageTimestamp;
23
+	/** @var bool */
24
+	private $used;
25 25
 
26
-    /**
27
-     * Token constructor.
28
-     *
29
-     * @param string $tokenData
30
-     * @param string $context
31
-     */
32
-    public function __construct($tokenData, $context)
33
-    {
34
-        $this->tokenData = $tokenData;
35
-        $this->context = $context;
36
-        $this->generationTimestamp = new DateTimeImmutable();
37
-        $this->usageTimestamp = null;
38
-        $this->used = false;
39
-    }
26
+	/**
27
+	 * Token constructor.
28
+	 *
29
+	 * @param string $tokenData
30
+	 * @param string $context
31
+	 */
32
+	public function __construct($tokenData, $context)
33
+	{
34
+		$this->tokenData = $tokenData;
35
+		$this->context = $context;
36
+		$this->generationTimestamp = new DateTimeImmutable();
37
+		$this->usageTimestamp = null;
38
+		$this->used = false;
39
+	}
40 40
 
41
-    /**
42
-     * @return DateTimeImmutable
43
-     */
44
-    public function getGenerationTimestamp()
45
-    {
46
-        return $this->generationTimestamp;
47
-    }
41
+	/**
42
+	 * @return DateTimeImmutable
43
+	 */
44
+	public function getGenerationTimestamp()
45
+	{
46
+		return $this->generationTimestamp;
47
+	}
48 48
 
49
-    /**
50
-     * @return string
51
-     */
52
-    public function getContext()
53
-    {
54
-        return $this->context;
55
-    }
49
+	/**
50
+	 * @return string
51
+	 */
52
+	public function getContext()
53
+	{
54
+		return $this->context;
55
+	}
56 56
 
57
-    /**
58
-     * @return string
59
-     */
60
-    public function getTokenData()
61
-    {
62
-        return $this->tokenData;
63
-    }
57
+	/**
58
+	 * @return string
59
+	 */
60
+	public function getTokenData()
61
+	{
62
+		return $this->tokenData;
63
+	}
64 64
 
65
-    /**
66
-     * Returns a value indicating whether the token has already been used or not
67
-     *
68
-     * @return boolean
69
-     */
70
-    public function isUsed()
71
-    {
72
-        return $this->used;
73
-    }
65
+	/**
66
+	 * Returns a value indicating whether the token has already been used or not
67
+	 *
68
+	 * @return boolean
69
+	 */
70
+	public function isUsed()
71
+	{
72
+		return $this->used;
73
+	}
74 74
 
75
-    /**
76
-     * Marks the token as used
77
-     */
78
-    public function markAsUsed()
79
-    {
80
-        $this->used = true;
81
-        $this->usageTimestamp = new DateTimeImmutable();
82
-    }
75
+	/**
76
+	 * Marks the token as used
77
+	 */
78
+	public function markAsUsed()
79
+	{
80
+		$this->used = true;
81
+		$this->usageTimestamp = new DateTimeImmutable();
82
+	}
83 83
 
84
-    /**
85
-     * @return DateTimeImmutable
86
-     */
87
-    public function getUsageTimestamp()
88
-    {
89
-        return $this->usageTimestamp;
90
-    }
84
+	/**
85
+	 * @return DateTimeImmutable
86
+	 */
87
+	public function getUsageTimestamp()
88
+	{
89
+		return $this->usageTimestamp;
90
+	}
91 91
 }
92 92
\ No newline at end of file
Please login to merge, or discard this patch.
includes/Security/TokenManager.php 1 patch
Indentation   +87 added lines, -87 removed lines patch added patch discarded remove patch
@@ -13,91 +13,91 @@
 block discarded – undo
13 13
 
14 14
 class TokenManager
15 15
 {
16
-    /**
17
-     * Validates a CSRF token
18
-     *
19
-     * @param string      $data    The token data string itself
20
-     * @param string|null $context Token context for extra validation
21
-     *
22
-     * @return bool
23
-     */
24
-    public function validateToken($data, $context = null)
25
-    {
26
-        if (!is_string($data) || strlen($data) === 0) {
27
-            // Nothing to validate
28
-            return false;
29
-        }
30
-
31
-        $tokens = WebRequest::getSessionTokenData();
32
-
33
-        // if the token doesn't exist, then it's not valid
34
-        if (!array_key_exists($data, $tokens)) {
35
-            return false;
36
-        }
37
-
38
-        /** @var Token $token */
39
-        $token = unserialize($tokens[$data]);
40
-
41
-        if ($token->getTokenData() !== $data) {
42
-            return false;
43
-        }
44
-
45
-        if ($token->getContext() !== $context) {
46
-            return false;
47
-        }
48
-
49
-        if ($token->isUsed()) {
50
-            return false;
51
-        }
52
-
53
-        // mark the token as used, and save it back to the session
54
-        $token->markAsUsed();
55
-        $this->storeToken($token);
56
-
57
-        return true;
58
-    }
59
-
60
-    /**
61
-     * @param string|null $context An optional context for extra validation
62
-     *
63
-     * @return Token
64
-     */
65
-    public function getNewToken($context = null)
66
-    {
67
-        $token = new Token($this->generateTokenData(), $context);
68
-        $this->storeToken($token);
69
-
70
-        return $token;
71
-    }
72
-
73
-    /**
74
-     * Stores a token in the session data
75
-     *
76
-     * @param Token $token
77
-     */
78
-    private function storeToken(Token $token)
79
-    {
80
-        $tokens = WebRequest::getSessionTokenData();
81
-        $tokens[$token->getTokenData()] = serialize($token);
82
-        WebRequest::setSessionTokenData($tokens);
83
-    }
84
-
85
-    /**
86
-     * Generates a security token
87
-     *
88
-     * @return string
89
-     * @throws Exception
90
-     *
91
-     * @category Security-Critical
92
-     */
93
-    private function generateTokenData()
94
-    {
95
-        $genBytes = openssl_random_pseudo_bytes(33);
96
-
97
-        if ($genBytes !== false) {
98
-            return base64_encode($genBytes);
99
-        }
100
-
101
-        throw new Exception('Unable to generate secure token.');
102
-    }
16
+	/**
17
+	 * Validates a CSRF token
18
+	 *
19
+	 * @param string      $data    The token data string itself
20
+	 * @param string|null $context Token context for extra validation
21
+	 *
22
+	 * @return bool
23
+	 */
24
+	public function validateToken($data, $context = null)
25
+	{
26
+		if (!is_string($data) || strlen($data) === 0) {
27
+			// Nothing to validate
28
+			return false;
29
+		}
30
+
31
+		$tokens = WebRequest::getSessionTokenData();
32
+
33
+		// if the token doesn't exist, then it's not valid
34
+		if (!array_key_exists($data, $tokens)) {
35
+			return false;
36
+		}
37
+
38
+		/** @var Token $token */
39
+		$token = unserialize($tokens[$data]);
40
+
41
+		if ($token->getTokenData() !== $data) {
42
+			return false;
43
+		}
44
+
45
+		if ($token->getContext() !== $context) {
46
+			return false;
47
+		}
48
+
49
+		if ($token->isUsed()) {
50
+			return false;
51
+		}
52
+
53
+		// mark the token as used, and save it back to the session
54
+		$token->markAsUsed();
55
+		$this->storeToken($token);
56
+
57
+		return true;
58
+	}
59
+
60
+	/**
61
+	 * @param string|null $context An optional context for extra validation
62
+	 *
63
+	 * @return Token
64
+	 */
65
+	public function getNewToken($context = null)
66
+	{
67
+		$token = new Token($this->generateTokenData(), $context);
68
+		$this->storeToken($token);
69
+
70
+		return $token;
71
+	}
72
+
73
+	/**
74
+	 * Stores a token in the session data
75
+	 *
76
+	 * @param Token $token
77
+	 */
78
+	private function storeToken(Token $token)
79
+	{
80
+		$tokens = WebRequest::getSessionTokenData();
81
+		$tokens[$token->getTokenData()] = serialize($token);
82
+		WebRequest::setSessionTokenData($tokens);
83
+	}
84
+
85
+	/**
86
+	 * Generates a security token
87
+	 *
88
+	 * @return string
89
+	 * @throws Exception
90
+	 *
91
+	 * @category Security-Critical
92
+	 */
93
+	private function generateTokenData()
94
+	{
95
+		$genBytes = openssl_random_pseudo_bytes(33);
96
+
97
+		if ($genBytes !== false) {
98
+			return base64_encode($genBytes);
99
+		}
100
+
101
+		throw new Exception('Unable to generate secure token.');
102
+	}
103 103
 }
104 104
\ No newline at end of file
Please login to merge, or discard this patch.
includes/WebStart.php 2 patches
Indentation   +220 added lines, -220 removed lines patch added patch discarded remove patch
@@ -30,224 +30,224 @@
 block discarded – undo
30 30
  */
31 31
 class WebStart extends ApplicationBase
32 32
 {
33
-    /**
34
-     * @var IRequestRouter $requestRouter The request router to use. Note that different entry points have different
35
-     *                                    routers and hence different URL mappings
36
-     */
37
-    private $requestRouter;
38
-    /**
39
-     * @var bool $isPublic Determines whether to use public interface objects or internal interface objects
40
-     */
41
-    private $isPublic = false;
42
-
43
-    /**
44
-     * WebStart constructor.
45
-     *
46
-     * @param SiteConfiguration $configuration The site configuration
47
-     * @param IRequestRouter    $router        The request router to use
48
-     */
49
-    public function __construct(SiteConfiguration $configuration, IRequestRouter $router)
50
-    {
51
-        parent::__construct($configuration);
52
-
53
-        $this->requestRouter = $router;
54
-    }
55
-
56
-    /**
57
-     * @param ITask             $page
58
-     * @param SiteConfiguration $siteConfiguration
59
-     * @param PdoDatabase       $database
60
-     * @param PdoDatabase       $notificationsDatabase
61
-     *
62
-     * @return void
63
-     */
64
-    protected function setupHelpers(
65
-        ITask $page,
66
-        SiteConfiguration $siteConfiguration,
67
-        PdoDatabase $database,
68
-        PdoDatabase $notificationsDatabase = null
69
-    ) {
70
-        parent::setupHelpers($page, $siteConfiguration, $database, $notificationsDatabase);
71
-
72
-        if ($page instanceof PageBase) {
73
-            $page->setTokenManager(new TokenManager());
74
-
75
-            if ($page instanceof InternalPageBase) {
76
-                $page->setTypeAheadHelper(new TypeAheadHelper());
77
-
78
-                $identificationVerifier = new IdentificationVerifier($page->getHttpHelper(), $siteConfiguration,
79
-                    $database);
80
-                $page->setIdentificationVerifier($identificationVerifier);
81
-
82
-                $page->setSecurityManager(new SecurityManager($identificationVerifier, new RoleConfiguration()));
83
-
84
-                if ($siteConfiguration->getTitleBlacklistEnabled()) {
85
-                    $page->setBlacklistHelper(new FakeBlacklistHelper());
86
-                }
87
-                else {
88
-                    $page->setBlacklistHelper(new BlacklistHelper($page->getHttpHelper(),
89
-                        $siteConfiguration->getMediawikiWebServiceEndpoint()));
90
-                }
91
-            }
92
-        }
93
-    }
94
-
95
-    /**
96
-     * Application entry point.
97
-     *
98
-     * Sets up the environment and runs the application, performing any global cleanup operations when done.
99
-     */
100
-    public function run()
101
-    {
102
-        try {
103
-            if ($this->setupEnvironment()) {
104
-                $this->main();
105
-            }
106
-        }
107
-        catch (EnvironmentException $ex) {
108
-            ob_end_clean();
109
-            print Offline::getOfflineMessage($this->isPublic(), $ex->getMessage());
110
-        }
111
-        catch (ReadableException $ex) {
112
-            ob_end_clean();
113
-            print $ex->getReadableError();
114
-        }
115
-        finally {
116
-            $this->cleanupEnvironment();
117
-        }
118
-    }
119
-
120
-    /**
121
-     * Environment setup
122
-     *
123
-     * This method initialises the tool environment. If the tool cannot be initialised correctly, it will return false
124
-     * and shut down prematurely.
125
-     *
126
-     * @return bool
127
-     * @throws EnvironmentException
128
-     */
129
-    protected function setupEnvironment()
130
-    {
131
-        // initialise global exception handler
132
-        set_exception_handler(array(ExceptionHandler::class, 'exceptionHandler'));
133
-        set_error_handler(array(ExceptionHandler::class, 'errorHandler'), E_RECOVERABLE_ERROR);
134
-
135
-        // start output buffering if necessary
136
-        if (ob_get_level() === 0) {
137
-            ob_start();
138
-        }
139
-
140
-        // initialise super-global providers
141
-        WebRequest::setGlobalStateProvider(new GlobalStateProvider());
142
-
143
-        if (Offline::isOffline()) {
144
-            print Offline::getOfflineMessage($this->isPublic());
145
-            ob_end_flush();
146
-
147
-            return false;
148
-        }
149
-
150
-        // Call parent setup
151
-        if (!parent::setupEnvironment()) {
152
-            return false;
153
-        }
154
-
155
-        // Start up sessions
156
-        Session::start();
157
-
158
-        // Check the user is allowed to be logged in still. This must be before we call any user-loading functions and
159
-        // get the current user cached.
160
-        // I'm not sure if this function call being here is particularly a good thing, but it's part of starting up a
161
-        // session I suppose.
162
-        $this->checkForceLogout();
163
-
164
-        // environment initialised!
165
-        return true;
166
-    }
167
-
168
-    /**
169
-     * Main application logic
170
-     */
171
-    protected function main()
172
-    {
173
-        // Get the right route for the request
174
-        $page = $this->requestRouter->route();
175
-
176
-        $siteConfiguration = $this->getConfiguration();
177
-        $database = PdoDatabase::getDatabaseConnection('acc');
178
-
179
-        if ($siteConfiguration->getIrcNotificationsEnabled()) {
180
-            $notificationsDatabase = PdoDatabase::getDatabaseConnection('notifications');
181
-        }
182
-        else {
183
-            // @todo federated table here?
184
-            $notificationsDatabase = $database;
185
-        }
186
-
187
-        $this->setupHelpers($page, $siteConfiguration, $database, $notificationsDatabase);
188
-
189
-        /* @todo Remove this global statement! It's here for User.php, which does far more than it should. */
190
-        global $oauthHelper;
191
-        $oauthHelper = $page->getOAuthHelper();
192
-
193
-        /* @todo Remove this global statement! It's here for Request.php, which does far more than it should. */
194
-        global $globalXffTrustProvider;
195
-        $globalXffTrustProvider = $page->getXffTrustProvider();
196
-
197
-        // run the route code for the request.
198
-        $page->execute();
199
-    }
200
-
201
-    /**
202
-     * Any cleanup tasks should go here
203
-     *
204
-     * Note that we need to be very careful here, as exceptions may have been thrown and handled.
205
-     * This should *only* be for cleaning up, no logic should go here.
206
-     */
207
-    protected function cleanupEnvironment()
208
-    {
209
-        // Clean up anything we splurged after sending the page.
210
-        if (ob_get_level() > 0) {
211
-            for ($i = ob_get_level(); $i > 0; $i--) {
212
-                ob_end_clean();
213
-            }
214
-        }
215
-    }
216
-
217
-    private function checkForceLogout()
218
-    {
219
-        $database = PdoDatabase::getDatabaseConnection('acc');
220
-
221
-        $sessionUserId = WebRequest::getSessionUserId();
222
-        iF ($sessionUserId === null) {
223
-            return;
224
-        }
225
-
226
-        // Note, User::getCurrent() caches it's result, which we *really* don't want to trigger.
227
-        $currentUser = User::getById($sessionUserId, $database);
228
-
229
-        if ($currentUser === false) {
230
-            // Umm... this user has a session cookie with a userId set, but no user exists...
231
-            Session::restart();
232
-
233
-            $currentUser = User::getCurrent($database);
234
-        }
235
-
236
-        if ($currentUser->getForceLogout()) {
237
-            Session::restart();
238
-
239
-            $currentUser->setForceLogout(false);
240
-            $currentUser->save();
241
-        }
242
-    }
243
-
244
-    public function isPublic()
245
-    {
246
-        return $this->isPublic;
247
-    }
248
-
249
-    public function setPublic($isPublic)
250
-    {
251
-        $this->isPublic = $isPublic;
252
-    }
33
+	/**
34
+	 * @var IRequestRouter $requestRouter The request router to use. Note that different entry points have different
35
+	 *                                    routers and hence different URL mappings
36
+	 */
37
+	private $requestRouter;
38
+	/**
39
+	 * @var bool $isPublic Determines whether to use public interface objects or internal interface objects
40
+	 */
41
+	private $isPublic = false;
42
+
43
+	/**
44
+	 * WebStart constructor.
45
+	 *
46
+	 * @param SiteConfiguration $configuration The site configuration
47
+	 * @param IRequestRouter    $router        The request router to use
48
+	 */
49
+	public function __construct(SiteConfiguration $configuration, IRequestRouter $router)
50
+	{
51
+		parent::__construct($configuration);
52
+
53
+		$this->requestRouter = $router;
54
+	}
55
+
56
+	/**
57
+	 * @param ITask             $page
58
+	 * @param SiteConfiguration $siteConfiguration
59
+	 * @param PdoDatabase       $database
60
+	 * @param PdoDatabase       $notificationsDatabase
61
+	 *
62
+	 * @return void
63
+	 */
64
+	protected function setupHelpers(
65
+		ITask $page,
66
+		SiteConfiguration $siteConfiguration,
67
+		PdoDatabase $database,
68
+		PdoDatabase $notificationsDatabase = null
69
+	) {
70
+		parent::setupHelpers($page, $siteConfiguration, $database, $notificationsDatabase);
71
+
72
+		if ($page instanceof PageBase) {
73
+			$page->setTokenManager(new TokenManager());
74
+
75
+			if ($page instanceof InternalPageBase) {
76
+				$page->setTypeAheadHelper(new TypeAheadHelper());
77
+
78
+				$identificationVerifier = new IdentificationVerifier($page->getHttpHelper(), $siteConfiguration,
79
+					$database);
80
+				$page->setIdentificationVerifier($identificationVerifier);
81
+
82
+				$page->setSecurityManager(new SecurityManager($identificationVerifier, new RoleConfiguration()));
83
+
84
+				if ($siteConfiguration->getTitleBlacklistEnabled()) {
85
+					$page->setBlacklistHelper(new FakeBlacklistHelper());
86
+				}
87
+				else {
88
+					$page->setBlacklistHelper(new BlacklistHelper($page->getHttpHelper(),
89
+						$siteConfiguration->getMediawikiWebServiceEndpoint()));
90
+				}
91
+			}
92
+		}
93
+	}
94
+
95
+	/**
96
+	 * Application entry point.
97
+	 *
98
+	 * Sets up the environment and runs the application, performing any global cleanup operations when done.
99
+	 */
100
+	public function run()
101
+	{
102
+		try {
103
+			if ($this->setupEnvironment()) {
104
+				$this->main();
105
+			}
106
+		}
107
+		catch (EnvironmentException $ex) {
108
+			ob_end_clean();
109
+			print Offline::getOfflineMessage($this->isPublic(), $ex->getMessage());
110
+		}
111
+		catch (ReadableException $ex) {
112
+			ob_end_clean();
113
+			print $ex->getReadableError();
114
+		}
115
+		finally {
116
+			$this->cleanupEnvironment();
117
+		}
118
+	}
119
+
120
+	/**
121
+	 * Environment setup
122
+	 *
123
+	 * This method initialises the tool environment. If the tool cannot be initialised correctly, it will return false
124
+	 * and shut down prematurely.
125
+	 *
126
+	 * @return bool
127
+	 * @throws EnvironmentException
128
+	 */
129
+	protected function setupEnvironment()
130
+	{
131
+		// initialise global exception handler
132
+		set_exception_handler(array(ExceptionHandler::class, 'exceptionHandler'));
133
+		set_error_handler(array(ExceptionHandler::class, 'errorHandler'), E_RECOVERABLE_ERROR);
134
+
135
+		// start output buffering if necessary
136
+		if (ob_get_level() === 0) {
137
+			ob_start();
138
+		}
139
+
140
+		// initialise super-global providers
141
+		WebRequest::setGlobalStateProvider(new GlobalStateProvider());
142
+
143
+		if (Offline::isOffline()) {
144
+			print Offline::getOfflineMessage($this->isPublic());
145
+			ob_end_flush();
146
+
147
+			return false;
148
+		}
149
+
150
+		// Call parent setup
151
+		if (!parent::setupEnvironment()) {
152
+			return false;
153
+		}
154
+
155
+		// Start up sessions
156
+		Session::start();
157
+
158
+		// Check the user is allowed to be logged in still. This must be before we call any user-loading functions and
159
+		// get the current user cached.
160
+		// I'm not sure if this function call being here is particularly a good thing, but it's part of starting up a
161
+		// session I suppose.
162
+		$this->checkForceLogout();
163
+
164
+		// environment initialised!
165
+		return true;
166
+	}
167
+
168
+	/**
169
+	 * Main application logic
170
+	 */
171
+	protected function main()
172
+	{
173
+		// Get the right route for the request
174
+		$page = $this->requestRouter->route();
175
+
176
+		$siteConfiguration = $this->getConfiguration();
177
+		$database = PdoDatabase::getDatabaseConnection('acc');
178
+
179
+		if ($siteConfiguration->getIrcNotificationsEnabled()) {
180
+			$notificationsDatabase = PdoDatabase::getDatabaseConnection('notifications');
181
+		}
182
+		else {
183
+			// @todo federated table here?
184
+			$notificationsDatabase = $database;
185
+		}
186
+
187
+		$this->setupHelpers($page, $siteConfiguration, $database, $notificationsDatabase);
188
+
189
+		/* @todo Remove this global statement! It's here for User.php, which does far more than it should. */
190
+		global $oauthHelper;
191
+		$oauthHelper = $page->getOAuthHelper();
192
+
193
+		/* @todo Remove this global statement! It's here for Request.php, which does far more than it should. */
194
+		global $globalXffTrustProvider;
195
+		$globalXffTrustProvider = $page->getXffTrustProvider();
196
+
197
+		// run the route code for the request.
198
+		$page->execute();
199
+	}
200
+
201
+	/**
202
+	 * Any cleanup tasks should go here
203
+	 *
204
+	 * Note that we need to be very careful here, as exceptions may have been thrown and handled.
205
+	 * This should *only* be for cleaning up, no logic should go here.
206
+	 */
207
+	protected function cleanupEnvironment()
208
+	{
209
+		// Clean up anything we splurged after sending the page.
210
+		if (ob_get_level() > 0) {
211
+			for ($i = ob_get_level(); $i > 0; $i--) {
212
+				ob_end_clean();
213
+			}
214
+		}
215
+	}
216
+
217
+	private function checkForceLogout()
218
+	{
219
+		$database = PdoDatabase::getDatabaseConnection('acc');
220
+
221
+		$sessionUserId = WebRequest::getSessionUserId();
222
+		iF ($sessionUserId === null) {
223
+			return;
224
+		}
225
+
226
+		// Note, User::getCurrent() caches it's result, which we *really* don't want to trigger.
227
+		$currentUser = User::getById($sessionUserId, $database);
228
+
229
+		if ($currentUser === false) {
230
+			// Umm... this user has a session cookie with a userId set, but no user exists...
231
+			Session::restart();
232
+
233
+			$currentUser = User::getCurrent($database);
234
+		}
235
+
236
+		if ($currentUser->getForceLogout()) {
237
+			Session::restart();
238
+
239
+			$currentUser->setForceLogout(false);
240
+			$currentUser->save();
241
+		}
242
+	}
243
+
244
+	public function isPublic()
245
+	{
246
+		return $this->isPublic;
247
+	}
248
+
249
+	public function setPublic($isPublic)
250
+	{
251
+		$this->isPublic = $isPublic;
252
+	}
253 253
 }
Please login to merge, or discard this patch.
Braces   +2 added lines, -4 removed lines patch added patch discarded remove patch
@@ -83,8 +83,7 @@  discard block
 block discarded – undo
83 83
 
84 84
                 if ($siteConfiguration->getTitleBlacklistEnabled()) {
85 85
                     $page->setBlacklistHelper(new FakeBlacklistHelper());
86
-                }
87
-                else {
86
+                } else {
88 87
                     $page->setBlacklistHelper(new BlacklistHelper($page->getHttpHelper(),
89 88
                         $siteConfiguration->getMediawikiWebServiceEndpoint()));
90 89
                 }
@@ -178,8 +177,7 @@  discard block
 block discarded – undo
178 177
 
179 178
         if ($siteConfiguration->getIrcNotificationsEnabled()) {
180 179
             $notificationsDatabase = PdoDatabase::getDatabaseConnection('notifications');
181
-        }
182
-        else {
180
+        } else {
183 181
             // @todo federated table here?
184 182
             $notificationsDatabase = $database;
185 183
         }
Please login to merge, or discard this patch.
includes/API/Actions/StatusAction.php 1 patch
Indentation   +39 added lines, -39 removed lines patch added patch discarded remove patch
@@ -17,67 +17,67 @@
 block discarded – undo
17 17
  */
18 18
 class StatusAction extends ApiPageBase implements IApiAction
19 19
 {
20
-    public function executeApiAction(DOMElement $apiDocument)
21
-    {
22
-        $statusElement = $this->document->createElement("status");
23
-        $apiDocument->appendChild($statusElement);
20
+	public function executeApiAction(DOMElement $apiDocument)
21
+	{
22
+		$statusElement = $this->document->createElement("status");
23
+		$apiDocument->appendChild($statusElement);
24 24
 
25
-        $query = $this->getDatabase()->prepare(<<<SQL
25
+		$query = $this->getDatabase()->prepare(<<<SQL
26 26
             SELECT /* Api/StatusAction */ COUNT(*) AS count
27 27
             FROM request
28 28
             WHERE
29 29
                 status = :pstatus
30 30
                 AND emailconfirm = 'Confirmed';
31 31
 SQL
32
-        );
32
+		);
33 33
 
34
-        $availableRequestStates = $this->getSiteConfiguration()->getRequestStates();
34
+		$availableRequestStates = $this->getSiteConfiguration()->getRequestStates();
35 35
 
36
-        foreach ($availableRequestStates as $key => $value) {
37
-            $query->bindValue(":pstatus", $key);
38
-            $query->execute();
39
-            $sus = $query->fetchColumn();
40
-            $statusElement->setAttribute($value['api'], $sus);
41
-            $query->closeCursor();
42
-        }
36
+		foreach ($availableRequestStates as $key => $value) {
37
+			$query->bindValue(":pstatus", $key);
38
+			$query->execute();
39
+			$sus = $query->fetchColumn();
40
+			$statusElement->setAttribute($value['api'], $sus);
41
+			$query->closeCursor();
42
+		}
43 43
 
44
-        $query = $this->getDatabase()->prepare(<<<SQL
44
+		$query = $this->getDatabase()->prepare(<<<SQL
45 45
             SELECT /* Api/StatusAction */ COUNT(*) AS count
46 46
             FROM ban
47 47
             WHERE
48 48
                 (duration > UNIX_TIMESTAMP() OR duration = -1)
49 49
                 AND active = 1;
50 50
 SQL
51
-        );
51
+		);
52 52
 
53
-        $query->execute();
54
-        $sus = $query->fetchColumn();
55
-        $statusElement->setAttribute("bans", $sus);
56
-        $query->closeCursor();
53
+		$query->execute();
54
+		$sus = $query->fetchColumn();
55
+		$statusElement->setAttribute("bans", $sus);
56
+		$query->closeCursor();
57 57
 
58
-        $query = $this->getDatabase()->prepare(<<<SQL
58
+		$query = $this->getDatabase()->prepare(<<<SQL
59 59
 SELECT /* Api/StatusAction */ COUNT(*) AS count
60 60
 FROM user WHERE status = :ulevel;
61 61
 SQL
62
-        );
63
-        $query->bindValue(":ulevel", "Admin");
64
-        $query->execute();
65
-        $sus = $query->fetchColumn();
66
-        $statusElement->setAttribute("useradmin", $sus);
67
-        $query->closeCursor();
62
+		);
63
+		$query->bindValue(":ulevel", "Admin");
64
+		$query->execute();
65
+		$sus = $query->fetchColumn();
66
+		$statusElement->setAttribute("useradmin", $sus);
67
+		$query->closeCursor();
68 68
 
69
-        $query->bindValue(":ulevel", "User");
70
-        $query->execute();
71
-        $sus = $query->fetchColumn();
72
-        $statusElement->setAttribute("user", $sus);
73
-        $query->closeCursor();
69
+		$query->bindValue(":ulevel", "User");
70
+		$query->execute();
71
+		$sus = $query->fetchColumn();
72
+		$statusElement->setAttribute("user", $sus);
73
+		$query->closeCursor();
74 74
 
75
-        $query->bindValue(":ulevel", "New");
76
-        $query->execute();
77
-        $sus = $query->fetchColumn();
78
-        $statusElement->setAttribute("usernew", $sus);
79
-        $query->closeCursor();
75
+		$query->bindValue(":ulevel", "New");
76
+		$query->execute();
77
+		$sus = $query->fetchColumn();
78
+		$statusElement->setAttribute("usernew", $sus);
79
+		$query->closeCursor();
80 80
 
81
-        return $apiDocument;
82
-    }
81
+		return $apiDocument;
82
+	}
83 83
 }
Please login to merge, or discard this patch.