diff --git a/app/Jobs/Ledger/ClientLedgerBalanceUpdate.php b/app/Jobs/Ledger/ClientLedgerBalanceUpdate.php index 29d780bfabb8..639fd2be3370 100644 --- a/app/Jobs/Ledger/ClientLedgerBalanceUpdate.php +++ b/app/Jobs/Ledger/ClientLedgerBalanceUpdate.php @@ -25,8 +25,13 @@ use Illuminate\Queue\SerializesModels; class ClientLedgerBalanceUpdate implements ShouldQueue { use Dispatchable, InteractsWithQueue, Queueable, SerializesModels; + public $tries = 1; + public $deleteWhenMissingModels = true; + + private ?CompanyLedger $next_balance_record; + public function __construct(public Company $company, public Client $client) { } @@ -39,34 +44,78 @@ class ClientLedgerBalanceUpdate implements ShouldQueue */ public function handle() :void { - // nlog("Updating company ledger for client ". $this->client->id); + $uuid = \Illuminate\Support\Str::uuid(); + + nlog("Updating company ledger for client {$this->client->id} {$uuid}"); MultiDB::setDb($this->company->db); - CompanyLedger::query()->where('balance', 0)->where('client_id', $this->client->id)->orderBy('updated_at', 'ASC')->cursor()->each(function ($company_ledger) { - if ($company_ledger->balance == 0) { - $last_record = CompanyLedger::query()->where('client_id', $company_ledger->client_id) - ->where('company_id', $company_ledger->company_id) - ->where('balance', '!=', 0) - ->orderBy('id', 'DESC') - ->first(); + $dupes = CompanyLedger::query() + ->where('client_id', $this->client->id) + ->where('balance', 0) + ->where('hash', '<>', '') + ->groupBy(['adjustment','hash']) + ->havingRaw('COUNT(*) > 1') + ->pluck('id'); - if (! $last_record) { - $last_record = CompanyLedger::query()->where('client_id', $company_ledger->client_id) - ->where('company_id', $company_ledger->company_id) - ->orderBy('id', 'DESC') - ->first(); - } - } + // CompanyLedger::query()->whereIn('id', $dupes)->delete(); + + $dupes = CompanyLedger::query() + ->where('client_id', $this->client->id) + ->where('balance', 0) + ->where('hash', '<>', '') + ->groupBy(['adjustment','hash']) + ->havingRaw('COUNT(*) > 1') + ->pluck('id'); + + // CompanyLedger::query()->whereIn('id', $dupes)->delete(); + + CompanyLedger::query() + ->where('balance', 0) + ->where('client_id', $this->client->id) + ->orderBy('id', 'ASC') + ->get() + ->each(function ($company_ledger) { + + $parent_ledger = CompanyLedger::query() + ->where('id', '<', $company_ledger->id) + ->where('client_id', $company_ledger->client_id) + ->where('company_id', $company_ledger->company_id) + ->where('balance', '!=', 0) + ->orderBy('id', 'DESC') + ->first(); + + // if ($company_ledger->balance == 0) { + + // $last_record = CompanyLedger::query() + // ->where('client_id', $company_ledger->client_id) + // ->where('company_id', $company_ledger->company_id) + // ->where('balance', '!=', 0) + // ->orderBy('id', 'DESC') + // ->first(); + + // if (! $last_record) { + // $last_record = CompanyLedger::query() + // ->where('client_id', $company_ledger->client_id) + // ->where('company_id', $company_ledger->company_id) + // ->orderBy('id', 'DESC') + // ->first(); + // } + + // } + + // $company_ledger->balance = $last_record->balance + $company_ledger->adjustment; + $company_ledger->balance = ($parent_ledger ? $parent_ledger->balance : 0) + $company_ledger->adjustment; + $company_ledger->save(); - $company_ledger->balance = $last_record->balance + $company_ledger->adjustment; - $company_ledger->save(); }); - } + nlog("finished job {$uuid}"); + } public function middleware() { + nlog("middle ware {$this->client->id}"); return [(new WithoutOverlapping($this->client->id))->dontRelease()]; } } diff --git a/app/Jobs/Ledger/UpdateLedger.php b/app/Jobs/Ledger/UpdateLedger.php index 08d81c5785e2..48605c75a766 100644 --- a/app/Jobs/Ledger/UpdateLedger.php +++ b/app/Jobs/Ledger/UpdateLedger.php @@ -20,6 +20,7 @@ use Illuminate\Contracts\Queue\ShouldQueue; use Illuminate\Foundation\Bus\Dispatchable; use Illuminate\Queue\Middleware\WithoutOverlapping; +//@deprecated class UpdateLedger implements ShouldQueue { use Dispatchable, InteractsWithQueue, Queueable, SerializesModels; diff --git a/app/Repositories/BaseRepository.php b/app/Repositories/BaseRepository.php index 6e7b3b471a96..44ddd501aab6 100644 --- a/app/Repositories/BaseRepository.php +++ b/app/Repositories/BaseRepository.php @@ -290,10 +290,10 @@ class BaseRepository /* Perform model specific tasks */ if ($model instanceof Invoice) { - if ($model->status_id != Invoice::STATUS_DRAFT) { + if ($model->status_id != Invoice::STATUS_DRAFT && ($state['starting_amount'] != $state['finished_amount'])) { $model->service()->updateStatus()->save(); $model->client->service()->calculateBalance(); - $model->ledger()->mutateInvoiceBalance($state['starting_amount'], "Update adjustment for invoice {$model->number}"); + $model->ledger()->updateInvoiceBalance(($state['finished_amount'] - $state['starting_amount']), "Update adjustment for invoice {$model->number}"); } if (! $model->design_id) { diff --git a/app/Services/Invoice/HandleCancellation.php b/app/Services/Invoice/HandleCancellation.php index 85b2eee73168..206d1391e0bc 100644 --- a/app/Services/Invoice/HandleCancellation.php +++ b/app/Services/Invoice/HandleCancellation.php @@ -66,10 +66,7 @@ class HandleCancellation extends AbstractService $this->invoice->ledger()->updateInvoiceBalance($adjustment, "Invoice {$this->invoice->number} reversal"); - // $this->invoice->ledger()->mutateInvoiceBalance($this->invoice->amount, "Invoice {$this->invoice->number} reversal"); - - - $this->invoice->fresh(); + $this->invoice = $this->invoice->fresh(); /* Reverse the invoice status and balance */ $this->invoice->balance += $adjustment; diff --git a/app/Services/Invoice/HandleRestore.php b/app/Services/Invoice/HandleRestore.php index 823301fb9ce3..cc251bdb97a4 100644 --- a/app/Services/Invoice/HandleRestore.php +++ b/app/Services/Invoice/HandleRestore.php @@ -51,8 +51,6 @@ class HandleRestore extends AbstractService //adjust ledger balance $this->invoice->ledger()->updateInvoiceBalance($this->invoice->balance, "Restored invoice {$this->invoice->number}")->save(); - // $this->invoice->ledger()->mutateInvoiceBalance($this->invoice->amount, "Restored invoice {$this->invoice->number}"); - //@todo $this->invoice->client ->service() diff --git a/app/Services/Invoice/HandleReversal.php b/app/Services/Invoice/HandleReversal.php index 4c3076fd6204..2b1410950e12 100644 --- a/app/Services/Invoice/HandleReversal.php +++ b/app/Services/Invoice/HandleReversal.php @@ -68,7 +68,6 @@ class HandleReversal extends AbstractService /* Set invoice balance to 0 */ if ($this->invoice->balance != 0) { $this->invoice->ledger()->updateInvoiceBalance($balance_remaining * -1, $notes)->save(); - // $this->invoice->ledger()->mutateInvoiceBalance($this->invoice->amount, $notes); } $this->invoice->balance = 0; diff --git a/app/Services/Invoice/InvoiceService.php b/app/Services/Invoice/InvoiceService.php index 8e1d2d8138da..e435263879b1 100644 --- a/app/Services/Invoice/InvoiceService.php +++ b/app/Services/Invoice/InvoiceService.php @@ -462,7 +462,6 @@ class InvoiceService ->ledger() ->updateInvoiceBalance($adjustment * -1, 'Adjustment for removing gateway fee'); - // $this->invoice->ledger()->mutateInvoiceBalance($this->invoice->amount, "Adjustment for removing gateway fee {$adjustment} Invoice {$this->invoice->number}"); $this->invoice->client->service()->calculateBalance(); } diff --git a/app/Services/Invoice/MarkSent.php b/app/Services/Invoice/MarkSent.php index b9541b04b4cf..dc6af4a65659 100644 --- a/app/Services/Invoice/MarkSent.php +++ b/app/Services/Invoice/MarkSent.php @@ -45,10 +45,7 @@ class MarkSent extends AbstractService ->ledger() ->updateInvoiceBalance($adjustment, "Invoice {$this->invoice->number} marked as sent."); - -// $this->invoice->ledger()->mutateInvoiceBalance($this->invoice->amount, "Invoice {$this->invoice->number} marked as sent => {$this->invoice->amount}"); -$this->invoice->client->service()->calculateBalance(); - + $this->invoice->client->service()->calculateBalance(); /* Perform additional actions on invoice */ $this->invoice diff --git a/app/Services/Ledger/LedgerService.php b/app/Services/Ledger/LedgerService.php index 376b8823d667..97715350a2c9 100644 --- a/app/Services/Ledger/LedgerService.php +++ b/app/Services/Ledger/LedgerService.php @@ -11,10 +11,11 @@ namespace App\Services\Ledger; +use App\Models\Activity; +use App\Models\CompanyLedger; +use App\Jobs\Ledger\UpdateLedger; use App\Factory\CompanyLedgerFactory; use App\Jobs\Ledger\ClientLedgerBalanceUpdate; -use App\Jobs\Ledger\UpdateLedger; -use App\Models\Activity; class LedgerService { @@ -25,32 +26,43 @@ class LedgerService $this->entity = $entity; } - public function mutateInvoiceBalance(float $start_amount, string $notes ='') - { - $company_ledger = CompanyLedgerFactory::create($this->entity->company_id, $this->entity->user_id); - $company_ledger->client_id = $this->entity->client_id; - $company_ledger->adjustment = 0; - $company_ledger->notes = $notes; - $company_ledger->activity_id = Activity::UPDATE_INVOICE; - $company_ledger->save(); - - $this->entity->company_ledger()->save($company_ledger); - - UpdateLedger::dispatch($company_ledger->id, $start_amount, $this->entity->company->company_key, $this->entity->company->db); - } - public function updateInvoiceBalance($adjustment, $notes = '') { + + if($adjustment == 0) + return $this; + + // $timestamp = \Carbon\Carbon::createFromTimestamp($this->entity->updated_at)->format('ymdhhmmssSS'); + // $hash = sha1($adjustment.$notes.$this->entity->status_id.$this->entity->client_id.$this->entity->amount.$this->entity->balance.$this->entity->company_id.Activity::UPDATE_INVOICE); + // $hash = sha1($hash); + // $hash = sha1("{$this->entity->amount}.{$this->entity->balance}"); + $hash = "{$this->entity->amount}.{$this->entity->balance}"; + + $exists = CompanyLedger::query() + ->where('client_id', $this->entity->client_id) + ->where('company_id', $this->entity->company_id) + ->where('activity_id', Activity::UPDATE_INVOICE) + ->where('adjustment', $adjustment) + ->where('hash', $hash) + ->where('notes', $notes) + ->where('created_at', '>=', now()->subSeconds(1)) + ->exists(); + + if($exists) { + return $this; + } + $company_ledger = CompanyLedgerFactory::create($this->entity->company_id, $this->entity->user_id); $company_ledger->client_id = $this->entity->client_id; $company_ledger->adjustment = $adjustment; $company_ledger->notes = $notes; + $company_ledger->hash = $hash; $company_ledger->activity_id = Activity::UPDATE_INVOICE; $company_ledger->save(); $this->entity->company_ledger()->save($company_ledger); - ClientLedgerBalanceUpdate::dispatch($this->entity->company, $this->entity->client)->delay(rand(3, 13)); + ClientLedgerBalanceUpdate::dispatch($this->entity->company, $this->entity->client)->delay(rand(4, 7)); return $this; } @@ -66,7 +78,7 @@ class LedgerService $this->entity->company_ledger()->save($company_ledger); - ClientLedgerBalanceUpdate::dispatch($this->entity->company, $this->entity->client)->delay(rand(3, 13)); + ClientLedgerBalanceUpdate::dispatch($this->entity->company, $this->entity->client)->delay(rand(1, 3)); return $this; } @@ -82,7 +94,7 @@ class LedgerService $this->entity->company_ledger()->save($company_ledger); - ClientLedgerBalanceUpdate::dispatch($this->entity->company, $this->entity->client)->delay(rand(3, 13)); + ClientLedgerBalanceUpdate::dispatch($this->entity->company, $this->entity->client)->delay(rand(1, 3)); return $this; } diff --git a/app/Services/Payment/DeletePayment.php b/app/Services/Payment/DeletePayment.php index 1d7295b43661..c54ef2812646 100644 --- a/app/Services/Payment/DeletePayment.php +++ b/app/Services/Payment/DeletePayment.php @@ -101,9 +101,6 @@ class DeletePayment ->updateInvoiceBalance($net_deletable, "Adjusting invoice {$paymentable_invoice->number} due to deletion of Payment {$this->payment->number}") ->save(); - // $paymentable_invoice->ledger() - // ->mutateInvoiceBalance($paymentable_invoice->amount, "Adjusting invoice {$paymentable_invoice->number} due to deletion of Payment {$this->payment->number}"); - //@todo refactor $this->payment ->client diff --git a/app/Services/Payment/RefundPayment.php b/app/Services/Payment/RefundPayment.php index b12210375d4f..b06833eeff0d 100644 --- a/app/Services/Payment/RefundPayment.php +++ b/app/Services/Payment/RefundPayment.php @@ -294,10 +294,6 @@ class RefundPayment ->updateInvoiceBalance($refunded_invoice['amount'], "Refund of payment # {$this->payment->number}") ->save(); - // $invoice->ledger() - // ->mutateInvoiceBalance($invoice->amount, "Refund of payment # {$this->payment->number}"); - - if ($invoice->amount == $invoice->balance) { $invoice->service()->setStatus(Invoice::STATUS_SENT); } else {