Move the model callbacks into Observables; reduce caching since it held balances incorrectly
This commit is contained in:
2
Procfile
2
Procfile
@@ -1,5 +1,5 @@
|
|||||||
dnsmasq: /usr/local/sbin/dnsmasq --keep-in-foreground
|
dnsmasq: /usr/local/sbin/dnsmasq --keep-in-foreground
|
||||||
php-fpm: /usr/local/sbin/php-fpm --nodaemonize
|
php-fpm: /usr/local/sbin/php-fpm --nodaemonize
|
||||||
nginx: /usr/local/bin/nginx -g 'daemon off;'
|
nginx: /usr/local/bin/nginx -g 'daemon off;'
|
||||||
mysql: /usr/local/bin/mysqld
|
#mysql: /usr/local/bin/mysqld
|
||||||
#mailhog: /usr/local/bin/mailhog
|
#mailhog: /usr/local/bin/mailhog
|
||||||
|
|||||||
@@ -4,7 +4,6 @@ namespace App\Models;
|
|||||||
|
|
||||||
use App\Models\Enums\AircraftStatus;
|
use App\Models\Enums\AircraftStatus;
|
||||||
use App\Models\Traits\ExpensableTrait;
|
use App\Models\Traits\ExpensableTrait;
|
||||||
use App\Support\ICAO;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @property mixed subfleet_id
|
* @property mixed subfleet_id
|
||||||
@@ -58,27 +57,23 @@ class Aircraft extends BaseModel
|
|||||||
];
|
];
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Callbacks
|
* See if this aircraft is active
|
||||||
|
* @return bool
|
||||||
*/
|
*/
|
||||||
protected static function boot()
|
public function getActiveAttribute(): bool
|
||||||
{
|
|
||||||
parent::boot();
|
|
||||||
static::creating(function (Aircraft $model) {
|
|
||||||
if (!empty($model->icao)) {
|
|
||||||
$model->icao = strtoupper(trim($model->icao));
|
|
||||||
}
|
|
||||||
|
|
||||||
if(empty($model->hex_code)) {
|
|
||||||
$model->hex_code = ICAO::createHexCode();
|
|
||||||
}
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
public function getActiveAttribute()
|
|
||||||
{
|
{
|
||||||
return $this->status === AircraftStatus::ACTIVE;
|
return $this->status === AircraftStatus::ACTIVE;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Capitalize the ICAO when set
|
||||||
|
* @param $icao
|
||||||
|
*/
|
||||||
|
public function setIcaoAttribute($icao): void
|
||||||
|
{
|
||||||
|
$this->attributes['icao'] = strtoupper($icao);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* foreign keys
|
* foreign keys
|
||||||
*/
|
*/
|
||||||
|
|||||||
@@ -7,6 +7,12 @@ use App\Models\Traits\JournalTrait;
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Class Airline
|
* Class Airline
|
||||||
|
* @property string code
|
||||||
|
* @property string icao
|
||||||
|
* @property string iata
|
||||||
|
* @property string name
|
||||||
|
* @property string logo
|
||||||
|
* @property string country
|
||||||
* @property Journal journal
|
* @property Journal journal
|
||||||
* @package App\Models
|
* @package App\Models
|
||||||
*/
|
*/
|
||||||
@@ -63,21 +69,21 @@ class Airline extends BaseModel
|
|||||||
return $this->icao;
|
return $this->icao;
|
||||||
}
|
}
|
||||||
|
|
||||||
protected static function boot()
|
/**
|
||||||
|
* Capitalize the IATA code when set
|
||||||
|
* @param $iata
|
||||||
|
*/
|
||||||
|
public function setIataAttribute($iata)
|
||||||
{
|
{
|
||||||
parent::boot();
|
$this->attributes['iata'] = strtoupper($iata);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* IATA and ICAO should be in all caps
|
* Capitalize the ICAO when set
|
||||||
*/
|
* @param $icao
|
||||||
static::creating(function (Airline $model) {
|
*/
|
||||||
if (!empty($model->iata)) {
|
public function setIcaoAttribute($icao): void
|
||||||
$model->iata = strtoupper($model->iata);
|
{
|
||||||
}
|
$this->attributes['icao'] = strtoupper($icao);
|
||||||
|
|
||||||
if (!empty($model->icao)) {
|
|
||||||
$model->icao = strtoupper($model->icao);
|
|
||||||
}
|
|
||||||
});
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -3,17 +3,18 @@
|
|||||||
namespace App\Models;
|
namespace App\Models;
|
||||||
|
|
||||||
use App\Models\Traits\ExpensableTrait;
|
use App\Models\Traits\ExpensableTrait;
|
||||||
use Illuminate\Notifications\Notifiable;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Class Airport
|
* Class Airport
|
||||||
|
* @property string id
|
||||||
|
* @property string iata
|
||||||
|
* @property string icao
|
||||||
* @property float ground_handling_cost
|
* @property float ground_handling_cost
|
||||||
* @package App\Models
|
* @package App\Models
|
||||||
*/
|
*/
|
||||||
class Airport extends BaseModel
|
class Airport extends BaseModel
|
||||||
{
|
{
|
||||||
use ExpensableTrait;
|
use ExpensableTrait;
|
||||||
use Notifiable;
|
|
||||||
|
|
||||||
public $table = 'airports';
|
public $table = 'airports';
|
||||||
public $timestamps = false;
|
public $timestamps = false;
|
||||||
@@ -59,32 +60,6 @@ class Airport extends BaseModel
|
|||||||
'ground_handling_cost' => 'nullable|numeric',
|
'ground_handling_cost' => 'nullable|numeric',
|
||||||
];
|
];
|
||||||
|
|
||||||
/**
|
|
||||||
* Callbacks
|
|
||||||
*/
|
|
||||||
public static function boot()
|
|
||||||
{
|
|
||||||
parent::boot();
|
|
||||||
|
|
||||||
static::creating(function ($model) {
|
|
||||||
if(filled($model->iata)) {
|
|
||||||
$model->iata = strtoupper(trim($model->iata));
|
|
||||||
}
|
|
||||||
|
|
||||||
$model->icao = strtoupper(trim($model->icao));
|
|
||||||
$model->id = $model->icao;
|
|
||||||
});
|
|
||||||
|
|
||||||
static::updating(function($model) {
|
|
||||||
if (filled($model->iata)) {
|
|
||||||
$model->iata = strtoupper(trim($model->iata));
|
|
||||||
}
|
|
||||||
|
|
||||||
$model->icao = strtoupper(trim($model->icao));
|
|
||||||
$model->id = $model->icao;
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @param $icao
|
* @param $icao
|
||||||
*/
|
*/
|
||||||
@@ -98,13 +73,12 @@ class Airport extends BaseModel
|
|||||||
/**
|
/**
|
||||||
* @param $iata
|
* @param $iata
|
||||||
*/
|
*/
|
||||||
public function setIataAttribute($iata)
|
public function setIataAttribute($iata): void
|
||||||
{
|
{
|
||||||
$iata = strtoupper($iata);
|
$iata = strtoupper($iata);
|
||||||
$this->attributes['iata'] = $iata;
|
$this->attributes['iata'] = $iata;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Return full name like:
|
* Return full name like:
|
||||||
* KJFK - John F Kennedy
|
* KJFK - John F Kennedy
|
||||||
@@ -121,14 +95,14 @@ class Airport extends BaseModel
|
|||||||
*/
|
*/
|
||||||
public function getTzAttribute(): string
|
public function getTzAttribute(): string
|
||||||
{
|
{
|
||||||
return $this->timezone;
|
return $this->attributes['timezone'];
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Shorthand for setting the timezone
|
* Shorthand for setting the timezone
|
||||||
* @param $value
|
* @param $value
|
||||||
*/
|
*/
|
||||||
public function setTzAttribute($value)
|
public function setTzAttribute($value): void
|
||||||
{
|
{
|
||||||
$this->attributes['timezone'] = $value;
|
$this->attributes['timezone'] = $value;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -40,9 +40,9 @@ class Fare extends BaseModel
|
|||||||
* any foreign keys
|
* any foreign keys
|
||||||
*/
|
*/
|
||||||
|
|
||||||
public function subfleets() {
|
public function subfleets()
|
||||||
|
{
|
||||||
return $this->belongsToMany(Subfleet::class, 'subfleet_fare')
|
return $this->belongsToMany(Subfleet::class, 'subfleet_fare')
|
||||||
->withPivot('price', 'cost', 'capacity');
|
->withPivot('price', 'cost', 'capacity');
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -4,10 +4,15 @@ namespace App\Models;
|
|||||||
|
|
||||||
use App\Models\Traits\HashIdTrait;
|
use App\Models\Traits\HashIdTrait;
|
||||||
use App\Support\Units\Distance;
|
use App\Support\Units\Distance;
|
||||||
use App\Support\Units\Time;
|
|
||||||
use PhpUnitsOfMeasure\Exception\NonNumericValue;
|
use PhpUnitsOfMeasure\Exception\NonNumericValue;
|
||||||
use PhpUnitsOfMeasure\Exception\NonStringUnitName;
|
use PhpUnitsOfMeasure\Exception\NonStringUnitName;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @property Airline airline
|
||||||
|
* @property mixed flight_number
|
||||||
|
* @property mixed route_code
|
||||||
|
* @property mixed route_leg
|
||||||
|
*/
|
||||||
class Flight extends BaseModel
|
class Flight extends BaseModel
|
||||||
{
|
{
|
||||||
use HashIdTrait;
|
use HashIdTrait;
|
||||||
@@ -64,7 +69,7 @@ class Flight extends BaseModel
|
|||||||
/**
|
/**
|
||||||
* Get the flight ident, e.,g JBU1900
|
* Get the flight ident, e.,g JBU1900
|
||||||
*/
|
*/
|
||||||
public function getIdentAttribute()
|
public function getIdentAttribute(): string
|
||||||
{
|
{
|
||||||
$flight_id = $this->airline->code;
|
$flight_id = $this->airline->code;
|
||||||
$flight_id .= $this->flight_number;
|
$flight_id .= $this->flight_number;
|
||||||
@@ -104,7 +109,7 @@ class Flight extends BaseModel
|
|||||||
* Set the distance unit, convert to our internal default unit
|
* Set the distance unit, convert to our internal default unit
|
||||||
* @param $value
|
* @param $value
|
||||||
*/
|
*/
|
||||||
public function setDistanceAttribute($value)
|
public function setDistanceAttribute($value): void
|
||||||
{
|
{
|
||||||
if($value instanceof Distance) {
|
if($value instanceof Distance) {
|
||||||
$this->attributes['distance'] = $value->toUnit(
|
$this->attributes['distance'] = $value->toUnit(
|
||||||
@@ -115,30 +120,6 @@ class Flight extends BaseModel
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* @return Time
|
|
||||||
*/
|
|
||||||
/*public function getFlightTimeAttribute()
|
|
||||||
{
|
|
||||||
if (!array_key_exists('flight_time', $this->attributes)) {
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
return new Time($this->attributes['flight_time']);
|
|
||||||
}*/
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @param $value
|
|
||||||
*/
|
|
||||||
/*public function setFlightTimeAttribute($value)
|
|
||||||
{
|
|
||||||
if ($value instanceof Time) {
|
|
||||||
$this->attributes['flight_time'] = $value->getMinutes();
|
|
||||||
} else {
|
|
||||||
$this->attributes['flight_time'] = $value;
|
|
||||||
}
|
|
||||||
}*/
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Relationship
|
* Relationship
|
||||||
*/
|
*/
|
||||||
|
|||||||
@@ -3,8 +3,7 @@
|
|||||||
namespace App\Models;
|
namespace App\Models;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Class Flight
|
* Class FlightFields
|
||||||
*
|
|
||||||
* @package App\Models
|
* @package App\Models
|
||||||
*/
|
*/
|
||||||
class FlightFields extends BaseModel
|
class FlightFields extends BaseModel
|
||||||
@@ -17,8 +16,6 @@ class FlightFields extends BaseModel
|
|||||||
'value',
|
'value',
|
||||||
];
|
];
|
||||||
|
|
||||||
protected $casts = [];
|
|
||||||
|
|
||||||
public static $rules = [];
|
public static $rules = [];
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -29,5 +26,4 @@ class FlightFields extends BaseModel
|
|||||||
{
|
{
|
||||||
return $this->belongsTo(Flight::class, 'flight_id');
|
return $this->belongsTo(Flight::class, 'flight_id');
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -10,7 +10,6 @@ use GeoJson\Geometry\Point;
|
|||||||
/**
|
/**
|
||||||
* Return different points/features in GeoJSON format
|
* Return different points/features in GeoJSON format
|
||||||
* https://tools.ietf.org/html/rfc7946
|
* https://tools.ietf.org/html/rfc7946
|
||||||
*
|
|
||||||
* @package App\Models
|
* @package App\Models
|
||||||
*/
|
*/
|
||||||
class GeoJson
|
class GeoJson
|
||||||
|
|||||||
@@ -34,10 +34,8 @@ class Journal extends BaseModel
|
|||||||
'morphed_id',
|
'morphed_id',
|
||||||
];
|
];
|
||||||
|
|
||||||
/**
|
|
||||||
* @var array
|
|
||||||
*/
|
|
||||||
protected $dates = [
|
protected $dates = [
|
||||||
|
'created_at',
|
||||||
'deleted_at',
|
'deleted_at',
|
||||||
'updated_at'
|
'updated_at'
|
||||||
];
|
];
|
||||||
@@ -50,20 +48,6 @@ class Journal extends BaseModel
|
|||||||
return $this->morphTo();
|
return $this->morphTo();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* @internal Journal $journal
|
|
||||||
* @throws \UnexpectedValueException
|
|
||||||
* @throws \InvalidArgumentException
|
|
||||||
*/
|
|
||||||
protected static function boot()
|
|
||||||
{
|
|
||||||
static::created(function (Journal $journal) {
|
|
||||||
$journal->resetCurrentBalances();
|
|
||||||
});
|
|
||||||
|
|
||||||
parent::boot();
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Relationship
|
* Relationship
|
||||||
* @return \Illuminate\Database\Eloquent\Relations\BelongsTo
|
* @return \Illuminate\Database\Eloquent\Relations\BelongsTo
|
||||||
|
|||||||
@@ -7,6 +7,7 @@
|
|||||||
namespace App\Models;
|
namespace App\Models;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* @property string id UUID type
|
||||||
* @property string currency
|
* @property string currency
|
||||||
* @property string memo
|
* @property string memo
|
||||||
* @property string transaction_group
|
* @property string transaction_group
|
||||||
@@ -15,6 +16,7 @@ namespace App\Models;
|
|||||||
* @property integer debit
|
* @property integer debit
|
||||||
* @property string ref_class
|
* @property string ref_class
|
||||||
* @property integer ref_class_id
|
* @property integer ref_class_id
|
||||||
|
* @property Journal journal
|
||||||
*/
|
*/
|
||||||
class JournalTransaction extends BaseModel
|
class JournalTransaction extends BaseModel
|
||||||
{
|
{
|
||||||
@@ -48,59 +50,6 @@ class JournalTransaction extends BaseModel
|
|||||||
'post_date',
|
'post_date',
|
||||||
];
|
];
|
||||||
|
|
||||||
/**
|
|
||||||
* Callbacks
|
|
||||||
* @throws \UnexpectedValueException
|
|
||||||
* @throws \InvalidArgumentException
|
|
||||||
*/
|
|
||||||
protected static function boot()
|
|
||||||
{
|
|
||||||
static::creating(function ($transaction) {
|
|
||||||
if(!$transaction->id) {
|
|
||||||
$transaction->id = \Ramsey\Uuid\Uuid::uuid4()->toString();
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Adjust the balance according to credits and debits
|
|
||||||
*/
|
|
||||||
static::saved(function ($transaction) {
|
|
||||||
//$transaction->journal->resetCurrentBalances();
|
|
||||||
$journal = $transaction->journal;
|
|
||||||
if($transaction['credit']) {
|
|
||||||
$balance = $journal->balance->toAmount();
|
|
||||||
$journal->balance = $balance + $transaction['credit'];
|
|
||||||
}
|
|
||||||
|
|
||||||
if($transaction['debit']) {
|
|
||||||
$balance = $journal->balance->toAmount();
|
|
||||||
$journal->balance = $balance - $transaction['debit'];
|
|
||||||
}
|
|
||||||
|
|
||||||
$journal->save();
|
|
||||||
});
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Deleting a transaction reverses the credits and debits
|
|
||||||
*/
|
|
||||||
static::deleted(function ($transaction) {
|
|
||||||
$journal = $transaction->journal;
|
|
||||||
if ($transaction['credit']) {
|
|
||||||
$balance = $journal->balance->toAmount();
|
|
||||||
$journal->balance = $balance - $transaction['credit'];
|
|
||||||
}
|
|
||||||
|
|
||||||
if ($transaction['debit']) {
|
|
||||||
$balance = $journal->balance->toAmount();
|
|
||||||
$journal->balance = $balance + $transaction['debit'];
|
|
||||||
}
|
|
||||||
|
|
||||||
$journal->save();
|
|
||||||
});
|
|
||||||
|
|
||||||
parent::boot();
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @return \Illuminate\Database\Eloquent\Relations\BelongsTo
|
* @return \Illuminate\Database\Eloquent\Relations\BelongsTo
|
||||||
*/
|
*/
|
||||||
|
|||||||
@@ -24,17 +24,12 @@ class Navdata extends BaseModel
|
|||||||
'freq' => 'float',
|
'freq' => 'float',
|
||||||
];
|
];
|
||||||
|
|
||||||
protected static function boot()
|
/**
|
||||||
|
* Make sure the ID is in all caps
|
||||||
|
* @param $id
|
||||||
|
*/
|
||||||
|
public function setIdAttribute($id): void
|
||||||
{
|
{
|
||||||
parent::boot();
|
$this->attributes['id'] = strtoupper($id);
|
||||||
|
|
||||||
/**
|
|
||||||
* Make sure the ID is all caps
|
|
||||||
*/
|
|
||||||
static::creating(function (Navdata $model) {
|
|
||||||
if (!empty($model->id)) {
|
|
||||||
$model->id = strtoupper($model->id);
|
|
||||||
}
|
|
||||||
});
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
20
app/Models/Observers/AircraftObserver.php
Normal file
20
app/Models/Observers/AircraftObserver.php
Normal file
@@ -0,0 +1,20 @@
|
|||||||
|
<?php
|
||||||
|
|
||||||
|
namespace App\Models\Observers;
|
||||||
|
|
||||||
|
use App\Models\Aircraft;
|
||||||
|
use App\Support\ICAO;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Class AircraftObserver
|
||||||
|
* @package App\Models\Observers
|
||||||
|
*/
|
||||||
|
class AircraftObserver
|
||||||
|
{
|
||||||
|
public function creating(Aircraft $aircraft): void
|
||||||
|
{
|
||||||
|
if (empty($aircraft->hex_code)) {
|
||||||
|
$aircraft->hex_code = ICAO::createHexCode();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
38
app/Models/Observers/AirportObserver.php
Normal file
38
app/Models/Observers/AirportObserver.php
Normal file
@@ -0,0 +1,38 @@
|
|||||||
|
<?php
|
||||||
|
|
||||||
|
namespace App\Models\Observers;
|
||||||
|
|
||||||
|
use App\Models\Airport;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Make sure that the fields are properly capitalized
|
||||||
|
* @package App\Models\Observers
|
||||||
|
*/
|
||||||
|
class AirportObserver
|
||||||
|
{
|
||||||
|
/**
|
||||||
|
* @param Airport $airport
|
||||||
|
*/
|
||||||
|
public function creating(Airport $airport): void
|
||||||
|
{
|
||||||
|
if (filled($airport->iata)) {
|
||||||
|
$airport->iata = strtoupper(trim($airport->iata));
|
||||||
|
}
|
||||||
|
|
||||||
|
$airport->icao = strtoupper(trim($airport->icao));
|
||||||
|
$airport->id = $airport->icao;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param Airport $airport
|
||||||
|
*/
|
||||||
|
public function updating(Airport $airport): void
|
||||||
|
{
|
||||||
|
if (filled($airport->iata)) {
|
||||||
|
$airport->iata = strtoupper(trim($airport->iata));
|
||||||
|
}
|
||||||
|
|
||||||
|
$airport->icao = strtoupper(trim($airport->icao));
|
||||||
|
$airport->id = $airport->icao;
|
||||||
|
}
|
||||||
|
}
|
||||||
22
app/Models/Observers/JournalObserver.php
Normal file
22
app/Models/Observers/JournalObserver.php
Normal file
@@ -0,0 +1,22 @@
|
|||||||
|
<?php
|
||||||
|
|
||||||
|
namespace App\Models\Observers;
|
||||||
|
|
||||||
|
use App\Models\Journal;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Class JournalObserver
|
||||||
|
* @package App\Models\Observers
|
||||||
|
*/
|
||||||
|
class JournalObserver
|
||||||
|
{
|
||||||
|
/**
|
||||||
|
* @param Journal $journal
|
||||||
|
* @throws \UnexpectedValueException
|
||||||
|
* @throws \InvalidArgumentException
|
||||||
|
*/
|
||||||
|
public function creating(Journal $journal): void
|
||||||
|
{
|
||||||
|
$journal->balance = 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
60
app/Models/Observers/JournalTransactionObserver.php
Normal file
60
app/Models/Observers/JournalTransactionObserver.php
Normal file
@@ -0,0 +1,60 @@
|
|||||||
|
<?php
|
||||||
|
|
||||||
|
namespace App\Models\Observers;
|
||||||
|
|
||||||
|
use App\Models\JournalTransaction;
|
||||||
|
|
||||||
|
class JournalTransactionObserver
|
||||||
|
{
|
||||||
|
/**
|
||||||
|
* Set the ID to a UUID
|
||||||
|
* @param JournalTransaction $transaction
|
||||||
|
*/
|
||||||
|
public function creating(JournalTransaction $transaction): void
|
||||||
|
{
|
||||||
|
if (!$transaction->id) {
|
||||||
|
$transaction->id = \Ramsey\Uuid\Uuid::uuid4()->toString();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* After transaction is saved, adjust the journal balance
|
||||||
|
* @param JournalTransaction $transaction
|
||||||
|
*/
|
||||||
|
public function saved(JournalTransaction $transaction): void
|
||||||
|
{
|
||||||
|
$journal = $transaction->journal;
|
||||||
|
if ($transaction['credit']) {
|
||||||
|
$balance = $journal->balance->toAmount();
|
||||||
|
$journal->balance = (int) $balance + $transaction->credit;
|
||||||
|
}
|
||||||
|
|
||||||
|
if ($transaction['debit']) {
|
||||||
|
$balance = $journal->balance->toAmount();
|
||||||
|
#$journal->balance = $journal->balance->subtract($transaction['debit']);
|
||||||
|
$journal->balance = (int) $balance - $transaction->debit;
|
||||||
|
}
|
||||||
|
|
||||||
|
$journal->save();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* After transaction is deleted, adjust the balance on the journal
|
||||||
|
* @param JournalTransaction $transaction
|
||||||
|
*/
|
||||||
|
public function deleted(JournalTransaction $transaction): void
|
||||||
|
{
|
||||||
|
$journal = $transaction->journal;
|
||||||
|
if ($transaction['credit']) {
|
||||||
|
$balance = $journal->balance->toAmount();
|
||||||
|
$journal->balance = $balance - $transaction['credit'];
|
||||||
|
}
|
||||||
|
|
||||||
|
if ($transaction['debit']) {
|
||||||
|
$balance = $journal->balance->toAmount();
|
||||||
|
$journal->balance = $balance + $transaction['debit'];
|
||||||
|
}
|
||||||
|
|
||||||
|
$journal->save();
|
||||||
|
}
|
||||||
|
}
|
||||||
28
app/Models/Observers/PirepFieldObserver.php
Normal file
28
app/Models/Observers/PirepFieldObserver.php
Normal file
@@ -0,0 +1,28 @@
|
|||||||
|
<?php
|
||||||
|
|
||||||
|
namespace App\Models\Observers;
|
||||||
|
|
||||||
|
use App\Models\PirepField;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Class PirepFieldObserver
|
||||||
|
* @package App\Models\Observers
|
||||||
|
*/
|
||||||
|
class PirepFieldObserver
|
||||||
|
{
|
||||||
|
/**
|
||||||
|
* @param PirepField $model
|
||||||
|
*/
|
||||||
|
public function creating(PirepField $model): void
|
||||||
|
{
|
||||||
|
$model->slug = str_slug($model->name);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param PirepField $model
|
||||||
|
*/
|
||||||
|
public function updating(PirepField $model): void
|
||||||
|
{
|
||||||
|
$model->slug = str_slug($model->name);
|
||||||
|
}
|
||||||
|
}
|
||||||
18
app/Models/Observers/SettingObserver.php
Normal file
18
app/Models/Observers/SettingObserver.php
Normal file
@@ -0,0 +1,18 @@
|
|||||||
|
<?php
|
||||||
|
|
||||||
|
namespace App\Models\Observers;
|
||||||
|
|
||||||
|
use App\Models\Setting;
|
||||||
|
|
||||||
|
class SettingObserver
|
||||||
|
{
|
||||||
|
/**
|
||||||
|
* @param Setting $model
|
||||||
|
*/
|
||||||
|
public function creating(Setting $model): void
|
||||||
|
{
|
||||||
|
if (!empty($model->id)) {
|
||||||
|
$model->id = Setting::formatKey($model->id);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -102,7 +102,7 @@ class Pirep extends BaseModel
|
|||||||
* Get the flight ident, e.,g JBU1900
|
* Get the flight ident, e.,g JBU1900
|
||||||
* @return string
|
* @return string
|
||||||
*/
|
*/
|
||||||
public function getIdentAttribute()
|
public function getIdentAttribute(): string
|
||||||
{
|
{
|
||||||
$flight_id = $this->airline->code;
|
$flight_id = $this->airline->code;
|
||||||
$flight_id .= $this->flight_number;
|
$flight_id .= $this->flight_number;
|
||||||
@@ -196,7 +196,7 @@ class Pirep extends BaseModel
|
|||||||
* Look up the flight, based on the PIREP flight info
|
* Look up the flight, based on the PIREP flight info
|
||||||
* @return Flight|null
|
* @return Flight|null
|
||||||
*/
|
*/
|
||||||
public function getFlightAttribute()
|
public function getFlightAttribute(): ?Flight
|
||||||
{
|
{
|
||||||
$where = [
|
$where = [
|
||||||
'airline_id' => $this->airline_id,
|
'airline_id' => $this->airline_id,
|
||||||
|
|||||||
@@ -4,6 +4,8 @@ namespace App\Models;
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Class PirepField
|
* Class PirepField
|
||||||
|
* @property string name
|
||||||
|
* @property string slug
|
||||||
* @package App\Models
|
* @package App\Models
|
||||||
*/
|
*/
|
||||||
class PirepField extends BaseModel
|
class PirepField extends BaseModel
|
||||||
@@ -25,33 +27,11 @@ class PirepField extends BaseModel
|
|||||||
'name' => 'required',
|
'name' => 'required',
|
||||||
];
|
];
|
||||||
|
|
||||||
/**
|
|
||||||
* Create/update the field slug
|
|
||||||
*/
|
|
||||||
protected static function boot()
|
|
||||||
{
|
|
||||||
parent::boot();
|
|
||||||
|
|
||||||
/**
|
|
||||||
* On creation
|
|
||||||
*/
|
|
||||||
static::creating(function (PirepField $model) {
|
|
||||||
$model->slug = str_slug($model->name);
|
|
||||||
});
|
|
||||||
|
|
||||||
/**
|
|
||||||
* When updating
|
|
||||||
*/
|
|
||||||
static::updating(function(PirepField $model) {
|
|
||||||
$model->slug = str_slug($model->name);
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* When setting the name attribute, also set the slug
|
* When setting the name attribute, also set the slug
|
||||||
* @param $name
|
* @param $name
|
||||||
*/
|
*/
|
||||||
public function setNameAttribute($name)
|
public function setNameAttribute($name): void
|
||||||
{
|
{
|
||||||
$this->attributes['name'] = $name;
|
$this->attributes['name'] = $name;
|
||||||
$this->attributes['slug'] = str_slug($name);
|
$this->attributes['slug'] = str_slug($name);
|
||||||
|
|||||||
@@ -25,22 +25,27 @@ class Rank extends BaseModel
|
|||||||
];
|
];
|
||||||
|
|
||||||
protected $casts = [
|
protected $casts = [
|
||||||
'hours' => 'integer',
|
'hours' => 'integer',
|
||||||
'base_pay_rate' => 'float',
|
'base_pay_rate' => 'float',
|
||||||
'auto_approve_acars' => 'bool',
|
'auto_approve_acars' => 'bool',
|
||||||
'auto_approve_manual' => 'bool',
|
'auto_approve_manual' => 'bool',
|
||||||
'auto_promote' => 'bool',
|
'auto_promote' => 'bool',
|
||||||
];
|
];
|
||||||
|
|
||||||
public static $rules = [
|
public static $rules = [
|
||||||
'name' => 'required',
|
'name' => 'required',
|
||||||
'hours' => 'required|integer',
|
'hours' => 'required|integer',
|
||||||
'acars_base_pay_rate' => 'nullable|numeric',
|
'acars_base_pay_rate' => 'nullable|numeric',
|
||||||
'manual_base_pay_rate' => 'nullable|numeric',
|
'manual_base_pay_rate' => 'nullable|numeric',
|
||||||
];
|
];
|
||||||
|
|
||||||
public function subfleets() {
|
/*
|
||||||
|
* Relationships
|
||||||
|
*/
|
||||||
|
|
||||||
|
public function subfleets()
|
||||||
|
{
|
||||||
return $this->belongsToMany(Subfleet::class, 'subfleet_rank')
|
return $this->belongsToMany(Subfleet::class, 'subfleet_rank')
|
||||||
->withPivot('acars_pay', 'manual_pay');
|
->withPivot('acars_pay', 'manual_pay');
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -2,6 +2,18 @@
|
|||||||
|
|
||||||
namespace App\Models;
|
namespace App\Models;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Class Setting
|
||||||
|
* @property string id
|
||||||
|
* @property string name
|
||||||
|
* @property string key
|
||||||
|
* @property string value
|
||||||
|
* @property string group
|
||||||
|
* @property string type
|
||||||
|
* @property string options
|
||||||
|
* @property string description
|
||||||
|
* @package App\Models
|
||||||
|
*/
|
||||||
class Setting extends BaseModel
|
class Setting extends BaseModel
|
||||||
{
|
{
|
||||||
public $table = 'settings';
|
public $table = 'settings';
|
||||||
@@ -33,29 +45,21 @@ class Setting extends BaseModel
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Callbacks
|
* Force formatting the key
|
||||||
|
* @param $id
|
||||||
*/
|
*/
|
||||||
protected static function boot()
|
public function setIdAttribute($id): void
|
||||||
{
|
{
|
||||||
parent::boot();
|
$id = strtolower($id);
|
||||||
static::creating(function (Setting $model) {
|
$this->attributes['id'] = self::formatKey($id);
|
||||||
if (!empty($model->id)) {
|
|
||||||
$model->id = Setting::formatKey($model->id);
|
|
||||||
}
|
|
||||||
});
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Override the casting mechanism
|
* Set the key to lowercase
|
||||||
* @param string $key
|
* @param $key
|
||||||
* @return mixed|string
|
|
||||||
*/
|
*/
|
||||||
/*protected function getCastType($key)
|
public function setKeyAttribute($key): void
|
||||||
{
|
{
|
||||||
if ($key === 'value' && !empty($this->type)) {
|
$this->attributes['key'] = strtolower($key);
|
||||||
return $this->type;
|
}
|
||||||
} else {
|
|
||||||
return parent::getCastType($key);
|
|
||||||
}
|
|
||||||
}*/
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,6 +1,19 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
namespace App\Providers;
|
namespace App\Providers;
|
||||||
|
|
||||||
|
use App\Models\Aircraft;
|
||||||
|
use App\Models\Airport;
|
||||||
|
use App\Models\Journal;
|
||||||
|
use App\Models\JournalTransaction;
|
||||||
|
use App\Models\Observers\AircraftObserver;
|
||||||
|
use App\Models\Observers\AirportObserver;
|
||||||
|
use App\Models\Observers\JournalObserver;
|
||||||
|
use App\Models\Observers\JournalTransactionObserver;
|
||||||
|
use App\Models\Observers\PirepFieldObserver;
|
||||||
|
use App\Models\Observers\SettingObserver;
|
||||||
|
use App\Models\PirepField;
|
||||||
|
use App\Models\Setting;
|
||||||
use App\Repositories\SettingRepository;
|
use App\Repositories\SettingRepository;
|
||||||
use App\Services\ModuleService;
|
use App\Services\ModuleService;
|
||||||
use Illuminate\Support\Facades\Schema;
|
use Illuminate\Support\Facades\Schema;
|
||||||
@@ -15,6 +28,14 @@ class AppServiceProvider extends ServiceProvider
|
|||||||
$this->app->bind('setting', SettingRepository::class);
|
$this->app->bind('setting', SettingRepository::class);
|
||||||
|
|
||||||
View::share('moduleSvc', app(ModuleService::class));
|
View::share('moduleSvc', app(ModuleService::class));
|
||||||
|
|
||||||
|
// Model observers
|
||||||
|
Aircraft::observe(AircraftObserver::class);
|
||||||
|
Airport::observe(AirportObserver::class);
|
||||||
|
Journal::observe(JournalObserver::class);
|
||||||
|
JournalTransaction::observe(JournalTransactionObserver::class);
|
||||||
|
PirepField::observe(PirepFieldObserver::class);
|
||||||
|
Setting::observe(SettingObserver::class);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|||||||
@@ -135,6 +135,8 @@ class JournalRepository extends BaseRepository implements CacheableInterface
|
|||||||
*/
|
*/
|
||||||
public function getBalance(Journal $journal=null, Carbon $date=null)
|
public function getBalance(Journal $journal=null, Carbon $date=null)
|
||||||
{
|
{
|
||||||
|
$journal->refresh();
|
||||||
|
|
||||||
if(!$date) {
|
if(!$date) {
|
||||||
$date = Carbon::now();
|
$date = Carbon::now();
|
||||||
}
|
}
|
||||||
@@ -160,27 +162,26 @@ class JournalRepository extends BaseRepository implements CacheableInterface
|
|||||||
Journal $journal=null,
|
Journal $journal=null,
|
||||||
Carbon $start_date=null,
|
Carbon $start_date=null,
|
||||||
$transaction_group=null
|
$transaction_group=null
|
||||||
): Money {
|
): Money
|
||||||
|
{
|
||||||
$where = [
|
$where = [];
|
||||||
['post_date', '<=', $date]
|
|
||||||
];
|
|
||||||
|
|
||||||
if ($journal) {
|
if ($journal) {
|
||||||
$where['journal_id'] = $journal->id;
|
$where['journal_id'] = $journal->id;
|
||||||
}
|
}
|
||||||
|
|
||||||
if ($start_date) {
|
|
||||||
$where[] = ['post_date', '>=', $start_date];
|
|
||||||
}
|
|
||||||
|
|
||||||
if ($transaction_group) {
|
if ($transaction_group) {
|
||||||
$where['transaction_group'] = $transaction_group;
|
$where['transaction_group'] = $transaction_group;
|
||||||
}
|
}
|
||||||
|
|
||||||
$balance = $this
|
$query = JournalTransaction::where($where);
|
||||||
->findWhere($where, ['id', 'credit'])
|
$query = $query->whereDate('post_date', '<=', $date->toDateString());
|
||||||
->sum('credit') ?: 0;
|
|
||||||
|
if ($start_date) {
|
||||||
|
$query = $query->whereDate('post_date', '>=', $start_date->toDateString());
|
||||||
|
}
|
||||||
|
|
||||||
|
$balance = $query->sum('credit') ?: 0;
|
||||||
|
|
||||||
return new Money($balance);
|
return new Money($balance);
|
||||||
}
|
}
|
||||||
@@ -191,6 +192,8 @@ class JournalRepository extends BaseRepository implements CacheableInterface
|
|||||||
* @param Carbon|null $start_date
|
* @param Carbon|null $start_date
|
||||||
* @param null $transaction_group
|
* @param null $transaction_group
|
||||||
* @return Money
|
* @return Money
|
||||||
|
* @throws \UnexpectedValueException
|
||||||
|
* @throws \InvalidArgumentException
|
||||||
*/
|
*/
|
||||||
public function getDebitBalanceBetween(
|
public function getDebitBalanceBetween(
|
||||||
Carbon $date,
|
Carbon $date,
|
||||||
@@ -199,29 +202,24 @@ class JournalRepository extends BaseRepository implements CacheableInterface
|
|||||||
$transaction_group = null
|
$transaction_group = null
|
||||||
): Money
|
): Money
|
||||||
{
|
{
|
||||||
|
$where = [];
|
||||||
$date = $this->formatPostDate($date);
|
|
||||||
|
|
||||||
$where = [
|
|
||||||
['post_date', '<=', $date]
|
|
||||||
];
|
|
||||||
|
|
||||||
if ($journal) {
|
if ($journal) {
|
||||||
$where['journal_id'] = $journal->id;
|
$where['journal_id'] = $journal->id;
|
||||||
}
|
}
|
||||||
|
|
||||||
if ($start_date) {
|
|
||||||
$start_date = $this->formatPostDate($start_date);
|
|
||||||
$where[] = ['post_date', '>=', $start_date];
|
|
||||||
}
|
|
||||||
|
|
||||||
if ($transaction_group) {
|
if ($transaction_group) {
|
||||||
$where['transaction_group'] = $transaction_group;
|
$where['transaction_group'] = $transaction_group;
|
||||||
}
|
}
|
||||||
|
|
||||||
$balance = $this
|
$query = JournalTransaction::where($where);
|
||||||
->findWhere($where, ['id', 'debit'])
|
$query = $query->whereDate('post_date', '<=', $date->toDateString());
|
||||||
->sum('debit') ?: 0;
|
|
||||||
|
if ($start_date) {
|
||||||
|
$query = $query->whereDate('post_date', '>=', $start_date->toDateString());
|
||||||
|
}
|
||||||
|
|
||||||
|
$balance = $query->sum('debit') ?: 0;
|
||||||
|
|
||||||
return new Money($balance);
|
return new Money($balance);
|
||||||
}
|
}
|
||||||
|
|||||||
10
composer.lock
generated
10
composer.lock
generated
@@ -2588,16 +2588,16 @@
|
|||||||
},
|
},
|
||||||
{
|
{
|
||||||
"name": "pragmarx/version",
|
"name": "pragmarx/version",
|
||||||
"version": "v0.2.6",
|
"version": "v0.2.7",
|
||||||
"source": {
|
"source": {
|
||||||
"type": "git",
|
"type": "git",
|
||||||
"url": "https://github.com/antonioribeiro/version.git",
|
"url": "https://github.com/antonioribeiro/version.git",
|
||||||
"reference": "73439723bf8f32534e0a79a07a914971b729ec1e"
|
"reference": "e48e1d193f55b0e0b8cd2980825485f572ff728f"
|
||||||
},
|
},
|
||||||
"dist": {
|
"dist": {
|
||||||
"type": "zip",
|
"type": "zip",
|
||||||
"url": "https://api.github.com/repos/antonioribeiro/version/zipball/73439723bf8f32534e0a79a07a914971b729ec1e",
|
"url": "https://api.github.com/repos/antonioribeiro/version/zipball/e48e1d193f55b0e0b8cd2980825485f572ff728f",
|
||||||
"reference": "73439723bf8f32534e0a79a07a914971b729ec1e",
|
"reference": "e48e1d193f55b0e0b8cd2980825485f572ff728f",
|
||||||
"shasum": ""
|
"shasum": ""
|
||||||
},
|
},
|
||||||
"require": {
|
"require": {
|
||||||
@@ -2645,7 +2645,7 @@
|
|||||||
"version",
|
"version",
|
||||||
"versioning"
|
"versioning"
|
||||||
],
|
],
|
||||||
"time": "2018-03-13T00:04:06+00:00"
|
"time": "2018-03-17T00:01:54+00:00"
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"name": "pragmarx/yaml",
|
"name": "pragmarx/yaml",
|
||||||
|
|||||||
@@ -479,7 +479,7 @@ class FinanceTest extends TestCase
|
|||||||
/**
|
/**
|
||||||
* @throws \Prettus\Validator\Exceptions\ValidatorException
|
* @throws \Prettus\Validator\Exceptions\ValidatorException
|
||||||
*/
|
*/
|
||||||
public function testJournalOperations()
|
public function testJournalOperations(): void
|
||||||
{
|
{
|
||||||
$journalRepo = app(JournalRepository::class);
|
$journalRepo = app(JournalRepository::class);
|
||||||
|
|
||||||
@@ -495,6 +495,7 @@ class FinanceTest extends TestCase
|
|||||||
|
|
||||||
$balance = $journalRepo->getBalance($journal);
|
$balance = $journalRepo->getBalance($journal);
|
||||||
$this->assertEquals(100, $balance->getValue());
|
$this->assertEquals(100, $balance->getValue());
|
||||||
|
$this->assertEquals(100, $journal->balance->getValue());
|
||||||
|
|
||||||
# add another transaction
|
# add another transaction
|
||||||
|
|
||||||
@@ -507,12 +508,9 @@ class FinanceTest extends TestCase
|
|||||||
|
|
||||||
$balance = $journalRepo->getBalance($journal);
|
$balance = $journalRepo->getBalance($journal);
|
||||||
$this->assertEquals(125, $balance->getValue());
|
$this->assertEquals(125, $balance->getValue());
|
||||||
|
|
||||||
# Get the total balance
|
|
||||||
$this->assertEquals(125, $journal->balance->getValue());
|
$this->assertEquals(125, $journal->balance->getValue());
|
||||||
|
|
||||||
# debit an amount
|
# debit an amount
|
||||||
|
|
||||||
$journalRepo->post(
|
$journalRepo->post(
|
||||||
$journal,
|
$journal,
|
||||||
null,
|
null,
|
||||||
@@ -522,7 +520,6 @@ class FinanceTest extends TestCase
|
|||||||
|
|
||||||
$balance = $journalRepo->getBalance($journal);
|
$balance = $journalRepo->getBalance($journal);
|
||||||
$this->assertEquals(100, $balance->getValue());
|
$this->assertEquals(100, $balance->getValue());
|
||||||
|
|
||||||
$this->assertEquals(100, $journal->balance->getValue());
|
$this->assertEquals(100, $journal->balance->getValue());
|
||||||
|
|
||||||
# find all transactions
|
# find all transactions
|
||||||
|
|||||||
Reference in New Issue
Block a user