custom/plugins/SwagCustomizedProducts/src/PayPal/PayPalLineItemSubscriber.php line 60

Open in your IDE?
  1. <?php declare(strict_types=1);
  2. /*
  3.  * (c) shopware AG <info@shopware.com>
  4.  * For the full copyright and license information, please view the LICENSE
  5.  * file that was distributed with this source code.
  6.  */
  7. namespace Swag\CustomizedProducts\PayPal;
  8. use Psr\Log\LoggerInterface;
  9. use Shopware\Core\Checkout\Cart\LineItem\LineItem;
  10. use Shopware\Core\Checkout\Cart\LineItem\LineItemCollection;
  11. use Shopware\Core\Checkout\Order\Aggregate\OrderLineItem\OrderLineItemCollection;
  12. use Shopware\Core\Checkout\Order\Aggregate\OrderLineItem\OrderLineItemEntity;
  13. use Shopware\Core\Framework\Struct\Collection;
  14. use Shopware\Core\Framework\Struct\Struct;
  15. use Swag\CustomizedProducts\Core\Checkout\CustomizedProductsCartDataCollector;
  16. use Swag\PayPal\OrdersApi\Builder\Event\PayPalV2ItemFromCartEvent;
  17. use Swag\PayPal\OrdersApi\Builder\Event\PayPalV2ItemFromOrderEvent;
  18. use Swag\PayPal\PaymentsApi\Builder\Event\PayPalV1ItemFromCartEvent;
  19. use Swag\PayPal\PaymentsApi\Builder\Event\PayPalV1ItemFromOrderEvent;
  20. use Swag\PayPal\RestApi\PayPalApiStruct;
  21. use Swag\PayPal\RestApi\V1\Api\Payment\Transaction\ItemList\Item as ItemV1;
  22. use Swag\PayPal\RestApi\V2\Api\Order\PurchaseUnit\Item as ItemV2;
  23. use Symfony\Component\EventDispatcher\EventSubscriberInterface;
  24. use Symfony\Contracts\EventDispatcher\Event;
  25. use Symfony\Contracts\Translation\TranslatorInterface;
  26. class PayPalLineItemSubscriber implements EventSubscriberInterface
  27. {
  28.     /**
  29.      * @var LoggerInterface
  30.      */
  31.     private $logger;
  32.     /**
  33.      * @var TranslatorInterface
  34.      */
  35.     private $translator;
  36.     public function __construct(LoggerInterface $loggerTranslatorInterface $translator)
  37.     {
  38.         $this->logger $logger;
  39.         $this->translator $translator;
  40.     }
  41.     public static function getSubscribedEvents(): array
  42.     {
  43.         return [
  44.             PayPalV1ItemFromOrderEvent::class => 'adjustPayPalItemFromOrder',
  45.             PayPalV1ItemFromCartEvent::class => 'adjustPayPalItemFromCart',
  46.             PayPalV2ItemFromOrderEvent::class => 'adjustPayPalItemFromOrder',
  47.             PayPalV2ItemFromCartEvent::class => 'adjustPayPalItemFromCart',
  48.         ];
  49.     }
  50.     /**
  51.      * @param PayPalV1ItemFromOrderEvent|PayPalV2ItemFromOrderEvent $event
  52.      */
  53.     public function adjustPayPalItemFromOrder(Event $event): void
  54.     {
  55.         $customProductsContainer $event->getOriginalShopwareLineItem();
  56.         if ($customProductsContainer->getType() !== CustomizedProductsCartDataCollector::CUSTOMIZED_PRODUCTS_TEMPLATE_LINE_ITEM_TYPE) {
  57.             return;
  58.         }
  59.         $childLineItems $customProductsContainer->getChildren();
  60.         if ($childLineItems === null) {
  61.             return;
  62.         }
  63.         $paypalLineItem $event->getPayPalLineItem();
  64.         $changedValues $this->processCustomProductLineItems($childLineItems);
  65.         $this->setName($paypalLineItem$changedValues['name'], $customProductsContainer);
  66.         $this->setSku($paypalLineItem$changedValues['sku'], $customProductsContainer);
  67.     }
  68.     /**
  69.      * @param PayPalV1ItemFromCartEvent|PayPalV2ItemFromCartEvent $event
  70.      */
  71.     public function adjustPayPalItemFromCart(Event $event): void
  72.     {
  73.         $customProductsContainer $event->getOriginalShopwareLineItem();
  74.         if ($customProductsContainer->getType() !== CustomizedProductsCartDataCollector::CUSTOMIZED_PRODUCTS_TEMPLATE_LINE_ITEM_TYPE) {
  75.             return;
  76.         }
  77.         $paypalLineItem $event->getPayPalLineItem();
  78.         $changedValues $this->processCustomProductLineItems($customProductsContainer->getChildren());
  79.         $this->setName($paypalLineItem$changedValues['name'], $customProductsContainer);
  80.         $this->setSku($paypalLineItem$changedValues['sku'], $customProductsContainer);
  81.     }
  82.     /**
  83.      * @param OrderLineItemCollection|LineItemCollection $customProductLineItems
  84.      *
  85.      * @return array{'name': string, 'sku': string|null}
  86.      */
  87.     private function processCustomProductLineItems(Collection $customProductLineItems): array
  88.     {
  89.         $name '';
  90.         $optionNames = [];
  91.         $sku null;
  92.         $optionNumbers = [];
  93.         foreach ($customProductLineItems as $customProductLineItem) {
  94.             $label = (string) $customProductLineItem->getLabel();
  95.             $productNumber null;
  96.             $payload $customProductLineItem->getPayload();
  97.             if ($payload !== null) {
  98.                 $productNumber $payload['productNumber'] ?? null;
  99.                 if ($productNumber !== null) {
  100.                     $productNumber = (string) $productNumber;
  101.                 }
  102.             }
  103.             if ($customProductLineItem->getType() === LineItem::PRODUCT_LINE_ITEM_TYPE) {
  104.                 $name $label;
  105.                 $sku $productNumber;
  106.                 continue;
  107.             }
  108.             if ($customProductLineItem->getType() === CustomizedProductsCartDataCollector::CUSTOMIZED_PRODUCTS_OPTION_LINE_ITEM_TYPE) {
  109.                 $optionValues $customProductLineItem->getChildren();
  110.                 $this->processOptionLineItems($label$productNumber$optionNames$optionNumbers$optionValues);
  111.             }
  112.         }
  113.         if ($optionNames !== []) {
  114.             $hint $this->translator->trans('customizedProducts.paypal.hint');
  115.             $name .= \sprintf(' (%s: %s)'$hint\implode(', '$optionNames));
  116.         }
  117.         if ($sku !== null && $optionNumbers !== []) {
  118.             $hint $this->translator->trans('customizedProducts.paypal.hint');
  119.             $sku .= \sprintf(' (%s: %s)'$hint\implode(', '$optionNumbers));
  120.         }
  121.         return ['name' => $name'sku' => $sku];
  122.     }
  123.     /**
  124.      * @param OrderLineItemCollection|LineItemCollection|null $optionValues
  125.      */
  126.     private function processOptionLineItems(
  127.         string $label,
  128.         ?string $productNumber,
  129.         array &$optionNames,
  130.         array &$optionNumbers,
  131.         ?Collection $optionValues
  132.     ): void {
  133.         if ($optionValues !== null && $optionValues->count() > 0) {
  134.             $optionValueResult $this->processOptionValueLineItems($optionValues$label);
  135.             $label $optionValueResult['label'];
  136.             $productNumber $optionValueResult['productNumber'];
  137.         }
  138.         if ($label !== '') {
  139.             $optionNames[] = $label;
  140.         }
  141.         if ($productNumber !== null && $productNumber !== CustomizedProductsCartDataCollector::FALLBACK_PRODUCT_NUMBER) {
  142.             $optionNumbers[] = $productNumber;
  143.         }
  144.     }
  145.     /**
  146.      * @param OrderLineItemCollection|LineItemCollection $optionValues
  147.      *
  148.      * @return array{'label': string, 'productNumber': string|null}
  149.      */
  150.     private function processOptionValueLineItems(Collection $optionValuesstring $label): array
  151.     {
  152.         $optionValueLabels = [];
  153.         $optionValueNumbers = [];
  154.         foreach ($optionValues as $optionValue) {
  155.             if ($optionValue->getType() !== CustomizedProductsCartDataCollector::CUSTOMIZED_PRODUCTS_OPTION_VALUE_LINE_ITEM_TYPE) {
  156.                 continue;
  157.             }
  158.             $optionValueLabels[] = $optionValue->getLabel();
  159.             $payload $optionValue->getPayload();
  160.             if ($payload !== null) {
  161.                 $optionValueNumbers[] = $payload['productNumber'] ?? null;
  162.             }
  163.         }
  164.         if ($optionValueLabels !== []) {
  165.             $label .= \sprintf(' (%s)'\implode(', '$optionValueLabels));
  166.         }
  167.         $productNumber null;
  168.         if ($optionValueNumbers !== []) {
  169.             $productNumber \implode(', '$optionValueNumbers);
  170.         }
  171.         return ['label' => $label'productNumber' => $productNumber];
  172.     }
  173.     /**
  174.      * @param ItemV2|ItemV1                $item
  175.      * @param OrderLineItemEntity|LineItem $customProductsContainer
  176.      */
  177.     private function setName(
  178.         PayPalApiStruct $item,
  179.         string $name,
  180.         Struct $customProductsContainer
  181.     ): void {
  182.         try {
  183.             $item->setName($name);
  184.         } catch (\LengthException $e) {
  185.             $this->logger->warning($e->getMessage(), ['lineItem' => $customProductsContainer]);
  186.             $item->setName(\substr($name0$item::MAX_LENGTH_NAME));
  187.         }
  188.     }
  189.     /**
  190.      * @param ItemV2|ItemV1                $item
  191.      * @param OrderLineItemEntity|LineItem $customProductsContainer
  192.      */
  193.     private function setSku(
  194.         PayPalApiStruct $item,
  195.         ?string $sku,
  196.         Struct $customProductsContainer
  197.     ): void {
  198.         if ($sku === null) {
  199.             $item->setSku(null);
  200.             return;
  201.         }
  202.         try {
  203.             $item->setSku($sku);
  204.         } catch (\LengthException $e) {
  205.             $this->logger->warning($e->getMessage(), ['lineItem' => $customProductsContainer]);
  206.             $item->setSku(\substr($sku0$item::MAX_LENGTH_SKU));
  207.         }
  208.     }
  209. }