impl. logs

This commit is contained in:
Dennis Eichhorn 2021-02-08 20:17:08 +01:00
parent 87f3afd630
commit d404e26b90
15 changed files with 212 additions and 65 deletions

View File

@ -19,7 +19,7 @@
"type": 3, "type": 3,
"subtype": 1, "subtype": 1,
"name": "Dashboard", "name": "Dashboard",
"uri": "{/prefix}admin/exchange/dashboard?{?}", "uri": "{/prefix}admin/exchange/log/list?{?}",
"target": "self", "target": "self",
"icon": null, "icon": null,
"order": 1, "order": 1,

View File

@ -66,11 +66,23 @@
"type": "TINYINT", "type": "TINYINT",
"null": false "null": false
}, },
"exchange_log_time": { "exchange_log_subtype": {
"name": "exchange_log_time", "name": "exchange_log_subtype",
"type": "VARCHAR(100)",
"null": false
},
"exchange_log_created_at": {
"name": "exchange_log_created_at",
"type": "DATETIME", "type": "DATETIME",
"null": false "null": false
}, },
"exchange_log_created_by": {
"name": "exchange_log_created_by",
"type": "INT",
"null": false,
"foreignTable": "account",
"foreignKey": "account_id"
},
"exchange_log_exchange": { "exchange_log_exchange": {
"name": "exchange_log_exchange", "name": "exchange_log_exchange",
"type": "INT", "type": "INT",

View File

@ -50,9 +50,20 @@ return [
], ],
], ],
], ],
'^.*/admin/exchange/dashboard.*$' => [ '^.*/admin/exchange/log/list.*$' => [
[ [
'dest' => '\Modules\Exchange\Controller\BackendController:viewExchangeDashboard', 'dest' => '\Modules\Exchange\Controller\BackendController:viewExchangeLogList',
'verb' => RouteVerb::GET,
'permission' => [
'module' => BackendController::MODULE_NAME,
'type' => PermissionType::READ,
'state' => PermissionState::DASHBOARD,
],
],
],
'^.*/admin/exchange/log\?.*$' => [
[
'dest' => '\Modules\Exchange\Controller\BackendController:viewExchangeLog',
'verb' => RouteVerb::GET, 'verb' => RouteVerb::GET,
'permission' => [ 'permission' => [
'module' => BackendController::MODULE_NAME, 'module' => BackendController::MODULE_NAME,

View File

@ -14,6 +14,7 @@ declare(strict_types=1);
namespace Modules\Exchange\Controller; namespace Modules\Exchange\Controller;
use Modules\Exchange\Models\ExchangeLogMapper;
use Modules\Exchange\Models\InterfaceManager; use Modules\Exchange\Models\InterfaceManager;
use Modules\Exchange\Models\InterfaceManagerMapper; use Modules\Exchange\Models\InterfaceManagerMapper;
use Modules\Media\Models\UploadFile; use Modules\Media\Models\UploadFile;
@ -54,7 +55,11 @@ final class ApiController extends Controller
$status = NotificationLevel::ERROR; $status = NotificationLevel::ERROR;
$message = 'Import failed.'; $message = 'Import failed.';
if ($import) { foreach ($import['logs'] as $log) {
$this->createModel($request->header->account, $log, ExchangeLogMapper::class, 'import', $request->getOrigin());
}
if ($import['status']) {
$status = NotificationLevel::OK; $status = NotificationLevel::OK;
$message = 'Import succeeded.'; $message = 'Import succeeded.';
} }
@ -71,26 +76,18 @@ final class ApiController extends Controller
* *
* @param RequestAbstract $request Request * @param RequestAbstract $request Request
* *
* @return bool * @return array
* *
* @since 1.0.0 * @since 1.0.0
*/ */
private function importDataFromRequest(RequestAbstract $request) : bool private function importDataFromRequest(RequestAbstract $request) : array
{ {
/** @var \Modules\Exchange\Models\InterfaceManager[] $interfaces */ /** @var \Modules\Exchange\Models\InterfaceManager $interface */
$interfaces = InterfaceManagerMapper::getAll(); $interface = InterfaceManagerMapper::get($request->getData('id'));
foreach ($interfaces as $interface) { $class = '\\Modules\\Exchange\\Interfaces\\' . $interface->getInterfacePath() . '\\Importer';
if ($request->getData('exchange') ?? '' === $interface->getInterfacePath()) { $importer = new $class($this->app->dbPool->get());
$class = '\\Modules\\Exchange\\Interfaces\\' . $interface->getInterfacePath() . '\\Importer';
$importer = new $class($this->app->dbPool->get());
return $importer->importFromRequest($request); return $importer->importFromRequest($request);
}
}
Directory::delete(__DIR__ . '/../tmp/');
return false;
} }
/** /**
@ -162,6 +159,10 @@ final class ApiController extends Controller
public function apiExchangeExport(RequestAbstract $request, ResponseAbstract $response, $data = null) : void public function apiExchangeExport(RequestAbstract $request, ResponseAbstract $response, $data = null) : void
{ {
$export = $this->exportDataFromRequest($request); $export = $this->exportDataFromRequest($request);
foreach ($export['logs'] as $log) {
$this->createModel($request->header->account, $log, ExchangeLogMapper::class, 'export', $request->getOrigin());
}
if ($export['type'] === 'file') { if ($export['type'] === 'file') {
$file = \explode('.', $export['name']); $file = \explode('.', $export['name']);
@ -206,20 +207,12 @@ final class ApiController extends Controller
*/ */
private function exportDataFromRequest(RequestAbstract $request) : array private function exportDataFromRequest(RequestAbstract $request) : array
{ {
/** @var \Modules\Exchange\Models\InterfaceManager[] $interfaces */ /** @var \Modules\Exchange\Models\InterfaceManager $interface */
$interfaces = InterfaceManagerMapper::getAll(); $interface = InterfaceManagerMapper::get($request->getData('id'));
foreach ($interfaces as $interface) { $class = '\\Modules\\Exchange\\Interfaces\\' . $interface->getInterfacePath() . '\\Exporter';
if ($request->getData('exchange') ?? '' === $interface->getInterfacePath()) { $exporter = new $class($this->app->dbPool->get());
$class = '\\Modules\\Exchange\\Interfaces\\' . $interface->getInterfacePath() . '\\Exporter';
$exporter = new $class($this->app->dbPool->get());
return $exporter->exportFromRequest($request); return $exporter->exportFromRequest($request);
}
}
Directory::delete(__DIR__ . '/../tmp/');
return [];
} }
/** /**

View File

@ -19,6 +19,7 @@ use phpOMS\Contract\RenderableInterface;
use phpOMS\Message\RequestAbstract; use phpOMS\Message\RequestAbstract;
use phpOMS\Message\ResponseAbstract; use phpOMS\Message\ResponseAbstract;
use phpOMS\Views\View; use phpOMS\Views\View;
use Modules\Exchange\Models\ExchangeLogMapper;
/** /**
* Exchange controller class. * Exchange controller class.
@ -42,12 +43,50 @@ final class BackendController extends Controller
* @since 1.0.0 * @since 1.0.0
* @codeCoverageIgnore * @codeCoverageIgnore
*/ */
public function viewExchangeDashboard(RequestAbstract $request, ResponseAbstract $response, $data = null) : RenderableInterface public function viewExchangeLogList(RequestAbstract $request, ResponseAbstract $response, $data = null) : RenderableInterface
{ {
$view = new View($this->app->l11nManager, $request, $response); $view = new View($this->app->l11nManager, $request, $response);
$view->setTemplate('/Modules/Exchange/Theme/Backend/exchange-dashboard'); $view->setTemplate('/Modules/Exchange/Theme/Backend/exchange-log-list');
$view->addData('nav', $this->app->moduleManager->get('Navigation')->createNavigationMid(1007001001, $request, $response)); $view->addData('nav', $this->app->moduleManager->get('Navigation')->createNavigationMid(1007001001, $request, $response));
if ($request->getData('ptype') === 'p') {
$view->setData('logs',
ExchangeLogMapper::getBeforePivot((int) ($request->getData('id') ?? 0), limit: 25, depth: 4)
);
} elseif ($request->getData('ptype') === 'n') {
$view->setData('logs',
ExchangeLogMapper::getAfterPivot((int) ($request->getData('id') ?? 0), limit: 25, depth: 4)
);
} else {
$view->setData('logs',
ExchangeLogMapper::getAfterPivot(0, limit: 25, depth: 4)
);
}
return $view;
}
/**
* Routing end-point for application behaviour.
*
* @param RequestAbstract $request Request
* @param ResponseAbstract $response Response
* @param mixed $data Generic data
*
* @return RenderableInterface
*
* @since 1.0.0
* @codeCoverageIgnore
*/
public function viewExchangeLog(RequestAbstract $request, ResponseAbstract $response, $data = null) : RenderableInterface
{
$view = new View($this->app->l11nManager, $request, $response);
$view->setTemplate('/Modules/Exchange/Theme/Backend/exchange-log');
$view->addData('nav', $this->app->moduleManager->get('Navigation')->createNavigationMid(1007001001, $request, $response));
$log = ExchangeLogMapper::get((int) $request->getData('id'));
$view->setData('log', $log);
return $view; return $view;
} }

View File

@ -14,6 +14,8 @@ declare(strict_types=1);
namespace Modules\Exchange\Interfaces\OMS; namespace Modules\Exchange\Interfaces\OMS;
use Modules\Exchange\Models\ExchangeLog;
use Modules\Exchange\Models\ExchangeType;
use phpOMS\DataStorage\Database\Connection\ConnectionAbstract; use phpOMS\DataStorage\Database\Connection\ConnectionAbstract;
use phpOMS\DataStorage\Database\Connection\ConnectionFactory; use phpOMS\DataStorage\Database\Connection\ConnectionFactory;
use phpOMS\DataStorage\Database\DatabaseStatus; use phpOMS\DataStorage\Database\DatabaseStatus;
@ -84,10 +86,19 @@ final class Exporter extends ExporterAbstract
$this->account = $request->header->account; $this->account = $request->header->account;
if ($request->getData('type') === 'language') { if ($request->getData('type') === 'language') {
return $this->exportLanguage(); $result = $this->exportLanguage();
$log = new ExchangeLog();
$log->createdBy = $this->account;
$log->setType(ExchangeType::EXPORT);
$log->message = 'Language file exported.'; // @todo: localize!
$log->subtype = 'language';
$log->exchange = (int) $request->getData('id');
$result['logs'][] = $log;
} }
return []; return $result;
} }
/** /**

View File

@ -14,6 +14,7 @@ declare(strict_types=1);
namespace Modules\Exchange\Interfaces\OMS; namespace Modules\Exchange\Interfaces\OMS;
use Modules\Exchange\Models\ExchangeLog;
use phpOMS\DataStorage\Database\Connection\ConnectionAbstract; use phpOMS\DataStorage\Database\Connection\ConnectionAbstract;
use phpOMS\DataStorage\Database\Connection\ConnectionFactory; use phpOMS\DataStorage\Database\Connection\ConnectionFactory;
use phpOMS\DataStorage\Database\DatabaseStatus; use phpOMS\DataStorage\Database\DatabaseStatus;
@ -25,6 +26,8 @@ use phpOMS\System\File\Local\Directory;
use phpOMS\Utils\IO\Zip\Zip; use phpOMS\Utils\IO\Zip\Zip;
use Modules\Media\Controller\ApiController; use Modules\Media\Controller\ApiController;
use Modules\Exchange\Models\ImporterAbstract; use Modules\Exchange\Models\ImporterAbstract;
use phpOMS\Message\Http\HttpRequest;
use Modules\Exchange\Models\ExchangeType;
/** /**
* OMS import class * OMS import class
@ -64,7 +67,7 @@ final class Importer extends ImporterAbstract
*/ */
public function import(\DateTime $start, \DateTime $end) : void public function import(\DateTime $start, \DateTime $end) : void
{ {
$this->importLanguage(); $this->importLanguage(new HttpRequest());
} }
/** /**
@ -72,11 +75,11 @@ final class Importer extends ImporterAbstract
* *
* @param RequestAbstract $request Request * @param RequestAbstract $request Request
* *
* @return bool * @return array
* *
* @since 1.0.0 * @since 1.0.0
*/ */
public function importFromRequest(RequestAbstract $request) : bool public function importFromRequest(RequestAbstract $request) : array
{ {
$start = new \DateTime($request->getData('start') ?? 'now'); $start = new \DateTime($request->getData('start') ?? 'now');
$end = new \DateTime($request->getData('end') ?? 'now'); $end = new \DateTime($request->getData('end') ?? 'now');
@ -95,17 +98,27 @@ final class Importer extends ImporterAbstract
$this->remote->connect(); $this->remote->connect();
if ($this->remote->getStatus() !== DatabaseStatus::OK) { if ($this->remote->getStatus() !== DatabaseStatus::OK) {
return false; return ['status' => false];
} }
} }
$this->account = $request->header->account; $this->account = $request->header->account;
$result = ['status' => true];
if ($request->getData('type') === 'language') { if ($request->getData('type') === 'language') {
$this->importLanguage($request); $this->importLanguage($request);
$log = new ExchangeLog();
$log->createdBy = $this->account;
$log->setType(ExchangeType::IMPORT);
$log->message = 'Language file imported.'; // @todo: localize!
$log->subtype = 'language';
$log->exchange = (int) $request->getData('id');
$result['logs'][] = $log;
} }
return true; return $result;
} }
/** /**

View File

@ -5,7 +5,7 @@ $lang = $this->getData('lang');
<div class="row"> <div class="row">
<div class="col-xs-12 col-md-6"> <div class="col-xs-12 col-md-6">
<section class="portlet"> <section class="portlet">
<form id="fImport" method="POST" action="<?= \phpOMS\Uri\UriFactory::build('{/api}admin/exchange/export/profile?{?}&exchange=OMS&type=language&csrf={$CSRF}'); ?>"> <form id="fImport" method="POST" action="<?= \phpOMS\Uri\UriFactory::build('{/api}admin/exchange/export/profile?{?}&id={?id}&type=language&csrf={$CSRF}'); ?>">
<div class="portlet-head"><?= $this->printHtml($lang['Language']); ?> - OMS</div> <div class="portlet-head"><?= $this->printHtml($lang['Language']); ?> - OMS</div>
<div class="portlet-body"> <div class="portlet-body">
</div> </div>

View File

@ -5,7 +5,7 @@ $lang = $this->getData('lang');
<div class="row"> <div class="row">
<div class="col-xs-12 col-md-6"> <div class="col-xs-12 col-md-6">
<section class="portlet"> <section class="portlet">
<form id="fImport" method="POST" action="<?= \phpOMS\Uri\UriFactory::build('{/api}admin/exchange/import/profile?{?}&exchange=OMS&type=language&csrf={$CSRF}'); ?>"> <form id="fImport" method="POST" action="<?= \phpOMS\Uri\UriFactory::build('{/api}admin/exchange/import/profile?{?}&id={?id}&type=language&csrf={$CSRF}'); ?>">
<div class="portlet-head"><?= $this->printHtml($lang['Language']); ?> - OMS</div> <div class="portlet-head"><?= $this->printHtml($lang['Language']); ?> - OMS</div>
<div class="portlet-body"> <div class="portlet-body">
<table class="layout wf-100" style="table-layout: fixed"> <table class="layout wf-100" style="table-layout: fixed">

View File

@ -14,6 +14,7 @@ declare(strict_types=1);
namespace Modules\Exchange\Models; namespace Modules\Exchange\Models;
use Modules\Admin\Models\Account;
use phpOMS\Contract\ArrayableInterface; use phpOMS\Contract\ArrayableInterface;
/** /**
@ -60,6 +61,14 @@ class ExchangeLog implements \JsonSerializable, ArrayableInterface
public string $subtype = ''; public string $subtype = '';
/**
* Exchange id.
*
* @var int
* @since 1.0.0
*/
public int|InterfaceManager $exchange = 0;
/** /**
* Date type. * Date type.
* *
@ -68,7 +77,7 @@ class ExchangeLog implements \JsonSerializable, ArrayableInterface
*/ */
public \DateTimeImmutable $createdAt; public \DateTimeImmutable $createdAt;
public int $createdBy = 0; public int|Account $createdBy = 0;
/** /**
* Constructor. * Constructor.

View File

@ -15,6 +15,7 @@ declare(strict_types=1);
namespace Modules\Exchange\Models; namespace Modules\Exchange\Models;
use phpOMS\DataStorage\Database\DataMapperAbstract; use phpOMS\DataStorage\Database\DataMapperAbstract;
use Modules\Admin\Models\AccountMapper;
/** /**
* Exchange log mapper class. * Exchange log mapper class.
@ -37,7 +38,10 @@ final class ExchangeLogMapper extends DataMapperAbstract
'exchange_log_message' => ['name' => 'exchange_log_message', 'type' => 'string', 'internal' => 'message'], 'exchange_log_message' => ['name' => 'exchange_log_message', 'type' => 'string', 'internal' => 'message'],
'exchange_log_fields' => ['name' => 'exchange_log_fields', 'type' => 'Json', 'internal' => 'fields'], 'exchange_log_fields' => ['name' => 'exchange_log_fields', 'type' => 'Json', 'internal' => 'fields'],
'exchange_log_type' => ['name' => 'exchange_log_type', 'type' => 'int', 'internal' => 'type'], 'exchange_log_type' => ['name' => 'exchange_log_type', 'type' => 'int', 'internal' => 'type'],
'exchange_log_time' => ['name' => 'exchange_log_time', 'type' => 'DateTimeImmutable', 'internal' => 'createdAt'], 'exchange_log_subtype' => ['name' => 'exchange_log_subtype', 'type' => 'string', 'internal' => 'subtype'],
'exchange_log_created_at' => ['name' => 'exchange_log_created_at', 'type' => 'DateTimeImmutable', 'internal' => 'createdAt', 'readonly' => true],
'exchange_log_created_by' => ['name' => 'exchange_log_created_by', 'type' => 'int', 'internal' => 'createdBy', 'readonly' => true],
'exchange_log_exchange' => ['name' => 'exchange_log_exchange', 'type' => 'int', 'internal' => 'exchange'],
]; ];
/** /**
@ -63,4 +67,21 @@ final class ExchangeLogMapper extends DataMapperAbstract
* @since 1.0.0 * @since 1.0.0
*/ */
protected static string $primaryField = 'exchange_log_id'; protected static string $primaryField = 'exchange_log_id';
/**
* Belongs to.
*
* @var array<string, array{mapper:string, external:string}>
* @since 1.0.0
*/
protected static array $belongsTo = [
'createdBy' => [
'mapper' => AccountMapper::class,
'external' => 'exchange_log_created_by',
],
'exchange' => [
'mapper' => InterfaceManagerMapper::class,
'external' => 'exchange_log_exchange',
],
];
} }

View File

@ -52,9 +52,9 @@ abstract class ImporterAbstract
* *
* @param RequestAbstract $request Request * @param RequestAbstract $request Request
* *
* @return bool * @return array
* *
* @since 1.0.0 * @since 1.0.0
*/ */
abstract public function importFromRequest(RequestAbstract $request) : bool; abstract public function importFromRequest(RequestAbstract $request) : array;
} }

View File

@ -1,16 +0,0 @@
<?php
/**
* Orange Management
*
* PHP Version 8.0
*
* @package Modules\Exchange
* @copyright Dennis Eichhorn
* @license OMS License 1.0
* @version 1.0.0
* @link https://orange-management.org
*/
declare(strict_types=1);
/** @var \phpOMS\Views\View $this */
echo $this->getData('nav')->render();

View File

@ -0,0 +1,54 @@
<?php
/**
* Orange Management
*
* PHP Version 8.0
*
* @package Modules\Exchange
* @copyright Dennis Eichhorn
* @license OMS License 1.0
* @version 1.0.0
* @link https://orange-management.org
*/
declare(strict_types=1);
use phpOMS\Uri\UriFactory;
/** @var \phpOMS\Views\View $this */
$logs = $this->getData('logs') ?? [];
echo $this->getData('nav')->render(); ?>
<div class="row">
<div class="col-xs-12">
<div class="portlet">
<div class="portlet-head"><?= $this->getHtml('Logs'); ?><i class="fa fa-download floatRight download btn"></i></div>
<table id="exchangeLogs" class="default">
<thead>
<tr>
<td><?= $this->getHtml('ID', '0', '0'); ?>
<td><?= $this->getHtml('Type'); ?>
<td><?= $this->getHtml('Subtype'); ?>
<td class="wf-100"><?= $this->getHtml('Exchange'); ?>
<td><?= $this->getHtml('CreatedBy'); ?>
<td><?= $this->getHtml('CreatedAt'); ?>
<tbody>
<?php $count = 0; foreach ($logs as $key => $value) :
++$count;
$url = UriFactory::build('{/prefix}admin/exchange/log?{?}&id=' . $value->getId());
?>
<tr data-href="<?= $url; ?>">
<td><a href="<?= $url; ?>"><?= $value->getId(); ?></a>
<td><a href="<?= $url; ?>"><?= $value->getType(); ?></a>
<td><a href="<?= $url; ?>"><?= $value->subtype; ?></a>
<td><a href="<?= $url; ?>"><?= $value->exchange->getName(); ?></a>
<td><a href="<?= $url; ?>"><?= $value->createdBy->name1; ?></a>
<td><a href="<?= $url; ?>"><?= $value->createdAt->format('Y-m-d'); ?></a>
<?php endforeach; ?>
<?php if ($count === 0) : ?>
<tr><td colspan="9" class="empty"><?= $this->getHtml('Empty', '0', '0'); ?>
<?php endif; ?>
</table>
</div>
</div>
</div>

View File