Skip to content

Commit 5ce01b3

Browse files
committed
Add User/Delete page
1 parent 2bac76c commit 5ce01b3

File tree

10 files changed

+227
-12
lines changed

10 files changed

+227
-12
lines changed

src/Controllers/Server/Create.php

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -31,7 +31,7 @@ public function invoke(?array $args): bool
3131
}
3232

3333
$this->model->_responseCode = HttpCode::HTTP_OK;
34-
$this->model->form = Router::query();
34+
$this->model->form_fields = Router::query();
3535
$this->model->server = new \BNETDocs\Libraries\Server\Server(null);
3636
$this->model->server_types = \BNETDocs\Libraries\Server\Type::getAllServerTypes();
3737
if (Router::requestMethod() == Router::METHOD_POST) $this->handlePost();
@@ -40,7 +40,7 @@ public function invoke(?array $args): bool
4040

4141
protected function handlePost(): void
4242
{
43-
$q = &$this->model->form;
43+
$q = &$this->model->form_fields;
4444
$this->model->server->setUser($this->model->active_user);
4545

4646
try { $this->model->server->setAddress($q['address'] ?? ''); }
@@ -55,8 +55,8 @@ protected function handlePost(): void
5555
try { $this->model->server->setTypeId(isset($q['type']) ? (int) $q['type'] : 0); }
5656
catch (OutOfBoundsException) { $this->model->error = FormModel::ERROR_INVALID_TYPE; return; }
5757

58-
$this->model->server->setDisabled((bool) ($this->model->form['disabled'] ?? null));
59-
$this->model->server->setOnline((bool) ($this->model->form['online'] ?? null));
58+
$this->model->server->setDisabled((bool) ($this->model->form_fields['disabled'] ?? null));
59+
$this->model->server->setOnline((bool) ($this->model->form_fields['online'] ?? null));
6060

6161
$this->model->error = $this->model->server->commit() ? FormModel::ERROR_SUCCESS : FormModel::ERROR_INTERNAL;
6262

src/Controllers/Server/Edit.php

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -30,8 +30,8 @@ public function invoke(?array $args): bool
3030
return true;
3131
}
3232

33-
$this->model->form = Router::query();
34-
$id = $this->model->form['id'] ?? null;
33+
$this->model->form_fields = Router::query();
34+
$id = $this->model->form_fields['id'] ?? null;
3535
if (!is_numeric($id))
3636
{
3737
$this->model->_responseCode = HttpCode::HTTP_BAD_REQUEST;
@@ -57,7 +57,7 @@ public function invoke(?array $args): bool
5757

5858
protected function handlePost(): void
5959
{
60-
$q = &$this->model->form;
60+
$q = &$this->model->form_fields;
6161

6262
try { $this->model->server->setAddress($q['address'] ?? ''); }
6363
catch (OutOfBoundsException) { $this->model->error = FormModel::ERROR_INVALID_ADDRESS; return; }
@@ -71,8 +71,8 @@ protected function handlePost(): void
7171
try { $this->model->server->setTypeId(isset($q['type']) ? (int) $q['type'] : 0); }
7272
catch (OutOfBoundsException) { $this->model->error = FormModel::ERROR_INVALID_TYPE; return; }
7373

74-
$this->model->server->setDisabled((bool) ($this->model->form['disabled'] ?? null));
75-
$this->model->server->setOnline((bool) ($this->model->form['online'] ?? null));
74+
$this->model->server->setDisabled((bool) ($this->model->form_fields['disabled'] ?? null));
75+
$this->model->server->setOnline((bool) ($this->model->form_fields['online'] ?? null));
7676

7777
$this->model->error = $this->model->server->commit() ? FormModel::ERROR_SUCCESS : FormModel::ERROR_INTERNAL;
7878

src/Controllers/User/Delete.php

Lines changed: 86 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,86 @@
1+
<?php
2+
3+
namespace BNETDocs\Controllers\User;
4+
5+
use \BNETDocs\Libraries\Core\HttpCode;
6+
use \BNETDocs\Libraries\Core\Router;
7+
use \BNETDocs\Libraries\EventLog\EventTypes;
8+
use \BNETDocs\Libraries\EventLog\Logger;
9+
use \BNETDocs\Models\User\Delete as DeleteModel;
10+
11+
class Delete extends \BNETDocs\Controllers\Base
12+
{
13+
public function __construct()
14+
{
15+
$this->model = new DeleteModel();
16+
}
17+
18+
public function invoke(?array $args): bool
19+
{
20+
$this->model->acl_allowed = $this->model->active_user
21+
&& $this->model->active_user->getOption(\BNETDocs\Libraries\User\User::OPTION_ACL_USER_DELETE);
22+
23+
if (!$this->model->acl_allowed)
24+
{
25+
$this->model->_responseCode = HttpCode::HTTP_FORBIDDEN;
26+
$this->model->error = DeleteModel::ERROR_ACL_NOT_SET;
27+
return true;
28+
}
29+
30+
$this->model->form_fields = Router::query();
31+
$this->model->target_id = $this->model->form_fields['id'] ?? null;
32+
33+
try
34+
{
35+
if (!\is_null($this->model->target_id))
36+
{
37+
$this->model->target_user = new \BNETDocs\Libraries\User\User($this->model->target_id);
38+
}
39+
}
40+
catch (\BNETDocs\Exceptions\UserNotFoundException)
41+
{
42+
$this->model->target_user = null;
43+
}
44+
finally
45+
{
46+
if (!$this->model->target_user)
47+
{
48+
$this->model->_responseCode = HttpCode::HTTP_NOT_FOUND;
49+
$this->model->error = DeleteModel::ERROR_NOT_FOUND;
50+
return true;
51+
}
52+
}
53+
54+
if (Router::requestMethod() == Router::METHOD_POST)
55+
{
56+
$this->model->deleted = $this->model->target_user->deallocate();
57+
58+
if (!$this->model->deleted)
59+
{
60+
$this->model->_responseCode = HttpCode::HTTP_INTERNAL_SERVER_ERROR;
61+
$this->model->error = DeleteModel::ERROR_INTERNAL_ERROR;
62+
return true;
63+
}
64+
else
65+
{
66+
$this->model->error = false;
67+
68+
$event = Logger::initEvent(
69+
EventTypes::USER_DELETED,
70+
$this->model->target_user->getId(),
71+
getenv('REMOTE_ADDR'),
72+
$this->model
73+
);
74+
75+
if ($event->commit())
76+
{
77+
$embed = Logger::initDiscordEmbed($event, $this->model->target_user->getURI());
78+
Logger::logToDiscord($event, $embed);
79+
}
80+
}
81+
}
82+
83+
$this->model->_responseCode = HttpCode::HTTP_OK;
84+
return true;
85+
}
86+
}

src/Libraries/EventLog/Event.php

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -232,7 +232,14 @@ public function getTypeName(): string
232232

233233
public function getUser(): ?User
234234
{
235-
return \is_null($this->user_id) ? null : new User($this->user_id);
235+
try
236+
{
237+
return \is_null($this->user_id) ? null : new User($this->user_id);
238+
}
239+
catch (\BNETDocs\Exceptions\UserNotFoundException)
240+
{
241+
return null;
242+
}
236243
}
237244

238245
public function getUserId(): ?int

src/Models/HttpForm.php

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -9,13 +9,13 @@ class HttpForm extends ActiveUser implements \JsonSerializable
99
*
1010
* @var array
1111
*/
12-
public array $form = [];
12+
public array $form_fields = [];
1313

1414
/**
1515
* Implements the JSON serialization function from the JsonSerializable interface.
1616
*/
1717
public function jsonSerialize(): mixed
1818
{
19-
return \array_merge(parent::jsonSerialize(), ['form' => $this->form]);
19+
return \array_merge(parent::jsonSerialize(), ['form_fields' => $this->form_fields]);
2020
}
2121
}

src/Models/User/Delete.php

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,26 @@
1+
<?php
2+
3+
namespace BNETDocs\Models\User;
4+
5+
class Delete extends \BNETDocs\Models\HttpForm implements \JsonSerializable
6+
{
7+
public const ERROR_ACL_NOT_SET = 'ACL_NOT_SET';
8+
public const ERROR_INTERNAL_ERROR = 'INTERNAL_ERROR';
9+
public const ERROR_NOT_FOUND = 'NOT_FOUND';
10+
public const ERROR_NOT_LOGGED_IN = 'NOT_LOGGED_IN';
11+
12+
public bool $acl_allowed = false;
13+
public bool $deleted = false;
14+
public ?int $target_id = null;
15+
public ?\BNETDocs\Libraries\User\User $target_user = null;
16+
17+
public function jsonSerialize(): mixed
18+
{
19+
return \array_merge(parent::jsonSerialize(), [
20+
'acl_allowed' => $this->acl_allowed,
21+
'deleted' => $this->deleted,
22+
'target_id' => $this->target_id,
23+
'target_user' => $this->target_user,
24+
]);
25+
}
26+
}

src/Templates/User/Delete.phtml

Lines changed: 61 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,61 @@
1+
<?php /* vim: set colorcolumn= expandtab shiftwidth=2 softtabstop=2 tabstop=4 smarttab: */
2+
namespace BNETDocs\Templates\User;
3+
use \BNETDocs\Models\User\Delete as DeleteModel;
4+
use \CarlBennett\MVC\Libraries\Pair;
5+
$title = 'Delete User';
6+
$description = 'This page confirms if the user wishes to delete another user.';
7+
$this->opengraph->attach(new Pair('url', '/user/delete'));
8+
$this->opengraph->attach(new Pair('type', 'article'));
9+
switch ($this->getContext()->error)
10+
{
11+
case DeleteModel::ERROR_ACL_NOT_SET: $message = 'You do not have the privilege to delete users.'; break;
12+
case DeleteModel::ERROR_NOT_FOUND: $message = 'Cannot find user by that id.'; break;
13+
case DeleteModel::ERROR_NOT_LOGGED_IN: $message = 'You must be logged in to delete users.'; break;
14+
case DeleteModel::ERROR_INTERNAL_ERROR: $message = 'An internal error occurred while processing your request. Our staff have been notified of the issue. Try again later.'; break;
15+
default: $message = $this->getContext()->error;
16+
}
17+
$target_id = $this->getContext()->target_id;
18+
$target_user = $this->getContext()->target_user;
19+
if ($target_user)
20+
{
21+
$target_user_avatar = $target_user->getAvatarURI(22);
22+
$target_user_id = $target_user->getId();
23+
$target_user_name = $target_user->getName();
24+
$target_user_url = $target_user->getURI();
25+
}
26+
require('./header.inc.phtml'); ?>
27+
<div class="container">
28+
<? if (is_null($this->getContext()->error)) { ?>
29+
30+
<h2 class="text-danger">Delete User</h2>
31+
<p class="text-danger">Are you sure you wish to delete this user?</p>
32+
<form method="POST" action="?id=<?=rawurlencode($target_id)?>">
33+
<table class="table table-striped text-white-50"><tbody>
34+
<tr><td><a href="<?=$target_user_url?>"><img class="avatar" src="<?=$target_user_avatar?>"/> <?=filter_var($target_user_name, FILTER_SANITIZE_FULL_SPECIAL_CHARS)?></a></td></tr>
35+
</tbody></table>
36+
<a class="btn btn-primary" href="javascript:history.go(-1);">Back</a>
37+
<input class="btn btn-danger" type="submit" value="Delete" tabindex="1" autofocus="autofocus"/>
38+
</form>
39+
40+
<? } else if ($this->getContext()->error === false) { ?>
41+
42+
<h2 class="text-success">Delete User</h2>
43+
<div class="alert alert-success">
44+
<p class="mb-0"><strong>The user was successfully deleted!</strong></p>
45+
</div>
46+
<a class="btn btn-primary" href="<?=\CarlBennett\MVC\Libraries\Common::relativeUrlToAbsolute('/user/index')?>">Back</a>
47+
48+
<? } else { ?>
49+
50+
<h2 class="text-danger">Delete User</h2>
51+
<div class="alert alert-danger">
52+
<p class="mb-0"><strong>An error occurred while attempting to delete the user:</strong></p>
53+
<p class="mb-0"><?=$message?></p>
54+
</div>
55+
<? if (isset($target_user_url) && !empty($target_user_url)) { ?>
56+
<a class="btn btn-primary" href="<?=$target_user_url?>">Back</a>
57+
<? } ?>
58+
59+
<? } ?>
60+
</div>
61+
<? require('./footer.inc.phtml'); ?>

src/Views/User/DeleteHtml.php

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
<?php
2+
3+
namespace BNETDocs\Views\User;
4+
5+
class DeleteHtml extends \BNETDocs\Views\Base\Html
6+
{
7+
public static function invoke(\BNETDocs\Interfaces\Model $model): void
8+
{
9+
if (!$model instanceof \BNETDocs\Models\User\Delete)
10+
{
11+
throw new \BNETDocs\Exceptions\InvalidModelException($model);
12+
}
13+
14+
(new \BNETDocs\Libraries\Core\Template($model, 'User/Delete'))->invoke();
15+
$model->_responseHeaders['Content-Type'] = self::mimeType();
16+
}
17+
}

src/Views/User/DeleteJson.php

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
<?php
2+
3+
namespace BNETDocs\Views\User;
4+
5+
class DeleteJson extends \BNETDocs\Views\Base\Json
6+
{
7+
public static function invoke(\BNETDocs\Interfaces\Model $model): void
8+
{
9+
if (!$model instanceof \BNETDocs\Models\User\Delete)
10+
{
11+
throw new \BNETDocs\Exceptions\InvalidModelException($model);
12+
}
13+
14+
echo json_encode($model, self::jsonFlags());
15+
$model->_responseHeaders['Content-Type'] = self::mimeType();
16+
}
17+
}

src/main.php

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -118,6 +118,7 @@ function main(): void
118118
['#^/user/(\d+)/?#', 'User\\View', ['User\\ViewHtml', 'User\\ViewJson']],
119119
['#^/user/changepassword/?$#', 'User\\ChangePassword', ['User\\ChangePasswordHtml']],
120120
['#^/user/createpassword/?$#', 'User\\CreatePassword', ['User\\CreatePasswordHtml']],
121+
['#^/user/delete/?#', 'User\\Delete', ['User\\DeleteHtml', 'User\\DeleteJson']],
121122
['#^/user/index/?$#', 'User\\Index', ['User\\IndexHtml']],
122123
['#^/user/login/?$#', 'User\\Login', ['User\\LoginHtml']],
123124
['#^/user/logout/?$#', 'User\\Logout', ['User\\LogoutHtml']],

0 commit comments

Comments
 (0)