From 37a56c6c49edd63c5a15f043a06b08f30b04ce6d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?D=2E=20Nagy=20Gerg=C5=91?= Date: Wed, 3 Jan 2024 13:43:13 +0100 Subject: [PATCH] wip --- database/factories/OrderFactory.php | 2 +- src/Events/CheckoutProcessed.php | 2 -- src/Gateway/CashDriver.php | 9 ++++++-- src/Gateway/Driver.php | 15 +++++++++++-- src/Gateway/TransferDriver.php | 16 ++----------- src/Listeners/PlaceOrder.php | 2 +- src/Models/Cart.php | 26 ++++++++++++++++----- tests/Cart/ManagerTest.php | 2 +- tests/Gateway/ManagerTest.php | 35 +++++++++++++---------------- 9 files changed, 61 insertions(+), 48 deletions(-) diff --git a/database/factories/OrderFactory.php b/database/factories/OrderFactory.php index 33538efd..cd9d8ca5 100644 --- a/database/factories/OrderFactory.php +++ b/database/factories/OrderFactory.php @@ -20,7 +20,7 @@ class OrderFactory extends Factory public function definition(): array { return [ - 'discount' => mt_rand(10, 1000), + 'discount' => 0, 'currency' => 'usd', ]; } diff --git a/src/Events/CheckoutProcessed.php b/src/Events/CheckoutProcessed.php index eb6843e7..3ccd8ba0 100644 --- a/src/Events/CheckoutProcessed.php +++ b/src/Events/CheckoutProcessed.php @@ -4,12 +4,10 @@ use Cone\Bazar\Models\Order; use Illuminate\Foundation\Events\Dispatchable; -use Illuminate\Queue\SerializesModels; class CheckoutProcessed { use Dispatchable; - use SerializesModels; /** * The order instance. diff --git a/src/Gateway/CashDriver.php b/src/Gateway/CashDriver.php index e5f52e0c..031df4a0 100644 --- a/src/Gateway/CashDriver.php +++ b/src/Gateway/CashDriver.php @@ -9,12 +9,17 @@ class CashDriver extends Driver { + /** + * The driver name. + */ + protected string $name = 'cash'; + /** * Process the payment. */ public function pay(Order $order, float $amount = null, array $attributes = []): Transaction { - $transaction = $order->pay($amount, 'cash', array_merge($attributes, [ + $transaction = parent::pay($order, $amount, array_merge($attributes, [ 'completed_at' => time(), ])); @@ -28,7 +33,7 @@ public function pay(Order $order, float $amount = null, array $attributes = []): */ public function refund(Order $order, float $amount = null, array $attributes = []): Transaction { - $transaction = $order->refund($amount, 'cash', array_merge($attributes, [ + $transaction = parent::refund($order, $amount, array_merge($attributes, [ 'completed_at' => time(), ])); diff --git a/src/Gateway/Driver.php b/src/Gateway/Driver.php index 1a292e90..0db30781 100644 --- a/src/Gateway/Driver.php +++ b/src/Gateway/Driver.php @@ -10,15 +10,26 @@ abstract class Driver extends BaseDriver { + /** + * The driver name. + */ + protected string $name; + /** * Process the payment. */ - abstract public function pay(Order $order, float $amount = null, array $attributes = []): Transaction; + public function pay(Order $order, float $amount = null, array $attributes = []): Transaction + { + return $order->pay($amount, $this->name, $attributes); + } /** * Process the refund. */ - abstract public function refund(Order $order, float $amount = null, array $attributes = []): Transaction; + public function refund(Order $order, float $amount = null, array $attributes = []): Transaction + { + return $order->refund($amount, $this->name, $attributes); + } /** * Get the URL of the transaction. diff --git a/src/Gateway/TransferDriver.php b/src/Gateway/TransferDriver.php index 6af11ea8..03faae81 100644 --- a/src/Gateway/TransferDriver.php +++ b/src/Gateway/TransferDriver.php @@ -3,26 +3,14 @@ namespace Cone\Bazar\Gateway; use Cone\Bazar\Models\Order; -use Cone\Bazar\Models\Transaction; use Illuminate\Http\Request; class TransferDriver extends Driver { /** - * Process the payment. + * The driver name. */ - public function pay(Order $order, float $amount = null, array $attributes = []): Transaction - { - return $order->pay($amount, 'transfer', $attributes); - } - - /** - * Process the refund. - */ - public function refund(Order $order, float $amount = null, array $attributes = []): Transaction - { - return $order->refund($amount, 'transfer', $attributes); - } + protected string $name = 'transfer'; /** * Handle the checkout request. diff --git a/src/Listeners/PlaceOrder.php b/src/Listeners/PlaceOrder.php index 9a2f7b11..b61a866d 100644 --- a/src/Listeners/PlaceOrder.php +++ b/src/Listeners/PlaceOrder.php @@ -14,7 +14,7 @@ public function handle(CheckoutProcessed $event): void { $event->order->markAs(Order::IN_PROGRESS); - if ($event->order->cart) { + if (! is_null($event->order->cart)) { $event->order->cart->delete(); } } diff --git a/src/Models/Cart.php b/src/Models/Cart.php index 14ba2225..84caaad9 100644 --- a/src/Models/Cart.php +++ b/src/Models/Cart.php @@ -14,6 +14,7 @@ use Illuminate\Database\Eloquent\Factories\HasFactory; use Illuminate\Database\Eloquent\Model; use Illuminate\Database\Eloquent\Relations\BelongsTo; +use Illuminate\Database\Eloquent\Relations\MorphOne; use Illuminate\Support\Facades\Date; class Cart extends Model implements Contract @@ -102,9 +103,21 @@ public function getMorphClass(): string */ public function order(): BelongsTo { - return $this->belongsTo(Order::getProxiedClass())->withDefault(function (): Order { - return Order::proxy()->newInstance($this->toArray()); - }); + return $this->belongsTo(Order::getProxiedClass()) + ->withDefault(function (Order $order): Order { + return $order->fill($this->toArray()); + }); + } + + /** + * Get the address for the model. + */ + public function address(): MorphOne + { + return $this->morphOne(Address::getProxiedClass(), 'addressable') + ->withDefault(function (Address $address): Address { + return $address->fill($this->user?->address?->toArray() ?: []); + }); } /** @@ -167,8 +180,11 @@ public function toOrder(): Order $this->order->items()->createMany($this->items->toArray()); $this->order->address->fill($this->address->toArray())->save(); - $this->order->shipping->fill($this->shipping->toArray())->save(); - $this->order->shipping->address->fill($this->shipping->address->toArray())->save(); + + if ($this->order->needsShipping()) { + $this->order->shipping->fill($this->shipping->toArray())->save(); + $this->order->shipping->address->fill($this->shipping->address->toArray())->save(); + } return $this->order; } diff --git a/tests/Cart/ManagerTest.php b/tests/Cart/ManagerTest.php index ed4ab83f..f41548c5 100644 --- a/tests/Cart/ManagerTest.php +++ b/tests/Cart/ManagerTest.php @@ -161,7 +161,7 @@ public function test_cart_updates_billing(): void $this->assertSame('Test', $this->manager->getBilling()->first_name); } - public function test_cart_has_getTotal(): void + public function test_cart_has_total(): void { $this->assertEquals( $this->manager->getModel()->total, $this->manager->getTotal() diff --git a/tests/Gateway/ManagerTest.php b/tests/Gateway/ManagerTest.php index 14ed0c7e..42efa7ae 100644 --- a/tests/Gateway/ManagerTest.php +++ b/tests/Gateway/ManagerTest.php @@ -13,6 +13,7 @@ use Cone\Bazar\Models\Transaction; use Cone\Bazar\Tests\TestCase; use Exception; +use Illuminate\Support\Facades\Date; use Illuminate\Support\Facades\Notification; class ManagerTest extends TestCase @@ -102,15 +103,15 @@ public function test_gateway_has_transfer_driver(): void $this->assertInstanceOf(TransferDriver::class, $driver); $this->assertSame('Transfer', $driver->getName()); - $payment = $driver->pay($this->order, 1); + $payment = $driver->pay($this->order, 1, ['completed_at' => Date::now()]); $this->assertEquals(1, $payment->amount); - $payment = $driver->pay($this->order); + $payment = $driver->pay($this->order, null, ['completed_at' => Date::now()]); $this->assertTrue($this->order->refresh()->paid()); $this->assertNull($driver->getTransactionUrl($payment)); - $refund = $driver->refund($this->order, 1); + $refund = $driver->refund($this->order, 1, ['completed_at' => Date::now()]); $this->assertEquals(1, $refund->amount); - $refund = $driver->refund($this->order); + $refund = $driver->refund($this->order, null, ['completed_at' => Date::now()]); $this->assertTrue($this->order->refresh()->refunded()); $this->assertNull($driver->getTransactionUrl($payment)); @@ -127,15 +128,15 @@ public function test_gateway_can_have_custom_driver(): void $driver = $this->manager->driver('custom-driver'); $this->assertInstanceOf(CustomGatewayDriver::class, $driver); - $payment = $driver->pay($this->order, 1); + $payment = $driver->pay($this->order, 1, ['completed_at' => Date::now()]); $this->assertEquals(1, $payment->amount); - $payment = $driver->pay($this->order); + $payment = $driver->pay($this->order, null, ['completed_at' => Date::now()]); $this->assertTrue($this->order->refresh()->paid()); $this->assertSame('fake-url', $driver->getTransactionUrl($payment)); - $refund = $driver->refund($this->order, 1); + $refund = $driver->refund($this->order, 1, ['completed_at' => Date::now()]); $this->assertEquals(1, $refund->amount); - $refund = $driver->refund($this->order); + $refund = $driver->refund($this->order, null, ['completed_at' => Date::now()]); $this->assertTrue($this->order->refresh()->refunded()); $this->assertSame('fake-url', $driver->getTransactionUrl($payment)); } @@ -163,31 +164,25 @@ public function test_gateway_handles_failed_checkout(): void class CustomGatewayDriver extends Driver { + protected string $name = 'custom-driver'; + public function getTransactionUrl(Transaction $transaction): ?string { return 'fake-url'; } - - public function pay(Order $order, float $amount = null, array $attributes = []): Transaction - { - return $order->pay($amount, 'custom-driver'); - } - - public function refund(Order $order, float $amount = null, array $attributes = []): Transaction - { - return $order->refund($amount, 'custom-driver'); - } } class FailingDriver extends Driver { + protected string $name = 'failing'; + public function pay(Order $order, float $amount = null, array $attributes = []): Transaction { - throw new Exception; + throw new Exception(); } public function refund(Order $order, float $amount = null, array $attributes = []): Transaction { - throw new Exception; + throw new Exception(); } }