Teren-app/app/Services/Import/Handlers/AccountHandler.php
Simon Pocrnjič dea7432deb changes
2025-12-26 22:39:58 +01:00

158 lines
5.0 KiB
PHP

<?php
namespace App\Services\Import\Handlers;
use App\Models\Account;
use App\Models\Import;
use App\Services\Import\BaseEntityHandler;
class AccountHandler extends BaseEntityHandler
{
public function getEntityClass(): string
{
return Account::class;
}
public function resolve(array $mapped, array $context = []): mixed
{
$reference = $mapped['reference'] ?? null;
$contractId = $mapped['contract_id'] ?? $context['contract']?->entity?->id ?? null;
if (! $reference || ! $contractId) {
return null;
}
return Account::where('contract_id', $contractId)
->where('reference', $reference)
->first();
}
public function process(Import $import, array $mapped, array $raw, array $context = []): array
{
// Ensure contract context
if (! isset($context['contract'])) {
return [
'action' => 'skipped',
'message' => 'Account requires contract context',
];
}
$contractId = $context['contract']->entity->id;
$mapped['contract_id'] = $contractId;
$existing = $this->resolve($mapped, $context);
if ($existing) {
// Track old balance for activity creation
$oldBalance = (float) ($existing->balance_amount ?? 0);
$payload = $this->buildPayload($mapped, $existing);
$appliedFields = $this->trackAppliedFields($existing, $payload);
if (empty($appliedFields)) {
return [
'action' => 'skipped',
'entity' => $existing,
'message' => 'No changes detected',
];
}
$existing->fill($payload);
$existing->save();
// Create activity if balance changed and tracking is enabled
if ($this->getOption('track_balance_changes', true) && array_key_exists('balance_amount', $appliedFields)) {
$this->createBalanceChangeActivity($existing, $oldBalance, $import, $context);
}
return [
'action' => 'updated',
'entity' => $existing,
'applied_fields' => $appliedFields,
];
}
// Create new account
$account = new Account;
$payload = $this->buildPayload($mapped, $account);
$account->fill($payload);
$account->save();
return [
'action' => 'inserted',
'entity' => $account,
'applied_fields' => array_keys($payload),
];
}
protected function buildPayload(array $mapped, $model): array
{
$payload = [];
$fieldMap = [
'contract_id' => 'contract_id',
'reference' => 'reference',
'title' => 'title',
'description' => 'description',
'balance_amount' => 'balance_amount',
'currency' => 'currency',
];
foreach ($fieldMap as $source => $target) {
if (array_key_exists($source, $mapped)) {
$payload[$target] = $mapped[$source];
}
}
return $payload;
}
/**
* Create activity when account balance changes.
*/
protected function createBalanceChangeActivity(Account $account, float $oldBalance, Import $import, array $context): void
{
if (! $this->getOption('create_activity_on_balance_change', true)) {
return;
}
try {
$newBalance = (float) ($account->balance_amount ?? 0);
// Skip if balance didn't actually change
if ($newBalance === $oldBalance) {
return;
}
$currency = \App\Models\PaymentSetting::first()?->default_currency ?? 'EUR';
$beforeStr = number_format($oldBalance, 2, ',', '.').' '.$currency;
$afterStr = number_format($newBalance, 2, ',', '.').' '.$currency;
$note = 'Sprememba stanja (Stanje pred: '.$beforeStr.', Stanje po: '.$afterStr.'; Izvor: sprememba)';
// Get client_case_id
$clientCaseId = $account->contract?->client_case_id;
if ($clientCaseId) {
// Use action_id from import meta if available
$metaActionId = (int) ($import->meta['action_id'] ?? 0);
if ($metaActionId > 0) {
\App\Models\Activity::create([
'due_date' => null,
'amount' => null,
'note' => $note,
'action_id' => $metaActionId,
'decision_id' => $import->meta['decision_id'] ?? null,
'client_case_id' => $clientCaseId,
'contract_id' => $account->contract_id,
]);
}
}
} catch (\Throwable $e) {
\Log::warning('Failed to create balance change activity', [
'account_id' => $account->id,
'error' => $e->getMessage(),
]);
}
}
}