mirror of
https://github.com/Karaka-Management/oms-LoanManagement.git
synced 2026-01-10 16:48:41 +00:00
ui fixes
This commit is contained in:
parent
d0e97083f1
commit
7707a72946
|
|
@ -57,21 +57,6 @@
|
|||
"permission": { "permission": 2, "type": null, "element": null },
|
||||
"parent": 1008301001,
|
||||
"children": []
|
||||
},
|
||||
{
|
||||
"id": 1008305001,
|
||||
"pid": "/finance/loan",
|
||||
"type": 3,
|
||||
"subtype": 1,
|
||||
"name": "Entries",
|
||||
"uri": "{/base}/finance/loan/entry/list?{?}",
|
||||
"target": "self",
|
||||
"icon": null,
|
||||
"order": 15,
|
||||
"from": "LoanManagement",
|
||||
"permission": { "permission": 2, "type": null, "element": null },
|
||||
"parent": 1008301001,
|
||||
"children": []
|
||||
}
|
||||
]
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,6 +1,17 @@
|
|||
[
|
||||
{
|
||||
"name": "loan",
|
||||
"sign": 1,
|
||||
"isLoan": true,
|
||||
"l11n": {
|
||||
"en": "Loan",
|
||||
"de": "Darlehen"
|
||||
}
|
||||
},
|
||||
{
|
||||
"name": "disagio",
|
||||
"sign": -1,
|
||||
"isLoan": true,
|
||||
"l11n": {
|
||||
"en": "Disagio",
|
||||
"de": "Disagio"
|
||||
|
|
@ -8,6 +19,7 @@
|
|||
},
|
||||
{
|
||||
"name": "interest",
|
||||
"sign": -1,
|
||||
"l11n": {
|
||||
"en": "Interest",
|
||||
"de": "Zinsen"
|
||||
|
|
@ -15,6 +27,8 @@
|
|||
},
|
||||
{
|
||||
"name": "repayment",
|
||||
"sign": -1,
|
||||
"isLoan": true,
|
||||
"l11n": {
|
||||
"en": "Repayment",
|
||||
"de": "Tilgung"
|
||||
|
|
@ -22,6 +36,8 @@
|
|||
},
|
||||
{
|
||||
"name": "unscheduled_repayment",
|
||||
"sign": -1,
|
||||
"isLoan": true,
|
||||
"l11n": {
|
||||
"en": "Unscheduled repayment",
|
||||
"de": "Sondertilgung"
|
||||
|
|
@ -29,6 +45,7 @@
|
|||
},
|
||||
{
|
||||
"name": "commitment_fee",
|
||||
"sign": -1,
|
||||
"l11n": {
|
||||
"en": "Commitment fee",
|
||||
"de": "Bereitstellungsgebühr"
|
||||
|
|
@ -36,6 +53,7 @@
|
|||
},
|
||||
{
|
||||
"name": "taxes",
|
||||
"sign": -1,
|
||||
"l11n": {
|
||||
"en": "Taxes",
|
||||
"de": "Steuern"
|
||||
|
|
@ -43,6 +61,7 @@
|
|||
},
|
||||
{
|
||||
"name": "other",
|
||||
"sign": -1,
|
||||
"l11n": {
|
||||
"en": "Others",
|
||||
"de": "Sonstige"
|
||||
|
|
|
|||
|
|
@ -14,6 +14,16 @@
|
|||
"type": "VARCHAR(255)",
|
||||
"null": false,
|
||||
"unique": true
|
||||
},
|
||||
"loanmgmt_cost_type_sign": {
|
||||
"name": "loanmgmt_cost_type_sign",
|
||||
"type": "TINYINT(1)",
|
||||
"null": false
|
||||
},
|
||||
"loanmgmt_cost_type_loan": {
|
||||
"name": "loanmgmt_cost_type_loan",
|
||||
"type": "TINYINT(1)",
|
||||
"null": false
|
||||
}
|
||||
}
|
||||
},
|
||||
|
|
@ -59,13 +69,8 @@
|
|||
"primary": true,
|
||||
"autoincrement": true
|
||||
},
|
||||
"loanmgmt_loan_start": {
|
||||
"name": "loanmgmt_loan_start",
|
||||
"type": "DATETIME",
|
||||
"null": true
|
||||
},
|
||||
"loanmgmt_loan_title": {
|
||||
"name": "loanmgmt_loan_title",
|
||||
"loanmgmt_loan_name": {
|
||||
"name": "loanmgmt_loan_name",
|
||||
"type": "VARCHAR(255)",
|
||||
"null": false
|
||||
},
|
||||
|
|
@ -74,58 +79,47 @@
|
|||
"type": "TEXT",
|
||||
"null": false
|
||||
},
|
||||
"loanmgmt_loan_payout_date": {
|
||||
"name": "loanmgmt_loan_payout_date",
|
||||
"loanmgmt_loan_status": {
|
||||
"name": "loanmgmt_loan_status",
|
||||
"type": "INT",
|
||||
"null": false
|
||||
},
|
||||
"loanmgmt_loan_borrowing_rate": {
|
||||
"name": "loanmgmt_loan_borrowing_rate",
|
||||
"type": "INT",
|
||||
"null": false
|
||||
},
|
||||
"loanmgmt_loan_post_rate": {
|
||||
"name": "loanmgmt_loan_post_rate",
|
||||
"type": "INT",
|
||||
"null": false
|
||||
},
|
||||
"loanmgmt_loan_special_payment": {
|
||||
"name": "loanmgmt_loan_special_payment",
|
||||
"type": "INT",
|
||||
"null": false
|
||||
},
|
||||
"loanmgmt_loan_supplier": {
|
||||
"name": "loanmgmt_loan_supplier",
|
||||
"type": "INT",
|
||||
"null": false,
|
||||
"foreignTable": "suppliermgmt_supplier",
|
||||
"foreignKey": "suppliermgmt_supplier_id"
|
||||
},
|
||||
"loanmgmt_loan_start": {
|
||||
"name": "loanmgmt_loan_start",
|
||||
"type": "DATETIME",
|
||||
"null": true
|
||||
},
|
||||
"loanmgmt_loan_amount": {
|
||||
"name": "loanmgmt_loan_amount",
|
||||
"type": "BIGINT",
|
||||
"null": false
|
||||
},
|
||||
"loanmgmt_loan_disagio": {
|
||||
"name": "loanmgmt_loan_disagio",
|
||||
"type": "BIGINT",
|
||||
"null": false
|
||||
},
|
||||
"loanmgmt_loan_provision": {
|
||||
"description": "Bereitstellungsgebuehr",
|
||||
"name": "loanmgmt_loan_provision",
|
||||
"type": "BIGINT",
|
||||
"null": false
|
||||
},
|
||||
"loanmgmt_loan_provision_rate": {
|
||||
"description": "Bereitstellungsgebuehr",
|
||||
"name": "loanmgmt_loan_provision_rate",
|
||||
"type": "BIGINT",
|
||||
"null": false
|
||||
},
|
||||
"loanmgmt_loan_interest_start": {
|
||||
"name": "loanmgmt_loan_interest_start",
|
||||
"loanmgmt_loan_end": {
|
||||
"name": "loanmgmt_loan_end",
|
||||
"type": "DATETIME",
|
||||
"null": true
|
||||
},
|
||||
"loanmgmt_loan_interest_rate": {
|
||||
"name": "loanmgmt_loan_interest_rate",
|
||||
"type": "INT",
|
||||
"null": false
|
||||
},
|
||||
"loanmgmt_loan_interest_rate_post": {
|
||||
"description": "Interest rate after binding period",
|
||||
"name": "loanmgmt_loan_interest_rate_post",
|
||||
"type": "INT",
|
||||
"null": false
|
||||
},
|
||||
"loanmgmt_loan_rate_binding": {
|
||||
"name": "loanmgmt_loan_rate_binding",
|
||||
"type": "INT",
|
||||
"null": false
|
||||
},
|
||||
"loanmgmt_loan_repayment_type": {
|
||||
"name": "loanmgmt_loan_repayment_type",
|
||||
"type": "TINYINT",
|
||||
"null": false
|
||||
"loanmgmt_loan_created_at": {
|
||||
"name": "loanmgmt_loan_created_at",
|
||||
"type": "DATETIME",
|
||||
"null": true
|
||||
},
|
||||
"loanmgmt_loan_created_by": {
|
||||
"name": "loanmgmt_loan_created_by",
|
||||
|
|
@ -143,5 +137,48 @@
|
|||
"foreignKey": "unit_id"
|
||||
}
|
||||
}
|
||||
},
|
||||
"loanmgmt_loan_element": {
|
||||
"name": "loanmgmt_loan_element",
|
||||
"fields": {
|
||||
"loanmgmt_loan_element_id": {
|
||||
"name": "loanmgmt_loan_element_id",
|
||||
"type": "INT",
|
||||
"null": false,
|
||||
"primary": true,
|
||||
"autoincrement": true
|
||||
},
|
||||
"loanmgmt_loan_description": {
|
||||
"name": "loanmgmt_loan_description",
|
||||
"type": "TEXT",
|
||||
"null": false
|
||||
},
|
||||
"loanmgmt_loan_element_amount": {
|
||||
"name": "loanmgmt_loan_element_amount",
|
||||
"type": "BIGINT",
|
||||
"null": false
|
||||
},
|
||||
"loanmgmt_loan_element_date": {
|
||||
"name": "loanmgmt_loan_element_date",
|
||||
"type": "DATETIME",
|
||||
"null": true
|
||||
},
|
||||
"loanmgmt_loan_element_type": {
|
||||
"name": "loanmgmt_loan_element_type",
|
||||
"type": "INT",
|
||||
"default": null,
|
||||
"null": true,
|
||||
"foreignTable": "loanmgmt_cost_type",
|
||||
"foreignKey": "loanmgmt_cost_type_id"
|
||||
},
|
||||
"loanmgmt_loan_element_loan": {
|
||||
"name": "loanmgmt_loan_element_loan",
|
||||
"type": "INT",
|
||||
"default": null,
|
||||
"null": true,
|
||||
"foreignTable": "loanmgmt_loan",
|
||||
"foreignKey": "loanmgmt_loan_id"
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -83,6 +83,8 @@ final class Installer extends InstallerAbstract
|
|||
$request->header->account = 1;
|
||||
$request->setData('name', $type['name'] ?? '');
|
||||
$request->setData('title', \reset($type['l11n']));
|
||||
$request->setData('sign', $type['sign'] ?? -1);
|
||||
$request->setData('is_loan', $type['isLoan'] ?? false);
|
||||
|
||||
$module->apiLoanCostTypeCreate($request, $response);
|
||||
|
||||
|
|
|
|||
|
|
@ -10,6 +10,7 @@ return [
|
|||
[
|
||||
'dest' => '\Modules\LoanManagement\Controller\BackendController:viewLoanList',
|
||||
'verb' => RouteVerb::GET,
|
||||
'active' => true,
|
||||
'permission' => [
|
||||
'module' => BackendController::MODULE_NAME,
|
||||
'type' => PermissionType::READ,
|
||||
|
|
@ -21,6 +22,7 @@ return [
|
|||
[
|
||||
'dest' => '\Modules\LoanManagement\Controller\BackendController:viewLoanView',
|
||||
'verb' => RouteVerb::GET,
|
||||
'active' => true,
|
||||
'permission' => [
|
||||
'module' => BackendController::MODULE_NAME,
|
||||
'type' => PermissionType::READ,
|
||||
|
|
@ -32,6 +34,7 @@ return [
|
|||
[
|
||||
'dest' => '\Modules\LoanManagement\Controller\BackendController:viewLoanCreate',
|
||||
'verb' => RouteVerb::GET,
|
||||
'active' => true,
|
||||
'permission' => [
|
||||
'module' => BackendController::MODULE_NAME,
|
||||
'type' => PermissionType::CREATE,
|
||||
|
|
@ -43,28 +46,7 @@ return [
|
|||
[
|
||||
'dest' => '\Modules\LoanManagement\Controller\BackendController:viewLoanTable',
|
||||
'verb' => RouteVerb::GET,
|
||||
'permission' => [
|
||||
'module' => BackendController::MODULE_NAME,
|
||||
'type' => PermissionType::READ,
|
||||
'state' => PermissionCategory::LOAN,
|
||||
],
|
||||
],
|
||||
],
|
||||
'^/finance/loan/entry/list(\?.*$|$)' => [
|
||||
[
|
||||
'dest' => '\Modules\LoanManagement\Controller\BackendController:viewLoanEntryList',
|
||||
'verb' => RouteVerb::GET,
|
||||
'permission' => [
|
||||
'module' => BackendController::MODULE_NAME,
|
||||
'type' => PermissionType::READ,
|
||||
'state' => PermissionCategory::LOAN,
|
||||
],
|
||||
],
|
||||
],
|
||||
'^/finance/loan/entry/view(\?.*$|$)' => [
|
||||
[
|
||||
'dest' => '\Modules\LoanManagement\Controller\BackendController:viewLoanEntryView',
|
||||
'verb' => RouteVerb::GET,
|
||||
'active' => true,
|
||||
'permission' => [
|
||||
'module' => BackendController::MODULE_NAME,
|
||||
'type' => PermissionType::READ,
|
||||
|
|
|
|||
|
|
@ -14,14 +14,23 @@ declare(strict_types=1);
|
|||
|
||||
namespace Modules\LoanManagement\Controller;
|
||||
|
||||
use Modules\LoanManagement\Models\CostType;
|
||||
use Modules\LoanManagement\Models\CostTypeL11nMapper;
|
||||
use Modules\LoanManagement\Models\CostTypeMapper;
|
||||
use Modules\LoanManagement\Models\Loan;
|
||||
use Modules\LoanManagement\Models\LoanElement;
|
||||
use phpOMS\Business\Finance\Loan as FinanceLoan;
|
||||
use Modules\LoanManagement\Models\LoanMapper;
|
||||
use Modules\LoanManagement\Models\LoanStatus;
|
||||
use Modules\LoanManagement\Models\NullCostType;
|
||||
use Modules\SupplierManagement\Models\NullSupplier;
|
||||
use phpOMS\Localization\BaseStringL11n;
|
||||
use phpOMS\Localization\BaseStringL11nType;
|
||||
use phpOMS\Localization\ISO639x1Enum;
|
||||
use phpOMS\Message\Http\RequestStatusCode;
|
||||
use phpOMS\Message\RequestAbstract;
|
||||
use phpOMS\Message\ResponseAbstract;
|
||||
use phpOMS\Stdlib\Base\FloatInt;
|
||||
use phpOMS\Stdlib\Base\SmartDateTime;
|
||||
|
||||
/**
|
||||
* LoanManagement class.
|
||||
|
|
@ -34,7 +43,7 @@ use phpOMS\Message\ResponseAbstract;
|
|||
final class ApiController extends Controller
|
||||
{
|
||||
/**
|
||||
* Api method to create tag
|
||||
* Api method to create loan
|
||||
*
|
||||
* @param RequestAbstract $request Request
|
||||
* @param ResponseAbstract $response Response
|
||||
|
|
@ -48,10 +57,135 @@ final class ApiController extends Controller
|
|||
*/
|
||||
public function apiLoanCreate(RequestAbstract $request, ResponseAbstract $response, array $data = []) : void
|
||||
{
|
||||
if (!empty($val = $this->validateLoanCreate($request))) {
|
||||
$response->header->status = RequestStatusCode::R_400;
|
||||
$this->createInvalidCreateResponse($request, $response, $val);
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
$costType = $this->createLoanFromRequest($request);
|
||||
$this->createModel($request->header->account, $costType, LoanMapper::class, 'loan', $request->getOrigin());
|
||||
$this->createStandardCreateResponse($request, $response, $costType);
|
||||
}
|
||||
|
||||
/**
|
||||
* Api method to create tag
|
||||
* Validate cost type create request
|
||||
*
|
||||
* @param RequestAbstract $request Request
|
||||
*
|
||||
* @return array<string, bool>
|
||||
*
|
||||
* @since 1.0.0
|
||||
*/
|
||||
private function validateLoanCreate(RequestAbstract $request) : array
|
||||
{
|
||||
$val = [];
|
||||
if (($val['name'] = !$request->hasData('name'))
|
||||
|| ($val['supplier'] = !$request->hasData('supplier'))
|
||||
|| ($val['start'] = !$request->hasData('start'))
|
||||
|| ($val['duration'] = !$request->hasData('duration'))
|
||||
|| ($val['amount'] = !$request->hasData('amount'))
|
||||
|| ($val['interest_rate'] = !$request->hasData('interest_rate'))
|
||||
) {
|
||||
return $val;
|
||||
}
|
||||
|
||||
return [];
|
||||
}
|
||||
|
||||
/**
|
||||
* Method to create cost type from request.
|
||||
*
|
||||
* @param RequestAbstract $request Request
|
||||
*
|
||||
* @return Loan
|
||||
*
|
||||
* @since 1.0.0
|
||||
*/
|
||||
private function createLoanFromRequest(RequestAbstract $request) : Loan
|
||||
{
|
||||
$loan = new Loan();
|
||||
|
||||
$loan->createdBy = $request->header->account;
|
||||
$loan->name = $request->getDataString('name');
|
||||
$loan->description = $request->getDataString('description');
|
||||
$loan->loanProvider = new NullSupplier((int) $request->getDataInt('supplier'));
|
||||
$loan->status = LoanStatus::tryFromValue($request->getData('status')) ?? LoanStatus::ACTIVE;
|
||||
$loan->nominalBorrowingRate = new FloatInt($request->getDataString('interest_rate') ?? 0);
|
||||
$loan->interestRateAfterDuration = new FloatInt($request->getDataString('post_interest_rate') ?? 0);
|
||||
$loan->start = $request->getDataDateTime('start') ?? new \DateTime('now');
|
||||
$loan->end = SmartDateTime::createFromDateTime($loan->start)->smartModify(0, (int) $request->getDataInt('duration'));
|
||||
$loan->isSpecialPaymentAllowed = $request->getDataBool('special_payment_allowed') ?? false;
|
||||
$loan->unit = $request->getDataInt('unit') ?? $this->app->unitId;
|
||||
|
||||
$paymentInterval = $request->getDataInt('payment_interval') ?? 12;
|
||||
|
||||
/** @var CostType[] $types */
|
||||
$types = CostTypeMapper::getAll()->executeGetArray();
|
||||
|
||||
$loanType = new NullCostType();
|
||||
$repaymentType = new NullCostType();
|
||||
$interestType = new NullCostType();
|
||||
|
||||
foreach ($types as $type) {
|
||||
if ($type->name === 'loan') {
|
||||
$loanType = $type;
|
||||
} elseif ($type->name === 'repayment') {
|
||||
$repaymentType = $type;
|
||||
} elseif ($type->name === 'interest') {
|
||||
$interestType = $type;
|
||||
}
|
||||
}
|
||||
|
||||
// Loan
|
||||
$element = new LoanElement();
|
||||
$element->amount = new FloatInt($request->getDataString('amount') ?? 0);
|
||||
$element->date = $loan->start;
|
||||
$element->type = $loanType;
|
||||
|
||||
$loan->elements[] = $element;
|
||||
|
||||
$currentDate = SmartDateTime::createFromDateTime($loan->start);
|
||||
$currentDate->smartModify(0, (int) (12 / $paymentInterval), -1);
|
||||
|
||||
// @feature Handle different loan types
|
||||
$schedule = FinanceLoan::getAmortizationSchedule(
|
||||
$element->amount->getNormalizedValue(),
|
||||
$loan->nominalBorrowingRate->getNormalizedValue() / 100,
|
||||
(int) $request->getDataInt('duration'),
|
||||
$paymentInterval
|
||||
);
|
||||
|
||||
foreach ($schedule as $idx => $e) {
|
||||
if ($idx === 0) {
|
||||
continue;
|
||||
}
|
||||
|
||||
// Repayment
|
||||
$element = new LoanElement();
|
||||
$element->amount = new FloatInt($e['principal']);
|
||||
$element->date = clone $currentDate;
|
||||
$element->type = $repaymentType;
|
||||
|
||||
$loan->elements[] = $element;
|
||||
|
||||
// Interest
|
||||
$element = new LoanElement();
|
||||
$element->amount = new FloatInt($e['interest']);
|
||||
$element->date = clone $currentDate;
|
||||
$element->type = $interestType;
|
||||
|
||||
$loan->elements[] = $element;
|
||||
|
||||
$currentDate->smartModify(0, (int) (12 / $paymentInterval));
|
||||
}
|
||||
|
||||
return $loan;
|
||||
}
|
||||
|
||||
/**
|
||||
* Api method to calculate loan timeline based on definitions
|
||||
*
|
||||
* @param RequestAbstract $request Request
|
||||
* @param ResponseAbstract $response Response
|
||||
|
|
@ -68,7 +202,7 @@ final class ApiController extends Controller
|
|||
}
|
||||
|
||||
/**
|
||||
* Api method to create tag
|
||||
* Api method to create loan elements
|
||||
*
|
||||
* @param RequestAbstract $request Request
|
||||
* @param ResponseAbstract $response Response
|
||||
|
|
@ -85,7 +219,7 @@ final class ApiController extends Controller
|
|||
}
|
||||
|
||||
/**
|
||||
* Api method to create item cost type
|
||||
* Api method to create loan cost type
|
||||
*
|
||||
* @param RequestAbstract $request Request
|
||||
* @param ResponseAbstract $response Response
|
||||
|
|
@ -112,7 +246,7 @@ final class ApiController extends Controller
|
|||
}
|
||||
|
||||
/**
|
||||
* Validate cost create request
|
||||
* Validate cost type create request
|
||||
*
|
||||
* @param RequestAbstract $request Request
|
||||
*
|
||||
|
|
@ -133,17 +267,20 @@ final class ApiController extends Controller
|
|||
}
|
||||
|
||||
/**
|
||||
* Method to create cost from request.
|
||||
* Method to create cost type from request.
|
||||
*
|
||||
* @param RequestAbstract $request Request
|
||||
*
|
||||
* @return BaseStringL11nType
|
||||
* @return CostType
|
||||
*
|
||||
* @since 1.0.0
|
||||
*/
|
||||
private function createCostTypeFromRequest(RequestAbstract $request) : BaseStringL11nType
|
||||
private function createCostTypeFromRequest(RequestAbstract $request) : CostType
|
||||
{
|
||||
$costType = new BaseStringL11nType($request->getDataString('name') ?? '');
|
||||
$costType = new CostType();
|
||||
$costType->name = $request->getDataString('name');
|
||||
$costType->sign = $request->getDataInt('sign') ?? -1;
|
||||
$costType->isLoan = $request->getDataBool('is_loan') ?? false;
|
||||
$costType->setL11n(
|
||||
$request->getDataString('title') ?? '',
|
||||
ISO639x1Enum::tryFromValue($request->getDataString('language')) ?? ISO639x1Enum::_EN
|
||||
|
|
@ -153,7 +290,7 @@ final class ApiController extends Controller
|
|||
}
|
||||
|
||||
/**
|
||||
* Api method to create item cost l11n
|
||||
* Api method to create loan cost l11n
|
||||
*
|
||||
* @param RequestAbstract $request Request
|
||||
* @param ResponseAbstract $response Response
|
||||
|
|
|
|||
103
Models/CostType.php
Executable file
103
Models/CostType.php
Executable file
|
|
@ -0,0 +1,103 @@
|
|||
<?php
|
||||
/**
|
||||
* Jingga
|
||||
*
|
||||
* PHP Version 8.2
|
||||
*
|
||||
* @package Modules\LoanManagement\Models
|
||||
* @copyright Dennis Eichhorn
|
||||
* @license OMS License 2.0
|
||||
* @version 1.0.0
|
||||
* @link https://jingga.app
|
||||
*/
|
||||
declare(strict_types=1);
|
||||
|
||||
namespace Modules\LoanManagement\Models;
|
||||
|
||||
use phpOMS\Localization\BaseStringL11n;
|
||||
use phpOMS\Localization\ISO639x1Enum;
|
||||
|
||||
/**
|
||||
* CostType class.
|
||||
*
|
||||
* @package Modules\LoanManagement\Models
|
||||
* @license OMS License 2.0
|
||||
* @link https://jingga.app
|
||||
* @since 1.0.0
|
||||
*/
|
||||
class CostType implements \JsonSerializable
|
||||
{
|
||||
/**
|
||||
* Article ID.
|
||||
*
|
||||
* @var int
|
||||
* @since 1.0.0
|
||||
*/
|
||||
public int $id = 0;
|
||||
|
||||
public string $name = '';
|
||||
|
||||
/**
|
||||
* Title.
|
||||
*
|
||||
* @var string|BaseStringL11n
|
||||
* @since 1.0.0
|
||||
*/
|
||||
public string | BaseStringL11n $l11n = '';
|
||||
|
||||
public int $sign = -1;
|
||||
|
||||
public bool $isLoan = false;
|
||||
|
||||
/**
|
||||
* @return string
|
||||
*
|
||||
* @since 1.0.0
|
||||
*/
|
||||
public function getL11n() : string
|
||||
{
|
||||
return $this->l11n instanceof BaseStringL11n ? $this->l11n->content : $this->l11n;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set l11n
|
||||
*
|
||||
* @param string|BaseStringL11n $l11n Tag article l11n
|
||||
* @param string $lang Language
|
||||
*
|
||||
* @return void
|
||||
*
|
||||
* @since 1.0.0
|
||||
*/
|
||||
public function setL11n(string | BaseStringL11n $l11n, string $lang = ISO639x1Enum::_EN) : void
|
||||
{
|
||||
if ($l11n instanceof BaseStringL11n) {
|
||||
$this->l11n = $l11n;
|
||||
} elseif (isset($this->l11n) && $this->l11n instanceof BaseStringL11n) {
|
||||
$this->l11n->content = $l11n;
|
||||
} else {
|
||||
$this->l11n = new BaseStringL11n();
|
||||
$this->l11n->content = $l11n;
|
||||
$this->l11n->language = $lang;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
public function toArray() : array
|
||||
{
|
||||
return [
|
||||
'id' => $this->id,
|
||||
'l11n' => $this->l11n,
|
||||
];
|
||||
}
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
public function jsonSerialize() : mixed
|
||||
{
|
||||
return $this->toArray();
|
||||
}
|
||||
}
|
||||
|
|
@ -18,7 +18,7 @@ use phpOMS\DataStorage\Database\Mapper\DataMapperFactory;
|
|||
use phpOMS\Localization\BaseStringL11n;
|
||||
|
||||
/**
|
||||
* Item mapper class.
|
||||
* CostTypeL11n mapper class.
|
||||
*
|
||||
* @package Modules\LoanManagement\Models
|
||||
* @license OMS License 2.0
|
||||
|
|
|
|||
|
|
@ -15,17 +15,16 @@ declare(strict_types=1);
|
|||
namespace Modules\LoanManagement\Models;
|
||||
|
||||
use phpOMS\DataStorage\Database\Mapper\DataMapperFactory;
|
||||
use phpOMS\Localization\BaseStringL11nType;
|
||||
|
||||
/**
|
||||
* Item mapper class.
|
||||
* CostType mapper class.
|
||||
*
|
||||
* @package Modules\LoanManagement\Models
|
||||
* @license OMS License 2.0
|
||||
* @link https://jingga.app
|
||||
* @since 1.0.0
|
||||
*
|
||||
* @template T of BaseStringL11nType
|
||||
* @template T of CostType
|
||||
* @extends DataMapperFactory<T>
|
||||
*/
|
||||
final class CostTypeMapper extends DataMapperFactory
|
||||
|
|
@ -38,7 +37,9 @@ final class CostTypeMapper extends DataMapperFactory
|
|||
*/
|
||||
public const COLUMNS = [
|
||||
'loanmgmt_cost_type_id' => ['name' => 'loanmgmt_cost_type_id', 'type' => 'int', 'internal' => 'id'],
|
||||
'loanmgmt_cost_type_name' => ['name' => 'loanmgmt_cost_type_name', 'type' => 'string', 'internal' => 'title', 'autocomplete' => true],
|
||||
'loanmgmt_cost_type_name' => ['name' => 'loanmgmt_cost_type_name', 'type' => 'string', 'internal' => 'name', 'autocomplete' => true],
|
||||
'loanmgmt_cost_type_sign' => ['name' => 'loanmgmt_cost_type_sign', 'type' => 'int', 'internal' => 'sign'],
|
||||
'loanmgmt_cost_type_loan' => ['name' => 'loanmgmt_cost_type_loan', 'type' => 'bool', 'internal' => 'isLoan'],
|
||||
];
|
||||
|
||||
/**
|
||||
|
|
@ -63,7 +64,7 @@ final class CostTypeMapper extends DataMapperFactory
|
|||
* @var class-string<T>
|
||||
* @since 1.0.0
|
||||
*/
|
||||
public const MODEL = BaseStringL11nType::class;
|
||||
public const MODEL = CostType::class;
|
||||
|
||||
/**
|
||||
* Primary table.
|
||||
|
|
|
|||
|
|
@ -16,6 +16,7 @@ namespace Modules\LoanManagement\Models;
|
|||
|
||||
use Modules\SupplierManagement\Models\NullSupplier;
|
||||
use Modules\SupplierManagement\Models\Supplier;
|
||||
use phpOMS\Stdlib\Base\FloatInt;
|
||||
|
||||
/**
|
||||
* Loan model.
|
||||
|
|
@ -37,40 +38,10 @@ class Loan
|
|||
|
||||
public int $status = LoanStatus::DRAFT;
|
||||
|
||||
public int $amount = 0;
|
||||
public FloatInt $nominalBorrowingRate;
|
||||
|
||||
public int $acquisitionFee = 0;
|
||||
|
||||
public int $disagio = 0;
|
||||
|
||||
public int $nominalBorrowingRate = 0;
|
||||
|
||||
public int $startingRepaymentRate = 0;
|
||||
|
||||
public int $startingRepayment = 0;
|
||||
|
||||
// 0 = end of month
|
||||
public int $dayOfRepayment = 0;
|
||||
|
||||
// monthly, quarterly, annually, end of duration
|
||||
public int $interestInterval = 0;
|
||||
|
||||
public int $interestTaxRate = 0;
|
||||
|
||||
// monthly, quarterly, annually, end of duration
|
||||
public int $repaymentInterval = 0;
|
||||
|
||||
// months
|
||||
public int $duration = 0;
|
||||
|
||||
public int $repaymentFreeTime = 0;
|
||||
|
||||
// Either separate (during the repayment free time) or during the repayment time
|
||||
public int $repaymentFreeInterest = 1;
|
||||
|
||||
public int $residualAmountAfterDuration = 0;
|
||||
|
||||
public int $annualSpecialPayment = 0;
|
||||
// 0 = not possible
|
||||
public FloatInt $interestRateAfterDuration;
|
||||
|
||||
public bool $isSpecialPaymentAllowed = false;
|
||||
|
||||
|
|
@ -78,24 +49,13 @@ class Loan
|
|||
|
||||
public \DateTime $end;
|
||||
|
||||
public \DateTime $payout;
|
||||
public \DateTimeImmutable $createdAt;
|
||||
|
||||
// 0 = not possible
|
||||
public int $interestRateAfterDuration = 0;
|
||||
public int $createdBy = 0;
|
||||
|
||||
// used to indicate if the interests/payments/taxes are manually adjusted
|
||||
public bool $hasManualInterestAmounts = false;
|
||||
public int $unit = 0;
|
||||
|
||||
public array $interests = [];
|
||||
|
||||
// in and out
|
||||
public array $payments = [];
|
||||
|
||||
public bool $hasManualPaymentAmounts = false;
|
||||
|
||||
public array $taxes = [];
|
||||
|
||||
public bool $hasManualTaxAmounts = false;
|
||||
public array $elements = [];
|
||||
|
||||
/**
|
||||
* Constructor.
|
||||
|
|
@ -104,9 +64,13 @@ class Loan
|
|||
*/
|
||||
public function __construct()
|
||||
{
|
||||
$this->createdAt = new \DateTimeImmutable();
|
||||
|
||||
$this->loanProvider = new NullSupplier();
|
||||
$this->start = new \DateTime();
|
||||
$this->end = $this->start->modify('+1 year');
|
||||
$this->payout = $this->start;
|
||||
|
||||
$this->nominalBorrowingRate = new FloatInt();
|
||||
$this->interestRateAfterDuration = new FloatInt();
|
||||
}
|
||||
}
|
||||
|
|
|
|||
47
Models/LoanElement.php
Normal file
47
Models/LoanElement.php
Normal file
|
|
@ -0,0 +1,47 @@
|
|||
<?php
|
||||
/**
|
||||
* Jingga
|
||||
*
|
||||
* PHP Version 8.2
|
||||
*
|
||||
* @package Modules\LoanManagement\Models
|
||||
* @copyright Dennis Eichhorn
|
||||
* @license OMS License 2.0
|
||||
* @version 1.0.0
|
||||
* @link https://jingga.app
|
||||
*/
|
||||
declare(strict_types=1);
|
||||
|
||||
namespace Modules\LoanManagement\Models;
|
||||
|
||||
use phpOMS\Stdlib\Base\FloatInt;
|
||||
|
||||
/**
|
||||
* Loan model.
|
||||
*
|
||||
* @package Modules\LoanManagement\Models
|
||||
* @license OMS License 2.0
|
||||
* @link https://jingga.app
|
||||
* @since 1.0.0
|
||||
*/
|
||||
class LoanElement
|
||||
{
|
||||
public int $id = 0;
|
||||
|
||||
public string $description = '';
|
||||
|
||||
public FloatInt $amount;
|
||||
|
||||
public \DateTime $date;
|
||||
|
||||
public int $loan = 0;
|
||||
|
||||
public CostType $type;
|
||||
|
||||
public function __construct()
|
||||
{
|
||||
$this->amount = new FloatInt();
|
||||
$this->date = new \DateTime();
|
||||
$this->type = new NullCostType();
|
||||
}
|
||||
}
|
||||
84
Models/LoanElementMapper.php
Normal file
84
Models/LoanElementMapper.php
Normal file
|
|
@ -0,0 +1,84 @@
|
|||
<?php
|
||||
/**
|
||||
* Jingga
|
||||
*
|
||||
* PHP Version 8.2
|
||||
*
|
||||
* @package Modules\LoanManagement\Models
|
||||
* @copyright Dennis Eichhorn
|
||||
* @license OMS License 2.0
|
||||
* @version 1.0.0
|
||||
* @link https://jingga.app
|
||||
*/
|
||||
declare(strict_types=1);
|
||||
|
||||
namespace Modules\LoanManagement\Models;
|
||||
|
||||
use Modules\SupplierManagement\Models\SupplierMapper;
|
||||
use phpOMS\DataStorage\Database\Mapper\DataMapperFactory;
|
||||
|
||||
/**
|
||||
* LoanElement mapper class.
|
||||
*
|
||||
* @package Modules\LoanManagement\Models
|
||||
* @license OMS License 2.0
|
||||
* @link https://jingga.app
|
||||
* @since 1.0.0
|
||||
*
|
||||
* @template T of LoanElement
|
||||
* @extends DataMapperFactory<T>
|
||||
*/
|
||||
final class LoanElementMapper extends DataMapperFactory
|
||||
{
|
||||
/**
|
||||
* Columns.
|
||||
*
|
||||
* @var array<string, array{name:string, type:string, internal:string, autocomplete?:bool, readonly?:bool, writeonly?:bool, annotations?:array}>
|
||||
* @since 1.0.0
|
||||
*/
|
||||
public const COLUMNS = [
|
||||
'loanmgmt_loan_element_id' => ['name' => 'loanmgmt_loan_element_id', 'type' => 'int', 'internal' => 'id'],
|
||||
'loanmgmt_loan_element_description' => ['name' => 'loanmgmt_loan_element_description', 'type' => 'string', 'internal' => 'description'],
|
||||
'loanmgmt_loan_element_date' => ['name' => 'loanmgmt_loan_element_date', 'type' => 'DateTime', 'internal' => 'date'],
|
||||
'loanmgmt_loan_element_type' => ['name' => 'loanmgmt_loan_element_type', 'type' => 'int', 'internal' => 'type'],
|
||||
'loanmgmt_loan_element_loan' => ['name' => 'loanmgmt_loan_element_loan', 'type' => 'int', 'internal' => 'loan'],
|
||||
'loanmgmt_loan_element_amount' => ['name' => 'loanmgmt_loan_element_amount', 'type' => 'Serializable', 'internal' => 'amount'],
|
||||
];
|
||||
|
||||
/**
|
||||
* Has one relation.
|
||||
*
|
||||
* @var array<string, array{mapper:class-string, external:string, by?:string, column?:string, conditional?:bool}>
|
||||
* @since 1.0.0
|
||||
*/
|
||||
public const OWNS_ONE = [
|
||||
'type' => [
|
||||
'mapper' => CostTypeMapper::class,
|
||||
'external' => 'loanmgmt_loan_element_type',
|
||||
],
|
||||
];
|
||||
|
||||
/**
|
||||
* Model to use by the mapper.
|
||||
*
|
||||
* @var class-string<T>
|
||||
* @since 1.0.0
|
||||
*/
|
||||
public const MODEL = LoanElement::class;
|
||||
|
||||
/**
|
||||
* Primary table.
|
||||
*
|
||||
* @var string
|
||||
* @since 1.0.0
|
||||
*/
|
||||
public const TABLE = 'loanmgmt_loan';
|
||||
|
||||
/**
|
||||
* Primary field name.
|
||||
*
|
||||
* @var string
|
||||
* @since 1.0.0
|
||||
*/
|
||||
public const PRIMARYFIELD = 'loanmgmt_loan_element_id';
|
||||
}
|
||||
106
Models/LoanMapper.php
Normal file
106
Models/LoanMapper.php
Normal file
|
|
@ -0,0 +1,106 @@
|
|||
<?php
|
||||
/**
|
||||
* Jingga
|
||||
*
|
||||
* PHP Version 8.2
|
||||
*
|
||||
* @package Modules\LoanManagement\Models
|
||||
* @copyright Dennis Eichhorn
|
||||
* @license OMS License 2.0
|
||||
* @version 1.0.0
|
||||
* @link https://jingga.app
|
||||
*/
|
||||
declare(strict_types=1);
|
||||
|
||||
namespace Modules\LoanManagement\Models;
|
||||
|
||||
use Modules\SupplierManagement\Models\SupplierMapper;
|
||||
use phpOMS\DataStorage\Database\Mapper\DataMapperFactory;
|
||||
|
||||
/**
|
||||
* Loan mapper class.
|
||||
*
|
||||
* @package Modules\LoanManagement\Models
|
||||
* @license OMS License 2.0
|
||||
* @link https://jingga.app
|
||||
* @since 1.0.0
|
||||
*
|
||||
* @template T of Loan
|
||||
* @extends DataMapperFactory<T>
|
||||
*/
|
||||
final class LoanMapper extends DataMapperFactory
|
||||
{
|
||||
/**
|
||||
* Columns.
|
||||
*
|
||||
* @var array<string, array{name:string, type:string, internal:string, autocomplete?:bool, readonly?:bool, writeonly?:bool, annotations?:array}>
|
||||
* @since 1.0.0
|
||||
*/
|
||||
public const COLUMNS = [
|
||||
'loanmgmt_loan_id' => ['name' => 'loanmgmt_loan_id', 'type' => 'int', 'internal' => 'id'],
|
||||
'loanmgmt_loan_name' => ['name' => 'loanmgmt_loan_name', 'type' => 'string', 'internal' => 'name', 'autocomplete' => true],
|
||||
'loanmgmt_loan_description' => ['name' => 'loanmgmt_loan_description', 'type' => 'string', 'internal' => 'description'],
|
||||
'loanmgmt_loan_start' => ['name' => 'loanmgmt_loan_start', 'type' => 'DateTime', 'internal' => 'start'],
|
||||
'loanmgmt_loan_end' => ['name' => 'loanmgmt_loan_end', 'type' => 'DateTime', 'internal' => 'end'],
|
||||
'loanmgmt_loan_created_at' => ['name' => 'loanmgmt_loan_created_at', 'type' => 'DateTimeImmutable', 'internal' => 'createdAt'],
|
||||
'loanmgmt_loan_created_by' => ['name' => 'loanmgmt_loan_created_by', 'type' => 'int', 'internal' => 'createdBy'],
|
||||
'loanmgmt_loan_unit' => ['name' => 'loanmgmt_loan_unit', 'type' => 'int', 'internal' => 'unit'],
|
||||
'loanmgmt_loan_supplier' => ['name' => 'loanmgmt_loan_supplier', 'type' => 'int', 'internal' => 'supplier'],
|
||||
'loanmgmt_loan_status' => ['name' => 'loanmgmt_loan_status', 'type' => 'int', 'internal' => 'status'],
|
||||
'loanmgmt_loan_borrowing_rate' => ['name' => 'loanmgmt_loan_borrowing_rate', 'type' => 'Serializable', 'internal' => 'nominalBorrowingRate'],
|
||||
'loanmgmt_loan_post_rate' => ['name' => 'loanmgmt_loan_post_rate', 'type' => 'Serializable', 'internal' => 'interestRateAfterDuration'],
|
||||
'loanmgmt_loan_special_payment' => ['name' => 'loanmgmt_loan_special_payment', 'type' => 'bool', 'internal' => 'isSpecialPaymentAllowed'],
|
||||
];
|
||||
|
||||
/**
|
||||
* Has one relation.
|
||||
*
|
||||
* @var array<string, array{mapper:class-string, external:string, by?:string, column?:string, conditional?:bool}>
|
||||
* @since 1.0.0
|
||||
*/
|
||||
public const OWNS_ONE = [
|
||||
'supplier' => [
|
||||
'mapper' => SupplierMapper::class,
|
||||
'external' => 'loanmgmt_loan_supplier',
|
||||
],
|
||||
];
|
||||
|
||||
/**
|
||||
* Has many relation.
|
||||
*
|
||||
* @var array<string, array{mapper:class-string, table:string, self?:?string, external?:?string, column?:string}>
|
||||
* @since 1.0.0
|
||||
*/
|
||||
public const HAS_MANY = [
|
||||
'elements' => [
|
||||
'mapper' => LoanElementMapper::class,
|
||||
'table' => 'loanmgmt_loan_element',
|
||||
'self' => 'loanmgmt_loan_element_loan',
|
||||
'external' => null,
|
||||
],
|
||||
];
|
||||
|
||||
/**
|
||||
* Model to use by the mapper.
|
||||
*
|
||||
* @var class-string<T>
|
||||
* @since 1.0.0
|
||||
*/
|
||||
public const MODEL = Loan::class;
|
||||
|
||||
/**
|
||||
* Primary table.
|
||||
*
|
||||
* @var string
|
||||
* @since 1.0.0
|
||||
*/
|
||||
public const TABLE = 'loanmgmt_loan';
|
||||
|
||||
/**
|
||||
* Primary field name.
|
||||
*
|
||||
* @var string
|
||||
* @since 1.0.0
|
||||
*/
|
||||
public const PRIMARYFIELD = 'loanmgmt_loan_id';
|
||||
}
|
||||
|
|
@ -17,7 +17,7 @@ namespace Modules\LoanManagement\Models;
|
|||
use phpOMS\Stdlib\Base\Enum;
|
||||
|
||||
/**
|
||||
* Loanment status enum.
|
||||
* Loan status enum.
|
||||
*
|
||||
* @package Modules\LoanManagement\Models
|
||||
* @license OMS License 2.0
|
||||
|
|
|
|||
34
Models/LoanType.php
Normal file
34
Models/LoanType.php
Normal file
|
|
@ -0,0 +1,34 @@
|
|||
<?php
|
||||
/**
|
||||
* Jingga
|
||||
*
|
||||
* PHP Version 8.2
|
||||
*
|
||||
* @package Modules\LoanManagement\Models
|
||||
* @copyright Dennis Eichhorn
|
||||
* @license OMS License 2.0
|
||||
* @version 1.0.0
|
||||
* @link https://jingga.app
|
||||
*/
|
||||
declare(strict_types=1);
|
||||
|
||||
namespace Modules\LoanManagement\Models;
|
||||
|
||||
use phpOMS\Stdlib\Base\Enum;
|
||||
|
||||
/**
|
||||
* Loan type enum.
|
||||
*
|
||||
* @package Modules\LoanManagement\Models
|
||||
* @license OMS License 2.0
|
||||
* @link https://jingga.app
|
||||
* @since 1.0.0
|
||||
*/
|
||||
abstract class LoanType extends Enum
|
||||
{
|
||||
public const AMORTIZED_LOAN = 1;
|
||||
|
||||
public const DEFERRED_PAYMENT_LOAN = 2;
|
||||
|
||||
public const BOND_LOAN = 3;
|
||||
}
|
||||
46
Models/NullCostType.php
Normal file
46
Models/NullCostType.php
Normal file
|
|
@ -0,0 +1,46 @@
|
|||
<?php
|
||||
/**
|
||||
* Jingga
|
||||
*
|
||||
* PHP Version 8.2
|
||||
*
|
||||
* @package Modules\LoanManagement\Models
|
||||
* @copyright Dennis Eichhorn
|
||||
* @license OMS License 2.0
|
||||
* @version 1.0.0
|
||||
* @link https://jingga.app
|
||||
*/
|
||||
declare(strict_types=1);
|
||||
|
||||
namespace Modules\LoanManagement\Models;
|
||||
|
||||
/**
|
||||
* Null model
|
||||
*
|
||||
* @package Modules\LoanManagement\Models
|
||||
* @license OMS License 2.0
|
||||
* @link https://jingga.app
|
||||
* @since 1.0.0
|
||||
*/
|
||||
final class NullCostType extends CostType
|
||||
{
|
||||
/**
|
||||
* Constructor
|
||||
*
|
||||
* @param int $id Model id
|
||||
*
|
||||
* @since 1.0.0
|
||||
*/
|
||||
public function __construct(int $id = 0)
|
||||
{
|
||||
$this->id = $id;
|
||||
}
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
public function jsonSerialize() : mixed
|
||||
{
|
||||
return ['id' => $this->id];
|
||||
}
|
||||
}
|
||||
47
Models/NullLoan.php
Normal file
47
Models/NullLoan.php
Normal file
|
|
@ -0,0 +1,47 @@
|
|||
<?php
|
||||
/**
|
||||
* Jingga
|
||||
*
|
||||
* PHP Version 8.2
|
||||
*
|
||||
* @package Modules\LoanManagement\Models
|
||||
* @copyright Dennis Eichhorn
|
||||
* @license OMS License 2.0
|
||||
* @version 1.0.0
|
||||
* @link https://jingga.app
|
||||
*/
|
||||
declare(strict_types=1);
|
||||
|
||||
namespace Modules\LoanManagement\Models;
|
||||
|
||||
/**
|
||||
* Null model
|
||||
*
|
||||
* @package Modules\LoanManagement\Models
|
||||
* @license OMS License 2.0
|
||||
* @link https://jingga.app
|
||||
* @since 1.0.0
|
||||
*/
|
||||
final class NullLoan extends Loan
|
||||
{
|
||||
/**
|
||||
* Constructor
|
||||
*
|
||||
* @param int $id Model id
|
||||
*
|
||||
* @since 1.0.0
|
||||
*/
|
||||
public function __construct(int $id = 0)
|
||||
{
|
||||
$this->id = $id;
|
||||
parent::__construct();
|
||||
}
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
public function jsonSerialize() : mixed
|
||||
{
|
||||
return ['id' => $this->id];
|
||||
}
|
||||
}
|
||||
47
Models/NullLoanElement.php
Normal file
47
Models/NullLoanElement.php
Normal file
|
|
@ -0,0 +1,47 @@
|
|||
<?php
|
||||
/**
|
||||
* Jingga
|
||||
*
|
||||
* PHP Version 8.2
|
||||
*
|
||||
* @package Modules\LoanManagement\Models
|
||||
* @copyright Dennis Eichhorn
|
||||
* @license OMS License 2.0
|
||||
* @version 1.0.0
|
||||
* @link https://jingga.app
|
||||
*/
|
||||
declare(strict_types=1);
|
||||
|
||||
namespace Modules\LoanManagement\Models;
|
||||
|
||||
/**
|
||||
* Null model
|
||||
*
|
||||
* @package Modules\LoanManagement\Models
|
||||
* @license OMS License 2.0
|
||||
* @link https://jingga.app
|
||||
* @since 1.0.0
|
||||
*/
|
||||
final class NullLoanElement extends LoanElement
|
||||
{
|
||||
/**
|
||||
* Constructor
|
||||
*
|
||||
* @param int $id Model id
|
||||
*
|
||||
* @since 1.0.0
|
||||
*/
|
||||
public function __construct(int $id = 0)
|
||||
{
|
||||
$this->id = $id;
|
||||
parent::__construct();
|
||||
}
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
public function jsonSerialize() : mixed
|
||||
{
|
||||
return ['id' => $this->id];
|
||||
}
|
||||
}
|
||||
Loading…
Reference in New Issue
Block a user