From 60d790afacddafffa28aef91cd14f51dc11dbd0c Mon Sep 17 00:00:00 2001 From: Vitalij Mik Date: Wed, 2 Oct 2024 14:42:51 +0200 Subject: [PATCH] PISHPS-352: Fix shipping for loggedin users (#854) * NTR: PISHPS-352: Fix shipping for loggedin users * NTR: Cs fix --------- Co-authored-by: Vitalij Mik --- .../Services/ApplePayShippingAddressFaker.php | 71 +++++++++++++++++++ .../Services/ApplePayShippingBuilder.php | 2 + .../CustomerAddressRepository.php | 34 +++++++++ .../CustomerAddressRepositoryInterface.php | 17 +++++ src/Resources/config/services/components.xml | 5 ++ .../config/services/repositories.xml | 4 ++ src/Resources/config/services/services.xml | 1 + src/Service/CartService.php | 33 +++++++-- 8 files changed, 163 insertions(+), 4 deletions(-) create mode 100644 src/Components/ApplePayDirect/Services/ApplePayShippingAddressFaker.php create mode 100644 src/Repository/CustomerAddress/CustomerAddressRepository.php create mode 100644 src/Repository/CustomerAddress/CustomerAddressRepositoryInterface.php diff --git a/src/Components/ApplePayDirect/Services/ApplePayShippingAddressFaker.php b/src/Components/ApplePayDirect/Services/ApplePayShippingAddressFaker.php new file mode 100644 index 000000000..d511040c9 --- /dev/null +++ b/src/Components/ApplePayDirect/Services/ApplePayShippingAddressFaker.php @@ -0,0 +1,71 @@ +customerRepository = $customerRepository; + $this->customerAddressRepository = $customerAddressRepository; + } + + + public function createFakeShippingAddress(string $countryId, CustomerEntity $customerEntity, Context $context): string + { + $applePayAddressId = $this->generateAddressId($customerEntity); + + $this->customerRepository->update([ + [ + 'id' => $customerEntity->getId(), + 'addresses' => [ + [ + 'id' => $applePayAddressId, + 'salutationId' => $customerEntity->getSalutationId(), + 'countryId' => $countryId, + 'firstName' => $customerEntity->getFirstName(), + 'lastName' => $customerEntity->getLastName(), + 'city' => 'not provided', //city is not necessary for rule builder + 'street' => 'not provided' //apple pay event "onshippingcontactselected" does not prvide a street https://developer.apple.com/documentation/apple_pay_on_the_web/applepaysession/1778009-onshippingcontactselected + ] + ] + ] + ], $context); + + return $applePayAddressId; + } + + public function deleteFakeShippingAddress(CustomerEntity $customerEntity, Context $context): void + { + $applePayAddressId = $this->generateAddressId($customerEntity); + $this->customerAddressRepository->delete([ + [ + 'id' => $applePayAddressId + ] + ], $context); + } + + private function generateAddressId(CustomerEntity $customerEntity): string + { + /** We cant use here Uuid::fromString because it does not exists in SW6.4 */ + return Uuid::fromBytesToHex(md5($customerEntity->getId() . '-' . self::ID_SUFFIX, true)); + } +} diff --git a/src/Components/ApplePayDirect/Services/ApplePayShippingBuilder.php b/src/Components/ApplePayDirect/Services/ApplePayShippingBuilder.php index 892e9ede1..c823d7863 100644 --- a/src/Components/ApplePayDirect/Services/ApplePayShippingBuilder.php +++ b/src/Components/ApplePayDirect/Services/ApplePayShippingBuilder.php @@ -97,6 +97,8 @@ public function getShippingMethods(string $countryID, SalesChannelContext $conte $availableShippingMethods = $this->shippingMethods->getActiveShippingMethods($context); + $this->cartService->clearFakeAddressIfExists($context); + foreach ($availableShippingMethods as $method) { # temporary switch to our shipping method. # we will then load the cart for this shipping method diff --git a/src/Repository/CustomerAddress/CustomerAddressRepository.php b/src/Repository/CustomerAddress/CustomerAddressRepository.php new file mode 100644 index 000000000..0e4956b26 --- /dev/null +++ b/src/Repository/CustomerAddress/CustomerAddressRepository.php @@ -0,0 +1,34 @@ +customerAddressRepository = $customerAddressRepository; + } + + /** + * @param array $ids + * @param Context $context + * @return EntityWrittenContainerEvent + */ + public function delete(array $ids, Context $context): EntityWrittenContainerEvent + { + return $this->customerAddressRepository->delete($ids, $context); + } +} diff --git a/src/Repository/CustomerAddress/CustomerAddressRepositoryInterface.php b/src/Repository/CustomerAddress/CustomerAddressRepositoryInterface.php new file mode 100644 index 000000000..d7ce9c077 --- /dev/null +++ b/src/Repository/CustomerAddress/CustomerAddressRepositoryInterface.php @@ -0,0 +1,17 @@ + $ids + * @param Context $context + * @return EntityWrittenContainerEvent + */ + public function delete(array $ids, Context $context): EntityWrittenContainerEvent; +} diff --git a/src/Resources/config/services/components.xml b/src/Resources/config/services/components.xml index d07d1c43a..568cd9a1b 100644 --- a/src/Resources/config/services/components.xml +++ b/src/Resources/config/services/components.xml @@ -75,6 +75,11 @@ + + + + + diff --git a/src/Resources/config/services/repositories.xml b/src/Resources/config/services/repositories.xml index 29163ce72..0edfc3c9a 100644 --- a/src/Resources/config/services/repositories.xml +++ b/src/Resources/config/services/repositories.xml @@ -93,6 +93,10 @@ + + + + diff --git a/src/Resources/config/services/services.xml b/src/Resources/config/services/services.xml index 52d552ead..ddb877ce3 100644 --- a/src/Resources/config/services/services.xml +++ b/src/Resources/config/services/services.xml @@ -140,6 +140,7 @@ + diff --git a/src/Service/CartService.php b/src/Service/CartService.php index 74b1fb0b0..853da875a 100644 --- a/src/Service/CartService.php +++ b/src/Service/CartService.php @@ -4,9 +4,11 @@ use Kiener\MolliePayments\Compatibility\Gateway\CompatibilityGateway; use Kiener\MolliePayments\Compatibility\Gateway\CompatibilityGatewayInterface; +use Kiener\MolliePayments\Components\ApplePayDirect\Services\ApplePayShippingAddressFaker; use Shopware\Core\Checkout\Cart\Cart; use Shopware\Core\Checkout\Cart\LineItemFactoryHandler\ProductLineItemFactory; use Shopware\Core\Checkout\Cart\SalesChannel\CartService as SalesChannelCartService; +use Shopware\Core\Checkout\Customer\CustomerEntity; use Shopware\Core\Framework\Validation\DataBag\DataBag; use Shopware\Core\System\SalesChannel\Context\SalesChannelContextService; use Shopware\Core\System\SalesChannel\SalesChannel\SalesChannelContextSwitcher; @@ -34,6 +36,11 @@ class CartService implements CartServiceInterface */ private $compatibilityGateway; + /** + * @var ApplePayShippingAddressFaker + */ + private $shippingAddressFaker; + /** * @param SalesChannelCartService $swCartService @@ -41,12 +48,13 @@ class CartService implements CartServiceInterface * @param ProductLineItemFactory $productItemFactory * @param CompatibilityGateway $compatibilityGateway */ - public function __construct(SalesChannelCartService $swCartService, SalesChannelContextSwitcher $contextSwitcher, ProductLineItemFactory $productItemFactory, CompatibilityGatewayInterface $compatibilityGateway) + public function __construct(SalesChannelCartService $swCartService, SalesChannelContextSwitcher $contextSwitcher, ProductLineItemFactory $productItemFactory, CompatibilityGatewayInterface $compatibilityGateway, ApplePayShippingAddressFaker $shippingAddressFaker) { $this->swCartService = $swCartService; $this->contextSwitcher = $contextSwitcher; $this->productItemFactory = $productItemFactory; $this->compatibilityGateway = $compatibilityGateway; + $this->shippingAddressFaker = $shippingAddressFaker; } @@ -106,10 +114,17 @@ public function getShippingCosts(Cart $cart): float public function updateCountry(SalesChannelContext $context, string $countryID): SalesChannelContext { $dataBag = new DataBag(); - - $dataBag->add([ + $dataBagData = [ SalesChannelContextService::COUNTRY_ID => $countryID - ]); + ]; + $customer = $context->getCustomer(); + + if ($customer instanceof CustomerEntity) { + $applePayAddressId = $this->shippingAddressFaker->createFakeShippingAddress($countryID, $customer, $context->getContext()); + $dataBagData[SalesChannelContextService::SHIPPING_ADDRESS_ID] = $applePayAddressId; + } + + $dataBag->add($dataBagData); $this->contextSwitcher->update($dataBag, $context); @@ -161,4 +176,14 @@ public function updatePaymentMethod(SalesChannelContext $context, string $paymen return $this->compatibilityGateway->getSalesChannelContext($scID, $dID, $context->getToken()); } + + public function clearFakeAddressIfExists(SalesChannelContext $context): void + { + $customer = $context->getCustomer(); + if ($customer === null) { + return; + } + + $this->shippingAddressFaker->deleteFakeShippingAddress($customer, $context->getContext()); + } }