Skip to content

Commit

Permalink
Fixes #29 -- Add CRUD controllers for Groups and Poster Types.
Browse files Browse the repository at this point in the history
  • Loading branch information
BusterNeece committed Jul 23, 2024
1 parent 9dd3385 commit 4c81ee8
Show file tree
Hide file tree
Showing 13 changed files with 504 additions and 83 deletions.
58 changes: 53 additions & 5 deletions backend/config/routes.php
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,59 @@
->setName('dashboard');

$group->group('/admin', function (RouteCollectorProxy $group) {
$group->group('/groups', function (RouteCollectorProxy $group) {
$group->get(
'',
App\Controller\Dashboard\Admin\GroupsController::class . ':listAction'
)->setName('dashboard:admin:groups');

$group->map(
['GET', 'POST'],
'/create',
App\Controller\Dashboard\Admin\GroupsController::class . ':createAction'
)->setName('dashboard:admin:groups:create');

$group->map(
['GET', 'POST'],
'/edit[/{id}]',
App\Controller\Dashboard\Admin\GroupsController::class . ':editAction'
)->setName('dashboard:admin:groups:edit');

$group->get(
'/delete[/{id}]',
App\Controller\Dashboard\Admin\GroupsController::class . ':deleteAction'
)->setName('dashboard:admin:groups:delete');
});

$group->group('/poster_types', function (RouteCollectorProxy $group) {
$group->get(
'',
App\Controller\Dashboard\Admin\PosterTypesController::class . ':listAction'
)->setName('dashboard:admin:poster_types');

$group->map(
['GET', 'POST'],
'/create',
App\Controller\Dashboard\Admin\PosterTypesController::class . ':createAction'
)->setName('dashboard:admin:poster_types:create');

$group->map(
['GET', 'POST'],
'/edit[/{id}]',
App\Controller\Dashboard\Admin\PosterTypesController::class . ':editAction'
)->setName('dashboard:admin:poster_types:edit');

$group->get(
'/delete[/{id}]',
App\Controller\Dashboard\Admin\PosterTypesController::class . ':deleteAction'
)->setName('dashboard:admin:poster_types:delete');
});

$group->get(
'/users',
App\Controller\Dashboard\Admin\UsersAction::class
)->setName('dashboard:admin:users');

$group->group('/worlds', function (RouteCollectorProxy $group) {
$group->get(
'',
Expand All @@ -54,11 +107,6 @@
App\Controller\Dashboard\Admin\WorldsController::class . ':deleteAction'
)->setName('dashboard:admin:worlds:delete');
});

$group->get(
'/users',
App\Controller\Dashboard\Admin\UsersAction::class
)->setName('dashboard:admin:users');
})->add(new App\Middleware\Auth\RequireAdmin());

$group->map(
Expand Down
2 changes: 0 additions & 2 deletions backend/src/Controller/Dashboard/AbstractCrudController.php
Original file line number Diff line number Diff line change
Expand Up @@ -51,8 +51,6 @@ public function createAction(
try {
$row = $this->modifyFromRequest($request);

unset($row[$this->idField]);

$this->db->insert($this->tableName, $row);

$request->getFlash()->success(sprintf('%s created.', $this->itemName));
Expand Down
43 changes: 43 additions & 0 deletions backend/src/Controller/Dashboard/Admin/GroupsController.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,43 @@
<?php

namespace App\Controller\Dashboard\Admin;

use App\Controller\Dashboard\AbstractCrudController;
use App\Http\ServerRequest;
use Doctrine\DBAL\Connection;

final class GroupsController extends AbstractCrudController
{
public function __construct(
Connection $db
) {
parent::__construct(
$db,
'Group',
'dashboard:admin:groups',
'dashboard/admin/groups/list',
'dashboard/admin/groups/edit',
'web_groups'
);
}

protected function modifyFromRequest(ServerRequest $request, array $row = [], bool $isEditMode = false): array
{
$postData = $request->getParsedBody();

if (!$isEditMode) {
$row['id'] = $postData['id'] ?? null;
if (empty($row['id'])) {
throw new \InvalidArgumentException('ID is required.');
}
}

$row['name'] = $postData['name'] ?? null;

if (empty($row['name'])) {
throw new \InvalidArgumentException('Name is required.');
}

return $row;
}
}
43 changes: 43 additions & 0 deletions backend/src/Controller/Dashboard/Admin/PosterTypesController.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,43 @@
<?php

namespace App\Controller\Dashboard\Admin;

use App\Controller\Dashboard\AbstractCrudController;
use App\Http\ServerRequest;
use Doctrine\DBAL\Connection;

final class PosterTypesController extends AbstractCrudController
{
public function __construct(
Connection $db
) {
parent::__construct(
$db,
'Poster Type',
'dashboard:admin:poster_types',
'dashboard/admin/poster_types/list',
'dashboard/admin/poster_types/edit',
'web_poster_types'
);
}

protected function modifyFromRequest(ServerRequest $request, array $row = [], bool $isEditMode = false): array
{
$postData = $request->getParsedBody();

if (!$isEditMode) {
$row['id'] = $postData['id'] ?? null;
if (empty($row['id'])) {
throw new \InvalidArgumentException('ID is required.');
}
}

$row['name'] = $postData['name'] ?? null;

if (empty($row['name'])) {
throw new \InvalidArgumentException('Name is required.');
}

return $row;
}
}
63 changes: 63 additions & 0 deletions backend/templates/dashboard/admin/groups/edit.twig
Original file line number Diff line number Diff line change
@@ -0,0 +1,63 @@
{% extends "layouts/dashboard.twig" %}

{% import "macros/breadcrumbs.twig" as breadcrumbs %}

{% block content %}
{{ breadcrumbs.body(
{
'dashboard': 'My Dashboard',
'dashboard:admin:groups': 'Manage Groups'
},
(isEditMode) ? 'Edit Group' : 'Create Group'
) }}

<h1>Manage Groups</h1>

<div class="card">
<h2 class="card-header">
{% if isEditMode %}
Edit Group
{% else %}
Create Group
{% endif %}
</h2>
<div class="card-body">
{% if error %}
<div class="alert alert-danger">
<b>Error:</b> {{ error }}
</div>
{% endif %}

<form action="" method="POST">
<div class="row mb-3">
<div class="col-md-8">
{% if not isEditMode %}
<div class="control-group mb-3">
<label for="id" class="form-label">Group ID:</label>
<input type="text" name="id" id="id"
value="{{ row.id|default('')|e('html_attr') }}"
class="form-control form-control-lg" required maxlength="50">

<p class="form-text">
The programmatic ID of the group. Should be only letters, numbers and underscores
(i.e. <code>my_group_1</code>).
</p>
</div>
{% endif %}

<div class="control-group">
<label for="name" class="form-label">Group Name:</label>
<input type="text" name="name" id="name"
value="{{ row.name|default('')|e('html_attr') }}"
class="form-control form-control-lg" required maxlength="255">
</div>
</div>
</div>

<div class="buttons">
<button type="submit" class="btn btn-lg btn-primary">Save Changes</button>
</div>
</form>
</div>
</div>
{% endblock %}
68 changes: 68 additions & 0 deletions backend/templates/dashboard/admin/groups/list.twig
Original file line number Diff line number Diff line change
@@ -0,0 +1,68 @@
{% extends "layouts/dashboard.twig" %}

{% import "macros/breadcrumbs.twig" as breadcrumbs %}

{% block head %}
{{ parent() }}

{{ renderAssets('frontend/dataTable.js') }}

<script>
ready(() => {
let dataTable = new DataTable('#data_table');
});
</script>
{% endblock %}

{% block content %}
{{ breadcrumbs.body(
{
'dashboard': 'My Dashboard'
},
'Manage Groups'
) }}

<h1>Manage Groups</h1>

<div class="card">
<h2 class="card-header">View Groups</h2>
<div class="card-body">
<div class="buttons mb-3">
<a class="btn btn-lg btn-success"
href="{{ urlFor('dashboard:admin:groups:create') }}">
<i class="bi-plus-circle-fill" aria-hidden="true"></i> Add Group
</a>
</div>

<table class="table table-striped table-bordered table-hover align-middle" id="data_table">
<thead>
<tr>
<th>Group ID</th>
<th>Group Name</th>
<th data-dt-order="disable" style="width:15%">Actions</th>
</tr>
</thead>
<tbody>
{% for row in records %}
<tr>
<td><code>{{ row.id }}</code></td>
<th scope="col">{{ row.name }}</th>
<td class="text-nowrap">
<a class="btn btn-sm btn-warning"
href="{{ urlFor('dashboard:admin:groups:edit', {id: row.id}) }}">
<i class="bi-pencil-fill" aria-hidden="true"></i> Edit
</a>
<a class="btn btn-sm btn-danger"
href="{{ urlFor('dashboard:admin:groups:delete', {id: row.id}) }}"
data-confirm-delete="Remove group? This will affect posters uploaded to this group as well."
>
<i class="bi-trash" aria-hidden="true"></i> Delete
</a>
</td>
</tr>
{% endfor %}
</tbody>
</table>
</div>
</div>
{% endblock %}
63 changes: 63 additions & 0 deletions backend/templates/dashboard/admin/poster_types/edit.twig
Original file line number Diff line number Diff line change
@@ -0,0 +1,63 @@
{% extends "layouts/dashboard.twig" %}

{% import "macros/breadcrumbs.twig" as breadcrumbs %}

{% block content %}
{{ breadcrumbs.body(
{
'dashboard': 'My Dashboard',
'dashboard:admin:poster_types': 'Manage Poster Types'
},
(isEditMode) ? 'Edit Poster Type' : 'Create Poster Type'
) }}

<h1>Manage Poster Types</h1>

<div class="card">
<h2 class="card-header">
{% if isEditMode %}
Edit Poster Type
{% else %}
Create Poster Type
{% endif %}
</h2>
<div class="card-body">
{% if error %}
<div class="alert alert-danger">
<b>Error:</b> {{ error }}
</div>
{% endif %}

<form action="" method="POST">
<div class="row mb-3">
<div class="col-md-8">
{% if not isEditMode %}
<div class="control-group mb-3">
<label for="id" class="form-label">Poster Type ID:</label>
<input type="text" name="id" id="id"
value="{{ row.id|default('')|e('html_attr') }}"
class="form-control form-control-lg" required maxlength="50">

<p class="form-text">
The programmatic ID of the poster type. Should be only letters, numbers and
underscores (i.e. <code>my_poster_type_1</code>).
</p>
</div>
{% endif %}

<div class="control-group">
<label for="name" class="form-label">Type Name:</label>
<input type="text" name="name" id="name"
value="{{ row.name|default('')|e('html_attr') }}"
class="form-control form-control-lg" required maxlength="255">
</div>
</div>
</div>

<div class="buttons">
<button type="submit" class="btn btn-lg btn-primary">Save Changes</button>
</div>
</form>
</div>
</div>
{% endblock %}
Loading

0 comments on commit 4c81ee8

Please sign in to comment.