58 lines
2.0 KiB
PHP
58 lines
2.0 KiB
PHP
<?php
|
|
|
|
namespace Modules\Accounting\Services;
|
|
|
|
use Illuminate\Support\Facades\DB;
|
|
use Modules\Accounting\Domain\FinancialPostingRequest;
|
|
use Modules\Accounting\Entities\AccountingAccount;
|
|
|
|
class OpeningBalanceService
|
|
{
|
|
public function __construct(protected FinancialPostingService $postingService) {}
|
|
|
|
public function post(int $businessId, int $userId, string $operationDate, array $lines, ?string $note = null)
|
|
{
|
|
$journalLines = [];
|
|
foreach ($lines as $line) {
|
|
if (empty($line['accounting_account_id']) || empty($line['amount']) || empty($line['type'])) {
|
|
continue;
|
|
}
|
|
$journalLines[] = [
|
|
'accounting_account_id' => (int) $line['accounting_account_id'],
|
|
'amount' => (float) $line['amount'],
|
|
'type' => $line['type'],
|
|
'sub_type' => 'opening_balance',
|
|
];
|
|
}
|
|
|
|
if (count($journalLines) < 2) {
|
|
throw new \InvalidArgumentException('Opening balance requires at least two lines.');
|
|
}
|
|
|
|
return $this->postingService->post(new FinancialPostingRequest(
|
|
businessId: $businessId,
|
|
userId: $userId,
|
|
sourceType: 'opening_balance',
|
|
sourceId: $operationDate,
|
|
note: $note ?? 'Opening balance entry',
|
|
lines: $journalLines,
|
|
operationDate: $operationDate,
|
|
mappingType: 'journal_entry',
|
|
), allowDuplicate: false);
|
|
}
|
|
|
|
public function accountsWithoutActivity(int $businessId): array
|
|
{
|
|
return AccountingAccount::where('business_id', $businessId)
|
|
->where('status', 'active')
|
|
->whereNotExists(function ($q) {
|
|
$q->select(DB::raw(1))
|
|
->from('accounting_accounts_transactions as aat')
|
|
->whereColumn('aat.accounting_account_id', 'accounting_accounts.id');
|
|
})
|
|
->orderBy('name')
|
|
->pluck('name', 'id')
|
|
->all();
|
|
}
|
|
}
|