From d42d65500dd0acf9b305831e1208d2f02c2e8bf5 Mon Sep 17 00:00:00 2001 From: Filip Kojic Date: Mon, 30 Dec 2024 11:27:07 +0100 Subject: [PATCH] Add payment methods filtering Filter based on enabled express checkout settings and availability rules ISSUE: AD4CR22I-14 --- src/Resources/config/services.xml | 1 + src/Service/ExpressCheckoutService.php | 10 ++++- src/Service/PaymentMethodsFilterService.php | 44 +++++++++++++++++++++ 3 files changed, 54 insertions(+), 1 deletion(-) diff --git a/src/Resources/config/services.xml b/src/Resources/config/services.xml index 85206c18..099f4c0e 100755 --- a/src/Resources/config/services.xml +++ b/src/Resources/config/services.xml @@ -71,6 +71,7 @@ + diff --git a/src/Service/ExpressCheckoutService.php b/src/Service/ExpressCheckoutService.php index 3678b663..f5278623 100644 --- a/src/Service/ExpressCheckoutService.php +++ b/src/Service/ExpressCheckoutService.php @@ -40,6 +40,11 @@ class ExpressCheckoutService */ private $paymentMethodsService; + /** + * @var PaymentMethodsFilterService + */ + private $paymentMethodsFilterService; + /** * @var Currency */ @@ -50,12 +55,14 @@ public function __construct( EntityRepository $countryRepository, EntityRepository $shippingMethodRepository, PaymentMethodsService $paymentMethodsService, + PaymentMethodsFilterService $paymentMethodsFilterService, Currency $currencyUtil ) { $this->cartService = $cartService; $this->countryRepository = $countryRepository; $this->shippingMethodRepository = $shippingMethodRepository; $this->paymentMethodsService = $paymentMethodsService; + $this->paymentMethodsFilterService = $paymentMethodsFilterService; $this->currencyUtil = $currencyUtil; } @@ -209,13 +216,14 @@ public function createCart( $cart = $this->cartService->recalculate($cart, $updatedSalesChannelContext); $paymentMethods = $this->paymentMethodsService->getPaymentMethods($updatedSalesChannelContext); + $filteredPaymentMethods = $this->paymentMethodsFilterService->filterAndValidatePaymentMethods($paymentMethods, $cart, $salesChannelContext); return [ 'cart' => $cart, 'shippingMethods' => $shippingMethods, 'shippingMethod' => $shippingMethod, 'shippingLocation' => $shippingLocation, - 'paymentMethods' => $paymentMethods, + 'paymentMethods' => $filteredPaymentMethods, ]; } diff --git a/src/Service/PaymentMethodsFilterService.php b/src/Service/PaymentMethodsFilterService.php index 6d9a6f6d..4cac6432 100644 --- a/src/Service/PaymentMethodsFilterService.php +++ b/src/Service/PaymentMethodsFilterService.php @@ -32,6 +32,8 @@ use Adyen\Shopware\Handlers\ApplePayPaymentMethodHandler; use Adyen\Shopware\PaymentMethods\RatepayDirectdebitPaymentMethod; use Adyen\Shopware\PaymentMethods\RatepayPaymentMethod; +use Shopware\Core\Checkout\Cart\Cart; +use Shopware\Core\Checkout\Cart\Rule\CartRuleScope; use Shopware\Core\Checkout\Payment\PaymentMethodCollection; use Shopware\Core\Checkout\Payment\PaymentMethodEntity; use Shopware\Core\Checkout\Payment\SalesChannel\AbstractPaymentMethodRoute; @@ -305,4 +307,46 @@ public function getGiftCardPaymentMethodId(SalesChannelContext $context): ?strin // Return the payment method ID or null if not found return $paymentMethod ? $paymentMethod->getId() : null; } + + public function filterAndValidatePaymentMethods( + PaymentMethodsResponse $paymentMethodsResponse, + Cart $cart, + SalesChannelContext $salesChannelContext + ): PaymentMethodsResponse { + // Extract original payment methods + $paymentMethods = $paymentMethodsResponse->getPaymentMethods(); + + // Supported payment methods and their corresponding configuration checks + $allowedMethods = [ + 'paywithgoogle' => [$this->configurationService, 'isGooglePayExpressCheckoutEnabled'], + 'paypal' => [$this->configurationService, 'isPayPalExpressCheckoutEnabled'], + 'applepay' => [$this->configurationService, 'isApplePayExpressCheckoutEnabled'] + ]; + + // Filter methods by type and configuration + $filteredMethods = array_filter($paymentMethods, function ($method) use ($allowedMethods, $salesChannelContext) { + $type = $method['type']; + if (!isset($allowedMethods[$type])) { + return false; + } + + $configCheck = $allowedMethods[$type]; + return $configCheck($salesChannelContext->getSalesChannelId()); + }); + + // Check rules for every method + $validMethods = []; + foreach ($filteredMethods as $method) { + $availabilityRule = $method['availabilityRule'] ?? null; + + if (!$availabilityRule || $availabilityRule->getPayload()->match(new CartRuleScope($cart, $salesChannelContext))) { + $validMethods[] = $method; + } + } + + $paymentMethodsResponse->setPaymentMethods($validMethods); + + return $paymentMethodsResponse; + } + }