OrderInterfaceBuilder.php 11 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277
  1. <?php
  2. /**
  3. * Refer to LICENSE.txt distributed with the Temando Shipping module for notice of license
  4. */
  5. namespace Temando\Shipping\Model;
  6. use Magento\Directory\Model\Currency;
  7. use Magento\Framework\Api\AbstractSimpleObjectBuilder;
  8. use Magento\Framework\Api\ObjectFactory;
  9. use Magento\Framework\Exception\LocalizedException;
  10. use Magento\Quote\Model\Quote\Address\RateRequest;
  11. use Magento\Sales\Model\Order;
  12. use Temando\Shipping\Api\Data\Delivery\CollectionPointSearchRequestInterface;
  13. use Temando\Shipping\Api\Data\Delivery\PickupLocationSearchRequestInterface;
  14. use Temando\Shipping\Api\Data\Delivery\QuoteCollectionPointInterface;
  15. use Temando\Shipping\Api\Data\Delivery\QuotePickupLocationInterface;
  16. use Temando\Shipping\Model\Checkout\RateRequest\Extractor;
  17. use Temando\Shipping\Model\Order\CheckoutFieldContainerInterface;
  18. use Temando\Shipping\Model\Order\CheckoutFieldContainerInterfaceBuilder;
  19. use Temando\Shipping\Model\Order\OrderBillingInterfaceBuilder;
  20. use Temando\Shipping\Model\Order\OrderItemInterfaceBuilder;
  21. use Temando\Shipping\Model\Order\OrderRecipientInterfaceBuilder;
  22. /**
  23. * Temando Order Interface Builder
  24. *
  25. * Create an entity to be shared between shipping module and Temando platform.
  26. *
  27. * @package Temando\Shipping\Model
  28. * @author Christoph Aßmann <christoph.assmann@netresearch.de>
  29. * @license https://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
  30. * @link https://www.temando.com/
  31. */
  32. class OrderInterfaceBuilder extends AbstractSimpleObjectBuilder
  33. {
  34. /**
  35. * @var Extractor
  36. */
  37. private $rateRequestExtractor;
  38. /**
  39. * @var OrderBillingInterfaceBuilder
  40. */
  41. private $billingBuilder;
  42. /**
  43. * @var OrderRecipientInterfaceBuilder
  44. */
  45. private $recipientBuilder;
  46. /**
  47. * @var OrderItemInterfaceBuilder
  48. */
  49. private $orderItemBuilder;
  50. /**
  51. * @var CheckoutFieldContainerInterfaceBuilder
  52. */
  53. private $checkoutFieldContainerBuilder;
  54. /**
  55. * OrderInterfaceBuilder constructor.
  56. * @param ObjectFactory $objectFactory
  57. * @param Extractor $rateRequestExtractor
  58. * @param OrderBillingInterfaceBuilder $billingBuilder
  59. * @param OrderRecipientInterfaceBuilder $recipientBuilder
  60. * @param OrderItemInterfaceBuilder $orderItemBuilder
  61. * @param CheckoutFieldContainerInterfaceBuilder $checkoutFieldContainerBuilder
  62. */
  63. public function __construct(
  64. ObjectFactory $objectFactory,
  65. Extractor $rateRequestExtractor,
  66. OrderBillingInterfaceBuilder $billingBuilder,
  67. OrderRecipientInterfaceBuilder $recipientBuilder,
  68. OrderItemInterfaceBuilder $orderItemBuilder,
  69. CheckoutFieldContainerInterfaceBuilder $checkoutFieldContainerBuilder
  70. ) {
  71. $this->rateRequestExtractor = $rateRequestExtractor;
  72. $this->billingBuilder = $billingBuilder;
  73. $this->recipientBuilder = $recipientBuilder;
  74. $this->orderItemBuilder = $orderItemBuilder;
  75. $this->checkoutFieldContainerBuilder = $checkoutFieldContainerBuilder;
  76. parent::__construct($objectFactory);
  77. }
  78. /**
  79. * Map order state code to platform order status.
  80. * Valid values: "awaiting payment" "confirmed" "processing" "fulfilled" "cancelled" "archived" "refunded" "closed"
  81. *
  82. * @param string $state
  83. * @return string
  84. */
  85. private function mapOrderState($state)
  86. {
  87. $map = [
  88. Order::STATE_NEW => OrderInterface::STATUS_CONFIRMED,
  89. Order::STATE_PENDING_PAYMENT => OrderInterface::STATUS_AWAITING_PAYMENT,
  90. Order::STATE_PROCESSING => OrderInterface::STATUS_PROCESSING,
  91. Order::STATE_COMPLETE => OrderInterface::STATUS_CLOSED,
  92. Order::STATE_CLOSED => OrderInterface::STATUS_REFUNDED,
  93. Order::STATE_CANCELED => OrderInterface::STATUS_CANCELLED,
  94. Order::STATE_HOLDED => OrderInterface::STATUS_ARCHIVED,
  95. Order::STATE_PAYMENT_REVIEW => OrderInterface::STATUS_AWAITING_PAYMENT,
  96. '--' => OrderInterface::STATUS_FULFILLED // shipments created: no corresponding order state available
  97. ];
  98. return isset($map[$state]) ? $map[$state] : '';
  99. }
  100. /**
  101. * @param RateRequest $rateRequest
  102. * @return void
  103. */
  104. public function setRateRequest(RateRequest $rateRequest)
  105. {
  106. try {
  107. $quote = $this->rateRequestExtractor->getQuote($rateRequest);
  108. $createdAt = $quote->getCreatedAt();
  109. $updatedAt = (strpos($quote->getUpdatedAt(), '0000') === 0)
  110. ? $quote->getCreatedAt()
  111. : $quote->getUpdatedAt();
  112. // orderedAt is a required field, although this does not make sense during checkout.
  113. $orderedAt = $quote->getConvertedAt()
  114. ? $quote->getConvertedAt()
  115. : $updatedAt;
  116. $sourceReference = $quote->getReservedOrderId()
  117. ? $quote->getReservedOrderId()
  118. : $quote->getId();
  119. } catch (LocalizedException $e) {
  120. // detailed order data unavailable
  121. $createdAt = gmdate('Y-m-d H:i:s');
  122. $updatedAt = $createdAt;
  123. $orderedAt = $createdAt;
  124. $sourceReference = '';
  125. }
  126. $currencyCode = $rateRequest->getBaseCurrency();
  127. if ($currencyCode instanceof Currency) {
  128. $currencyCode = $currencyCode->getCurrencyCode();
  129. }
  130. $this->billingBuilder->setRateRequest($rateRequest);
  131. $billingAddress = $this->billingBuilder->create();
  132. $this->recipientBuilder->setRateRequest($rateRequest);
  133. $recipient = $this->recipientBuilder->create();
  134. $orderItems = [];
  135. $rateRequestItems = $this->rateRequestExtractor->getItems($rateRequest);
  136. foreach ($rateRequestItems as $quoteItem) {
  137. if ($quoteItem->getParentItem()) {
  138. continue;
  139. }
  140. $this->orderItemBuilder->setRateRequest($rateRequest);
  141. $this->orderItemBuilder->setQuoteItem($quoteItem);
  142. $orderItems[]= $this->orderItemBuilder->create();
  143. }
  144. // add data path to checkout fields by reading definitions from config
  145. $this->checkoutFieldContainerBuilder->setRateRequest($rateRequest);
  146. /** @var CheckoutFieldContainerInterface $checkoutFieldContainer */
  147. $checkoutFieldContainer = $this->checkoutFieldContainerBuilder->create();
  148. $this->_set(OrderInterface::CREATED_AT, $createdAt);
  149. $this->_set(OrderInterface::ORDERED_AT, $orderedAt);
  150. $this->_set(OrderInterface::LAST_MODIFIED_AT, $updatedAt);
  151. $this->_set(OrderInterface::STATUS, '');
  152. $this->_set(OrderInterface::BILLING, $billingAddress);
  153. $this->_set(OrderInterface::RECIPIENT, $recipient);
  154. $this->_set(OrderInterface::ORDER_ITEMS, $orderItems);
  155. $this->_set(OrderInterface::CURRENCY, $currencyCode);
  156. $this->_set(OrderInterface::AMOUNT, $rateRequest->getPackageValueWithDiscount());
  157. $this->_set(OrderInterface::CHECKOUT_FIELDS, $checkoutFieldContainer->getFields());
  158. $this->_set(OrderInterface::SOURCE_REFERENCE, $sourceReference);
  159. }
  160. /**
  161. * @param \Magento\Sales\Api\Data\OrderInterface|\Magento\Sales\Model\Order $order
  162. * @return void
  163. */
  164. public function setOrder(\Magento\Sales\Api\Data\OrderInterface $order)
  165. {
  166. $shippingMethod = $order->getShippingMethod(true);
  167. $methodCode = $shippingMethod->getData('method');
  168. $this->billingBuilder->setOrder($order);
  169. $billingAddress = $this->billingBuilder->create();
  170. $this->recipientBuilder->setOrder($order);
  171. $recipient = $this->recipientBuilder->create();
  172. $orderItems = [];
  173. /** @var \Magento\Sales\Model\Order\Item $orderItem */
  174. foreach ($order->getAllVisibleItems() as $orderItem) {
  175. // turns out `getAllVisibleItems` is not reliable…
  176. if ($orderItem->getParentItem()) {
  177. continue;
  178. }
  179. $this->orderItemBuilder->setOrder($order);
  180. $this->orderItemBuilder->setOrderItem($orderItem);
  181. $orderItems[]= $this->orderItemBuilder->create();
  182. }
  183. if (strpos($order->getUpdatedAt(), '0000') === 0) {
  184. $updatedAt = $order->getCreatedAt();
  185. } else {
  186. $updatedAt = $order->getUpdatedAt();
  187. }
  188. // add data path to checkout fields by reading definitions from config
  189. $this->checkoutFieldContainerBuilder->setOrder($order);
  190. /** @var CheckoutFieldContainerInterface $checkoutFieldContainer */
  191. $checkoutFieldContainer = $this->checkoutFieldContainerBuilder->create();
  192. $this->_set(OrderInterface::CREATED_AT, $order->getCreatedAt());
  193. $this->_set(OrderInterface::ORDERED_AT, $order->getCreatedAt());
  194. $this->_set(OrderInterface::LAST_MODIFIED_AT, $updatedAt);
  195. $this->_set(OrderInterface::STATUS, $this->mapOrderState($order->getState()));
  196. $this->_set(OrderInterface::BILLING, $billingAddress);
  197. $this->_set(OrderInterface::RECIPIENT, $recipient);
  198. $this->_set(OrderInterface::ORDER_ITEMS, $orderItems);
  199. $this->_set(OrderInterface::CURRENCY, $order->getBaseCurrencyCode());
  200. $this->_set(OrderInterface::AMOUNT, $order->getBaseGrandTotal());
  201. $this->_set(OrderInterface::CHECKOUT_FIELDS, $checkoutFieldContainer->getFields());
  202. $this->_set(OrderInterface::SOURCE_REFERENCE, $order->getIncrementId());
  203. $this->_set(OrderInterface::SOURCE_ID, $order->getEntityId());
  204. $this->_set(OrderInterface::SOURCE_INCREMENT_ID, $order->getIncrementId());
  205. $this->_set(OrderInterface::SELECTED_EXPERIENCE_CODE, $methodCode);
  206. $this->_set(OrderInterface::SELECTED_EXPERIENCE_CURRENCY, $order->getBaseCurrencyCode());
  207. $this->_set(OrderInterface::SELECTED_EXPERIENCE_AMOUNT, $order->getBaseShippingAmount());
  208. $this->_set(OrderInterface::SELECTED_EXPERIENCE_LANGUAGE, 'en');
  209. $this->_set(OrderInterface::SELECTED_EXPERIENCE_DESCRIPTION, $order->getShippingDescription());
  210. }
  211. /**
  212. * @param CollectionPointSearchRequestInterface $searchRequest
  213. * @return void
  214. */
  215. public function setCollectionPointSearchRequest(CollectionPointSearchRequestInterface $searchRequest)
  216. {
  217. $this->_set(OrderInterface::COLLECTION_POINT_SEARCH_REQUEST, $searchRequest);
  218. }
  219. /**
  220. * @param QuoteCollectionPointInterface $collectionPoint
  221. * @return void
  222. */
  223. public function setCollectionPoint(QuoteCollectionPointInterface $collectionPoint)
  224. {
  225. $this->_set(OrderInterface::COLLECTION_POINT, $collectionPoint);
  226. }
  227. /**
  228. * @param PickupLocationSearchRequestInterface $isPickupLocationSearchRequest
  229. * @return void
  230. */
  231. public function setPickupLocationSearchRequest(PickupLocationSearchRequestInterface $isPickupLocationSearchRequest)
  232. {
  233. $this->_set(OrderInterface::PICKUP_LOCATION_SEARCH_REQUEST, $isPickupLocationSearchRequest);
  234. }
  235. /**
  236. * @param QuotePickupLocationInterface $pickupLocation
  237. * @return void
  238. */
  239. public function setPickupLocation(QuotePickupLocationInterface $pickupLocation)
  240. {
  241. $this->_set(OrderInterface::PICKUP_LOCATION, $pickupLocation);
  242. }
  243. }