custom/static-plugins/SamsonCustomer/src/Subscriber/RegisterSubscriber.php line 78

Open in your IDE?
  1. <?php declare(strict_types=1);
  2. namespace Samson\Subscriber;
  3. /***
  4.  *
  5.  * This file is part of the "SAMSON Shop" project.
  6.  *
  7.  * For the full copyright and license information, please read the
  8.  * LICENSE.txt file that was distributed with this source code.
  9.  *
  10.  *  (c) 2021
  11.  *
  12.  ***/
  13. use Exception;
  14. use Samson\CustomFieldSet\Constants\CustomerCustomFieldConstants;
  15. use Samson\Defaults;
  16. use Samson\Event\CustomDataMappingEvent;
  17. use Samson\Event\Sap\SapCustomerAddressSynchronizationEvent;
  18. use Samson\Event\Sap\SapCustomerRegistrationErrorEvent;
  19. use Samson\Exception\SapApiRequestException;
  20. use Samson\Service\PersistentCartService;
  21. use Samson\Api\Soap\Service\SoapCustomerService;
  22. use Sentry\State\Scope;
  23. use Shopware\Core\Checkout\Customer\CustomerEntity;
  24. use Shopware\Core\Checkout\Customer\CustomerEvents;
  25. use Shopware\Core\Checkout\Customer\Event\CustomerDoubleOptInRegistrationEvent;
  26. use Shopware\Core\Checkout\Customer\Event\CustomerLoginEvent;
  27. use Shopware\Core\Checkout\Customer\Event\CustomerRegisterEvent;
  28. use Shopware\Core\Framework\Context;
  29. use Shopware\Core\Framework\DataAbstractionLayer\EntityRepositoryInterface;
  30. use Shopware\Core\System\SystemConfig\SystemConfigService;
  31. use Symfony\Component\EventDispatcher\EventSubscriberInterface;
  32. use Symfony\Contracts\EventDispatcher\EventDispatcherInterface;
  33. use function Sentry\captureException;
  34. use function Sentry\withScope;
  35. /**
  36.  * Class RegisterSubscriber
  37.  * @package Samson\Subscriber
  38.  * @author Christian Schmitz <christian.schmitz@dkd.de>
  39.  */
  40. class RegisterSubscriber implements EventSubscriberInterface
  41. {
  42.     const ERROR_CUSTOMER_CREATION_IN_SAP 'Error while creating a customer in SAP';
  43.     private PersistentCartService $persistentCartService;
  44.     private EntityRepositoryInterface $customerRepository;
  45.     private SystemConfigService $systemConfigService;
  46.     private SoapCustomerService $soapCustomerService;
  47.     private EventDispatcherInterface $eventDispatcher;
  48.     public function __construct(
  49.         PersistentCartService     $persistentCartService,
  50.         EntityRepositoryInterface $customerRepository,
  51.         SystemConfigService       $systemConfigService,
  52.         SoapCustomerService       $soapCustomerService,
  53.         EventDispatcherInterface  $eventDispatcher
  54.     )
  55.     {
  56.         $this->persistentCartService $persistentCartService;
  57.         $this->customerRepository $customerRepository;
  58.         $this->systemConfigService $systemConfigService;
  59.         $this->soapCustomerService $soapCustomerService;
  60.         $this->eventDispatcher $eventDispatcher;
  61.     }
  62.     public static function getSubscribedEvents(): array
  63.     {
  64.         return [
  65.             CustomerLoginEvent::class => 'onCustomerLoginEvent',
  66.             CustomerRegisterEvent::class => 'onCustomerRegisterEvent',
  67.             CustomerEvents::MAPPING_REGISTER_CUSTOMER => 'onMappingRegisterCustomerEvent',
  68.         ];
  69.     }
  70.     public function onCustomerLoginEvent(CustomerLoginEvent $event): void
  71.     {
  72.         if (!empty($event->getCustomer())) {
  73.             $this->persistentCartService->loadCart(
  74.                 $event->getCustomer(),
  75.                 $event->getContext(),
  76.                 $event->getSalesChannelContext(),
  77.                 $event->getContextToken()
  78.             );
  79.         }
  80.     }
  81.     /**
  82.      * @throws Exception
  83.      */
  84.     public function onCustomerRegisterEvent(CustomerRegisterEvent $event): void
  85.     {
  86.         $salesChannelContext $event->getSalesChannelContext();
  87.         if (!$this->systemConfigService->get(Defaults::SAP_ACTIVATION_KEY$salesChannelContext->getSalesChannelId())) {
  88.             return;
  89.         }
  90.         if (!$this->systemConfigService->get(Defaults::SAP_CUSTOMER_REGISTRATION_KEY$salesChannelContext->getSalesChannelId())) {
  91.             return;
  92.         }
  93.         $customer $event->getCustomer();
  94.         $context $event->getContext();
  95.         if (isset($customer->getCustomFields()[CustomerCustomFieldConstants::CUSTOM_FIELD_IS_SUB_ACCOUNT])
  96.             && $customer->getCustomFields()[CustomerCustomFieldConstants::CUSTOM_FIELD_IS_SUB_ACCOUNT])  {
  97.             return;
  98.         }
  99.         try {
  100.             $customerExists $this->soapCustomerService->checkIfCustomerExistsInSap($customer$context);
  101.             if ($customerExists) {
  102.                 $customerInfo $this->soapCustomerService->synchronizeCustomerDataWithSap($customer$context);
  103.                 if (!empty($customerInfo) && !empty($customerInfo['address'])) {
  104.                     $this->eventDispatcher->dispatch(
  105.                         new SapCustomerAddressSynchronizationEvent($customerInfo['address'],
  106.                             $customerInfo['customerNumber'],
  107.                             $salesChannelContext->getSalesChannelId(),
  108.                             $context),
  109.                         SapCustomerRegistrationErrorEvent::EVENT_NAME);
  110.                 }
  111.             } else {
  112.                 $createCustomer $this->soapCustomerService->createCustomerInSap($customer$context);
  113.                 if (!$createCustomer) {
  114.                     $this->setCustomerInactiveIfErrorOccurs($customer$context);
  115.                     $this->eventDispatcher->dispatch(
  116.                         new SapCustomerRegistrationErrorEvent(self::ERROR_CUSTOMER_CREATION_IN_SAP,
  117.                             $salesChannelContext->getSalesChannelId(),
  118.                             $context),
  119.                         SapCustomerRegistrationErrorEvent::EVENT_NAME);
  120.                 }
  121.             }
  122.         } catch (Exception $e) {
  123.             $this->setCustomerInactiveIfErrorOccurs($customer$context);
  124.             $errorMessage $e->getMessage() . ': ' PHP_EOL;
  125.             if (isset($e->detail)) {
  126.                 $faultDetails $e->detail->MT_FAULT_MSG->standard->faultDetail;
  127.                 foreach ($faultDetails as $faultDetail) {
  128.                     $errorMessage $errorMessage $faultDetail->text PHP_EOL;
  129.                 }
  130.             }
  131.             $this->eventDispatcher->dispatch(
  132.                 new SapCustomerRegistrationErrorEvent($errorMessage,
  133.                     $salesChannelContext->getSalesChannelId(),
  134.                     $context),
  135.                 SapCustomerRegistrationErrorEvent::EVENT_NAME);
  136.             withScope(function (Scope $scope) use ($e$errorMessage): void {
  137.                 $scope->setContext('RegisterCustomerEventException',
  138.                     [
  139.                         'errorMessage' => $errorMessage
  140.                     ]);
  141.                 captureException($e);
  142.             });
  143.             throw new SapApiRequestException($errorMessage);
  144.         }
  145.     }
  146.     public function onMappingRegisterCustomerEvent(CustomDataMappingEvent $event): void
  147.     {
  148.         if (!$this->systemConfigService->get(Defaults::SAP_ACTIVATION_KEY$event->getSalesChannelContext()->getSalesChannelId())) {
  149.             return;
  150.         }
  151.         $data $event->getInput();
  152.         $customer $event->getOutput();
  153.         $hasCustomCustomerNumber $data->has('customerNumber') && !empty($data->get('customerNumber'));
  154.         $customer['customerNumber'] = $hasCustomCustomerNumber $data->get('customerNumber') : Defaults::CUSTOMER_NUMBER_WILDCARD;
  155.         $event->setOutput($customer);
  156.     }
  157.     private function setCustomerInactiveIfErrorOccurs(CustomerEntity $customerEntityContext $context): void
  158.     {
  159.         $this->customerRepository->update([['id' => $customerEntity->getId(), 'active' => false]], $context);
  160.     }
  161. }