Rebuild logs view

This commit is contained in:
Igor Scheller 2020-05-01 16:29:28 +02:00 committed by msquare
parent 64dc16e4d9
commit e947e788f9
14 changed files with 218 additions and 65 deletions

View File

@ -39,6 +39,10 @@ $route->get('/design', 'DesignController@index');
$route->addGroup(
'/admin',
function (RouteCollector $route) {
// Log
$route->get('/logs', 'Admin\\LogsController@index');
$route->post('/logs', 'Admin\\LogsController@index');
// Schedule
$route->addGroup(
'/schedule',
@ -48,6 +52,8 @@ $route->addGroup(
$route->post('/import', 'Admin\\Schedule\\ImportSchedule@importSchedule');
}
);
// News
$route->addGroup(
'/news',
function (RouteCollector $route) {

View File

@ -68,7 +68,6 @@ $includeFiles = [
__DIR__ . '/../includes/pages/admin_arrive.php',
__DIR__ . '/../includes/pages/admin_free.php',
__DIR__ . '/../includes/pages/admin_groups.php',
__DIR__ . '/../includes/pages/admin_log.php',
__DIR__ . '/../includes/pages/admin_questions.php',
__DIR__ . '/../includes/pages/admin_rooms.php',
__DIR__ . '/../includes/pages/admin_shifts.php',

View File

@ -102,12 +102,14 @@ function admin_free()
form([
div('row', [
div('col-md-12 form-inline', [
div('inline-form-spacing', [
form_text('search', __('Search'), $search),
form_select('angeltype', __('Angeltype'), $angel_types, $angelType),
form_submit('submit', __('Search'))
]),
]),
]),
]),
table([
'name' => __('Nick'),
'shift_state' => __('Next shift'),

View File

@ -1,45 +0,0 @@
<?php
use Engelsystem\Models\LogEntry;
/**
* @return string
*/
function admin_log_title()
{
return __('Log');
}
/**
* @return string
*/
function admin_log()
{
$filter = '';
if (request()->has('keyword')) {
$filter = strip_request_item('keyword');
}
$log_entries = LogEntry::filter($filter);
$entries = [];
foreach ($log_entries as $entry) {
$data = $entry->toArray();
$data['message'] = nl2br(htmlspecialchars($data['message']));
$data['created_at'] = date_format($entry->created_at, 'd.m.Y H:i');
$entries[] = $data;
}
return page_with_title(admin_log_title(), [
msg(),
form([
form_text('keyword', __('Search'), $filter),
form_submit(__('Search'), 'Go')
]),
table([
'created_at' => 'Time',
'level' => 'Type',
'message' => 'Log Entry'
], $entries)
]);
}

View File

@ -108,6 +108,8 @@ function make_navigation()
$admin_menu = [];
$admin_pages = [
// path => name
// path => [name, permission]
'admin_arrive' => 'Arrived angels',
'admin_active' => 'Active angels',
'admin_user' => 'All Angels',
@ -118,7 +120,7 @@ function make_navigation()
'admin_rooms' => 'Rooms',
'admin_groups' => 'Grouprights',
'admin/schedule' => ['schedule.import', 'schedule.import'],
'admin_log' => 'Log',
'admin/logs' => ['log.log', 'admin_log'],
'admin_event_config' => 'Event config',
];

View File

@ -248,6 +248,10 @@ h1, h2, h3, h4, h5, h6, .h1, .h2, .h3, .h4, .h5, .h6 {
overflow-x: inherit;
}
.inline-form-spacing {
margin-bottom: @form-group-margin-bottom;
}
@keyframes pulse {
0% {
transform: rotate(0deg);

View File

@ -986,8 +986,6 @@ msgstr "Alle Schichten anzeigen"
#: includes/pages/admin_active.php:307 includes/pages/admin_arrive.php:178
#: includes/pages/admin_arrive.php:179 includes/pages/admin_free.php:105
#: includes/pages/admin_free.php:107 includes/pages/admin_log.php:36
#: includes/pages/admin_log.php:37
msgid "Search"
msgstr "Suche"
@ -1294,10 +1292,6 @@ msgstr "Zu löschende Schichten"
msgid "It's done!"
msgstr "Erledigt!"
#: includes/pages/admin_log.php:10 includes/sys_menu.php:121
msgid "Log"
msgstr "Log"
#: includes/pages/user_messages.php:121
msgid "Message"
msgstr "Nachricht"
@ -2866,3 +2860,18 @@ msgstr "Treffen"
msgid "news.edit.message"
msgstr "Nachricht"
msgid "form.search"
msgstr "Suchen"
msgid "log.log"
msgstr "Logs"
msgid "log.time"
msgstr "Zeit"
msgid "log.level"
msgstr "Level"
msgid "log.message"
msgstr "Nachricht"

View File

@ -144,3 +144,18 @@ msgstr "Meeting"
msgid "news.edit.message"
msgstr "Message"
msgid "form.search"
msgstr "Search"
msgid "log.log"
msgstr "Logs"
msgid "log.time"
msgstr "Time"
msgid "log.level"
msgstr "Level"
msgid "log.message"
msgstr "Message"

View File

@ -0,0 +1,58 @@
{% extends 'layouts/app.twig' %}
{% import 'macros/base.twig' as m %}
{% import 'macros/form.twig' as f %}
{% set title %}{% block title %}{{ __('log.log') }}{% endblock %}{% endset %}
{% block content %}
<div class="col-md-12">
<h1>{{ block('title') }}</h1>
<div class="row">
<div class="col-md-12">
<div class="inline-form-spacing">
<form method="POST" action="{{ url('/admin/logs') }}" class="form-inline">
{{ csrf() }}
{{ f.input('search', __('form.search'), 'text', {'value': search, 'hide_label': true}) }}
{{ f.submit(__('form.search')) }}
</form>
</div>
<table class="table table-striped">
<tr>
<th>{{ __('log.time') }}</th>
<th>{{ __('log.level') }}</th>
<th>{{ __('log.message') }}</th>
</tr>
{% for entry in entries %}
{%- set type = 'default' %}
{%- if entry.level in ['notice', 'info'] %}
{%- set type = 'info' %}
{%- endif %}
{%- if entry.level in ['error', 'warning'] %}
{%- set type = 'warning' %}
{%- endif %}
{%- if entry.level in ['emergency', 'alert', 'critical'] %}
{%- set type = 'danger' %}
{%- endif %}
{%- set td_type = '' %}
{%- if type in ['warning', 'danger'] %}
{%- set td_type = type %}
{%- endif %}
<tr>
<td class="{{ td_type }}">{{ entry.created_at.format(__('Y-m-d H:i')) }}</td>
<td class="{{ td_type }}">
<span class="label label-{{ type }}">{{ entry.level|capitalize }}</span>
</td>
<td>{{ entry.message|nl2br }}</td>
</tr>
{% endfor %}
</table>
</div>
</div>
</div>
{% endblock %}

View File

@ -1,11 +1,11 @@
{% macro input(name, label, type, opt) %}
<div class="form-group">
{% if label -%}
<label for="{{ name }}">{{ label }}</label>
<label for="{{ name }}"{% if opt.hide_label|default(false) %} class="sr-only"{% endif %}>{{ label }}</label>
{%- endif %}
<input type="{{ type|default('text') }}" class="form-control"
id="{{ name }}" name="{{ name }}"
value="{{ opt.value|default('') }}"
value="{{ opt.value|default('')|escape('html_attr') }}"
{%- if opt.required|default(false) %}
required
{%- endif -%}
@ -59,7 +59,7 @@
{%- endmacro %}
{% macro hidden(name, value) %}
<input type="hidden" id="{{ name }}" name="{{ name }}" value="{{ value }}">
<input type="hidden" id="{{ name }}" name="{{ name }}" value="{{ value|escape('html_attr') }}">
{%- endmacro %}
{% macro button(label, opt) %}

View File

@ -101,6 +101,9 @@
<div class="col-md-2">
{{ f.input('form-input-text', 'Text', 'text', {'value': 'Value'}) }}
</div>
<div class="col-md-2">
{{ f.input('form-input-text-hidden-label', 'Hidden label', 'text', {'value': 'Hidden label', 'hide_label': true}) }}
</div>
<div class="col-md-2">
{{ f.input('form-input-text-disabled', 'Disabled', 'text', {'disabled': true, 'value': 'Value'}) }}
</div>
@ -113,11 +116,11 @@
<div class="col-md-2">
{{ f.input('form-input-number', 'Number', 'number', {'value': 42}) }}
</div>
</div>
<div class="row">
<div class="col-md-2">
{{ f.textarea('form-input-textarea', 'Textarea', {'rows': 2, 'value': lipsum}) }}
</div>
</div>
<div class="row">
<div class="col-md-2">
{{ f.select('form-input-select', {'lorem': 'Ipsum', 'dolor': 'Sit'}, 'Select', 'dolor') }}
</div>

View File

@ -0,0 +1,47 @@
<?php
namespace Engelsystem\Controllers\Admin;
use Engelsystem\Controllers\BaseController;
use Engelsystem\Http\Request;
use Engelsystem\Http\Response;
use Engelsystem\Models\LogEntry;
class LogsController extends BaseController
{
/** @var LogEntry */
protected $log;
/** @var Response */
protected $response;
/** @var array */
protected $permissions = [
'admin_log',
];
/**
* @param LogEntry $log
* @param Response $response
*/
public function __construct(LogEntry $log, Response $response)
{
$this->log = $log;
$this->response = $response;
}
/**
* @param Request $request
* @return Response
*/
public function index(Request $request): Response
{
$search = $request->input('search');
$entries = $this->log->filter($search);
return $this->response->withView(
'admin/log.twig',
['entries' => $entries, 'search' => $search]
);
}
}

View File

@ -188,10 +188,6 @@ class LegacyMiddleware implements MiddlewareInterface
$title = admin_shifts_title();
$content = admin_shifts();
return [$title, $content];
case 'admin_log':
$title = admin_log_title();
$content = admin_log();
return [$title, $content];
}
throw_redirect(page_link_to('login'));

View File

@ -0,0 +1,57 @@
<?php
namespace Engelsystem\Test\Unit\Controllers\Admin;
use Engelsystem\Controllers\Admin\LogsController;
use Engelsystem\Http\Request;
use Engelsystem\Http\Response;
use Engelsystem\Models\LogEntry;
use Engelsystem\Test\Unit\HasDatabase;
use Engelsystem\Test\Unit\TestCase;
use Illuminate\Database\Eloquent\Collection;
use Psr\Log\LogLevel;
class LogsControllerTest extends TestCase
{
use HasDatabase;
/**
* @covers \Engelsystem\Controllers\Admin\LogsController::index
* @covers \Engelsystem\Controllers\Admin\LogsController::__construct
*/
public function testIndex()
{
$log = new LogEntry();
$alert = $log->create(['level' => LogLevel::ALERT, 'message' => 'Alert test']);
$alert = $log->find($alert)->first();
$error = $log->create(['level' => LogLevel::ERROR, 'message' => 'Error test']);
$error = $log->find($error)->first();
$response = $this->createMock(Response::class);
$response->expects($this->exactly(2))
->method('withView')
->withConsecutive(
['admin/log.twig', ['entries' => new Collection([$error, $alert]), 'search' => null]],
['admin/log.twig', ['entries' => new Collection([$error]), 'search' => 'error']]
)
->willReturn($response);
$request = Request::create('/');
$controller = new LogsController($log, $response);
$controller->index($request);
$request->request->set('search', 'error');
$controller->index($request);
}
/**
* Setup the DB
*/
public function setUp(): void
{
parent::setUp();
$this->initDatabase();
}
}