Skip to content

Commit

Permalink
Changelog
Browse files Browse the repository at this point in the history
- Fixed: owed amount for customer not correctly computed
- Fixed: add refund status to order completely refunded
  • Loading branch information
Blair2004 committed Aug 6, 2021
1 parent c9a10af commit e09eb20
Show file tree
Hide file tree
Showing 5 changed files with 126 additions and 50 deletions.
77 changes: 44 additions & 33 deletions app/Jobs/ComputeCustomerAccountJob.php
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@
use App\Events\OrderAfterCreatedEvent;
use App\Events\OrderAfterPaymentCreatedEvent;
use App\Events\OrderAfterRefundedEvent;
use App\Events\OrderAfterUpdatedEvent;
use App\Events\OrderBeforeDeleteEvent;
use App\Models\Order;
use App\Models\OrderPayment;
Expand All @@ -19,16 +20,24 @@ class ComputeCustomerAccountJob implements ShouldQueue
{
use Dispatchable, InteractsWithQueue, Queueable, SerializesModels;

/**
* @var CustomerService
*/
protected $customerService;

public $event;

/**
* Create a new job instance.
*
* @return void
*/
public function __construct( $event )
{
$this->event = $event;
public function __construct(
$event,
CustomerService $customerService
) {
$this->event = $event;
$this->customerService = $customerService;
}

/**
Expand All @@ -38,61 +47,63 @@ public function __construct( $event )
*/
public function handle()
{
if ( $this->event instanceof OrderBeforeDeleteEvent ) {
$this->handleDeletion( $this->event );
} else if ( $this->event instanceof OrderAfterRefundedEvent ) {
$this->reduceCustomerPurchases( $this->event );
} else if ( $this->event instanceof OrderAfterCreatedEvent ) {
$this->computeCustomerOwed( $this->event );
$this->computeCustomerRewards( $this->event );
if ($this->event instanceof OrderBeforeDeleteEvent) {
$this->handleDeletion($this->event);
} else if ($this->event instanceof OrderAfterRefundedEvent) {
$this->reduceCustomerPurchases($this->event);
} else if (
$this->event instanceof OrderAfterCreatedEvent ||
$this->event instanceof OrderAfterUpdatedEvent
) {
$this->computeCustomerOwed($this->event);
$this->computeCustomerRewards($this->event);
}
}

private function computeCustomerOwed( OrderAfterCreatedEvent $event )
/**
* We'll make sure to update the customer owed amount
* when even he's involved on a transaction.
*/
private function computeCustomerOwed( $event )
{
$event->order->customer->owed_amount += ns()->currency
->define( $event->order->total )
->subtractBy( $event->order->tendered )
->getRaw();

$event->order->customer->save();
$this->customerService->updateCustomerOwedAmount($event->order->customer);
}

private function computeCustomerRewards( OrderAfterCreatedEvent $event )
private function computeCustomerRewards( $event )
{
if ( $event->order->payment_status === Order::PAYMENT_PAID ) {
if ($event->order->payment_status === Order::PAYMENT_PAID) {
/**
* @var CustomerService
*/
$customerService = app()->make( CustomerService::class );
$customerService->computeReward(
$event->order,
$event->order->customer
$customerService = app()->make(CustomerService::class);

$customerService->computeReward(
$event->order,
$event->order->customer
);
}
}

private function reduceCustomerPurchases( OrderAfterRefundedEvent $event )
private function reduceCustomerPurchases(OrderAfterRefundedEvent $event)
{
$event->order->customer->purchases_amount = $event->order->customer->purchases_amount - $event->orderRefund->total;
$event->order->customer->save();
}

private function handleDeletion( OrderBeforeDeleteEvent $event )
private function handleDeletion(OrderBeforeDeleteEvent $event)
{
switch( $event->order->payment_status ) {
case 'paid':
switch ($event->order->payment_status) {
case 'paid':
$event->order->customer->purchases_amount -= $event->order->total;
break;
case 'partially_paid':
break;
case 'partially_paid':
$event->order->customer->purchases_amount -= $event->order->tendered;
break;
break;
default:
$event->order->customer->owed_amount -= $event->order->total;
break;
break;
}

$event->order->customer->save();
}
}
41 changes: 38 additions & 3 deletions app/Listeners/OrderEventsSubscriber.php
Original file line number Diff line number Diff line change
Expand Up @@ -67,6 +67,27 @@ public function subscribe( $events )
[ OrderEventsSubscriber::class, 'handleOrderUpdate' ]
);

/**
* all events likely to affect
* the customer account.
*/
$events->listen(
OrderAfterCreatedEvent::class,
[ OrderEventsSubscriber::class, 'handleCustomerUpdates' ]
);
$events->listen(
OrderAfterUpdatedEvent::class,
[ OrderEventsSubscriber::class, 'handleCustomerUpdates' ]
);
$events->listen(
OrderBeforeDeleteEvent::class,
[ OrderEventsSubscriber::class, 'handleCustomerUpdates' ]
);
$events->listen(
OrderAfterRefundedEvent::class,
[ OrderEventsSubscriber::class, 'handleCustomerUpdates' ]
);

$events->listen(
OrderAfterCreatedEvent::class,
[ OrderEventsSubscriber::class, 'handleInstalmentPayment' ]
Expand Down Expand Up @@ -111,13 +132,27 @@ public function handleOrderUpdate( $event )
ComputeDayReportJob::dispatch()
->delay( now()->addSecond(5) );

ComputeCustomerAccountJob::dispatch( $event )
->delay( now()->addSecond(5) );

ComputeCashierSalesJob::dispatch( $event )
->delay( now()->addSecond(10) );
}

public function handleCustomerUpdates( $event )
{
if (
$event instanceof OrderAfterCreatedEvent ||
$event instanceof OrderAfterUpdatedEvent ||
$event instanceof OrderBeforeDeleteEvent ||
$event instanceof OrderAfterRefundedEvent

) {
ComputeCustomerAccountJob::dispatch(
$event,
app()->make( CustomerService::class )
)
->delay( now()->addSecond(5) );
}
}

/**
* When a sales is made on a specific order
* we to increase the customers purchases
Expand Down
22 changes: 22 additions & 0 deletions app/Services/CustomerService.php
Original file line number Diff line number Diff line change
Expand Up @@ -510,6 +510,28 @@ public function deleteRelatedCustomerCoupon( Coupon $coupon )
});
}

/**
* Will refresh the owed amount
* for the provided customer
*/
public function updateCustomerOwedAmount( Customer $customer )
{
$unpaid = Order::whereIn( 'payment_status', [
Order::PAYMENT_UNPAID
])->sum( 'total' );

/**
* Change here will be negative, so we
* want to be an absolute value.
*/
$change = abs( Order::whereIn( 'payment_status', [
Order::PAYMENT_PARTIALLY
])->sum( 'change' ) );

$customer->owed_amount = ns()->currency->getRaw( $unpaid + $change );
$customer->save();
}

/**
* Create customer group using
* provided fields
Expand Down
4 changes: 0 additions & 4 deletions app/Services/MenuService.php
Original file line number Diff line number Diff line change
Expand Up @@ -162,10 +162,6 @@ public function buildMenus()
'permissions' => [ 'nexopos.create.expenses-categories' ],
'href' => ns()->url( '/dashboard/expenses/categories/create' )
],
'cash-in' => [
'label' => __( 'Cash Flow' ),
'href' => ns()->url( '/dashboard/banking/cash-flow' )
]
]
],
'inventory' => [
Expand Down
32 changes: 22 additions & 10 deletions app/Services/OrdersService.php
Original file line number Diff line number Diff line change
Expand Up @@ -1816,6 +1816,10 @@ public function refreshOrder(Order $order)
return floatval($product->total_price);
})->sum();

$productTotalQuatity = $products->map( function( $product) {
return floatval( $product->quantity );
})->sum();

$productGrossTotal = $products->map(function ($product) {
return floatval($product->total_gross_price);
})->sum();
Expand Down Expand Up @@ -1848,16 +1852,24 @@ public function refreshOrder(Order $order)
$refunds = $order->refund;
$totalRefunds = $refunds->map( fn( $refund ) => $refund->total )->sum();

if ( ( float ) $order->total == 0 && $totalRefunds > 0 ) {
$order->payment_status = Order::PAYMENT_REFUNDED;
} else if ( $order->total > 0 && $totalRefunds > 0 ) {
$order->payment_status = Order::PAYMENT_PARTIALLY_REFUNDED;
} else if ( $order->tendered >= $order->total && $order->total > 0 ) {
$order->payment_status = Order::PAYMENT_PAID;
} else if ( ( float ) $order->tendered < ( float ) $order->total ) {
$order->payment_status = Order::PAYMENT_PARTIALLY;
} else if ( $order->total == 0 && $totalRefunds == 0 ) {
$order->payment_status = Order::PAYMENT_UNPAID;
/**
* We believe if the product total is greater
* than "0", then probably the order hasn't been paid yet.
*/
if ( $productTotal ) {
if ( ( float ) $order->total == 0 && $totalRefunds > 0 ) {
$order->payment_status = Order::PAYMENT_REFUNDED;
} else if ( $order->total > 0 && $totalRefunds > 0 ) {
$order->payment_status = Order::PAYMENT_PARTIALLY_REFUNDED;
} else if ( $order->tendered >= $order->total && $order->total > 0 ) {
$order->payment_status = Order::PAYMENT_PAID;
} else if ( ( float ) $order->tendered < ( float ) $order->total ) {
$order->payment_status = Order::PAYMENT_PARTIALLY;
} else if ( $order->total == 0 && $totalRefunds == 0 ) {
$order->payment_status = Order::PAYMENT_UNPAID;
}
} else if ( $productTotal == 0 && $productTotalQuatity == 0 ) {
$order->payment_status = Order::PAYMENT_REFUNDED;
}

$order->save();
Expand Down

0 comments on commit e09eb20

Please sign in to comment.