Implement events for cron expenses; add processing of daily/monthly expenses #136
This commit is contained in:
141
app/Services/Finance/RecurringFinanceService.php
Normal file
141
app/Services/Finance/RecurringFinanceService.php
Normal file
@@ -0,0 +1,141 @@
|
||||
<?php
|
||||
|
||||
namespace App\Services\Finance;
|
||||
|
||||
use App\Models\Airline;
|
||||
use App\Models\Enums\ExpenseType;
|
||||
use App\Models\Expense;
|
||||
use App\Models\JournalTransaction;
|
||||
use App\Repositories\JournalRepository;
|
||||
use App\Services\BaseService;
|
||||
use App\Support\Money;
|
||||
use Log;
|
||||
|
||||
/**
|
||||
* Process all of the daily expenses and charge them
|
||||
* @package App\Services\Finance
|
||||
*/
|
||||
class RecurringFinanceService extends BaseService
|
||||
{
|
||||
private $journalRepo;
|
||||
|
||||
public function __construct(JournalRepository $journalRepo)
|
||||
{
|
||||
$this->journalRepo = $journalRepo;
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine the journal to charge to, otherwise, it's charged
|
||||
* to every airline journal
|
||||
* @param Expense $expense
|
||||
* @return \Generator
|
||||
*/
|
||||
protected function findJournals(Expense $expense)
|
||||
{
|
||||
if($expense->airline_id) {
|
||||
$airline = Airline::find($expense->airline_id)->first(['id', 'icao']);
|
||||
Log::info('Charging to ' . $airline->icao);
|
||||
yield $airline->journal;
|
||||
} else {
|
||||
$airlines = Airline::all(['id', 'icao']);
|
||||
foreach($airlines as $airline) {
|
||||
Log::info('Charging to ' . $airline->icao);
|
||||
yield $airline->journal;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the name of the transaction group from the expense
|
||||
* @param Expense $expense
|
||||
* @return array
|
||||
*/
|
||||
protected function getMemoAndGroup(Expense $expense): array
|
||||
{
|
||||
$klass = 'Expense';
|
||||
if ($expense->ref_class) {
|
||||
$ref = explode('\\', $expense->ref_class);
|
||||
$klass = end($ref);
|
||||
$obj = $expense->getReference();
|
||||
}
|
||||
|
||||
if ($klass === 'Airport') {
|
||||
$memo = "Airport Expense: {$expense->name} ({$expense->ref_class_id})";
|
||||
$transaction_group = "Airport: {$expense->ref_class_id}";
|
||||
} elseif ($klass === 'Subfleet') {
|
||||
$memo = "Subfleet Expense: {$expense->name}";
|
||||
$transaction_group = "Subfleet: {$expense->name}";
|
||||
} elseif ($klass === 'Aircraft') {
|
||||
$memo = "Aircraft Expense: {$expense->name} ({$obj->name})";
|
||||
$transaction_group = "Aircraft: {$expense->name} ({$obj->name}-{$obj->registration})";
|
||||
} else {
|
||||
$memo = "Expense: {$expense->name}";
|
||||
$transaction_group = "Expense: {$expense->name}";
|
||||
}
|
||||
|
||||
return [$memo, $transaction_group];
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Run all of the daily expense/financials
|
||||
* @param int $type
|
||||
* @throws \UnexpectedValueException
|
||||
* @throws \InvalidArgumentException
|
||||
* @throws \Prettus\Validator\Exceptions\ValidatorException
|
||||
*/
|
||||
public function processExpenses($type=ExpenseType::DAILY): void
|
||||
{
|
||||
$expenses = Expense::where(['type' => $type])->get();
|
||||
|
||||
$tag = 'expense_recurring';
|
||||
if($type === ExpenseType::DAILY) {
|
||||
$tag = 'expenses_daily';
|
||||
} elseif ($type === ExpenseType::MONTHLY) {
|
||||
$tag === 'expenses_monthly';
|
||||
}
|
||||
|
||||
/**
|
||||
* @var $expenses Expense[]
|
||||
*/
|
||||
foreach ($expenses as $expense) {
|
||||
|
||||
# Apply the expenses to the appropriate journals
|
||||
$journals = $this->findJournals($expense);
|
||||
foreach($journals as $journal) {
|
||||
|
||||
$amount = $expense->amount;
|
||||
|
||||
# Has this expense already been charged? Check
|
||||
# against this specific journal, on today
|
||||
$w = [
|
||||
'journal_id' => $journal->id,
|
||||
'ref_class' => Expense::class,
|
||||
'ref_class_id' => $expense->id,
|
||||
'post_date' => \Carbon::now('UTC')->format('Y-m-d'),
|
||||
];
|
||||
|
||||
$found = JournalTransaction::where($w)->count(['id']);
|
||||
if($found > 0) {
|
||||
Log::info('Expense "'.$expense->name.'" already charged for today, skipping');
|
||||
continue;
|
||||
}
|
||||
|
||||
[$memo, $ta_group] = $this->getMemoAndGroup($expense);
|
||||
|
||||
$this->journalRepo->post(
|
||||
$journal,
|
||||
null,
|
||||
Money::createFromAmount($amount),
|
||||
$expense,
|
||||
$memo,
|
||||
null,
|
||||
$ta_group,
|
||||
$tag
|
||||
);
|
||||
|
||||
Log::info('Expense memo: "'.$memo.'"; group: "'. $ta_group. '" charged!');
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user