Magento 2 Documentation  2.3
Documentation for Magento 2 CMS v2.3 (December 2018)
ShippingMethodManagement.php
Go to the documentation of this file.
1 <?php
7 namespace Magento\Quote\Model;
8 
9 use Magento\Customer\Api\Data\AddressInterfaceFactory;
20 
26 class ShippingMethodManagement implements
30 {
36  protected $quoteRepository;
37 
43  protected $converter;
44 
50  protected $addressRepository;
51 
55  protected $totalsCollector;
56 
60  private $dataProcessor;
61 
65  private $addressFactory;
66 
70  private $quoteAddressResource;
71 
82  public function __construct(
84  Cart\ShippingMethodConverter $converter,
87  AddressInterfaceFactory $addressFactory = null,
88  QuoteAddressResource $quoteAddressResource = null
89  ) {
90  $this->quoteRepository = $quoteRepository;
91  $this->converter = $converter;
92  $this->addressRepository = $addressRepository;
93  $this->totalsCollector = $totalsCollector;
94  $this->addressFactory = $addressFactory ?: ObjectManager::getInstance()
95  ->get(AddressInterfaceFactory::class);
96  $this->quoteAddressResource = $quoteAddressResource ?: ObjectManager::getInstance()
97  ->get(QuoteAddressResource::class);
98  }
99 
103  public function get($cartId)
104  {
106  $quote = $this->quoteRepository->getActive($cartId);
107 
109  $shippingAddress = $quote->getShippingAddress();
110  if (!$shippingAddress->getCountryId()) {
111  throw new StateException(__('The shipping address is missing. Set the address and try again.'));
112  }
113 
114  $shippingMethod = $shippingAddress->getShippingMethod();
115  if (!$shippingMethod) {
116  return null;
117  }
118 
119  $shippingAddress->collectShippingRates();
121  $shippingRate = $shippingAddress->getShippingRateByCode($shippingMethod);
122  if (!$shippingRate) {
123  return null;
124  }
125  return $this->converter->modelToDataObject($shippingRate, $quote->getQuoteCurrencyCode());
126  }
127 
131  public function getList($cartId)
132  {
133  $output = [];
134 
136  $quote = $this->quoteRepository->getActive($cartId);
137 
138  // no methods applicable for empty carts or carts with virtual products
139  if ($quote->isVirtual() || 0 == $quote->getItemsCount()) {
140  return [];
141  }
142 
143  $shippingAddress = $quote->getShippingAddress();
144  if (!$shippingAddress->getCountryId()) {
145  throw new StateException(__('The shipping address is missing. Set the address and try again.'));
146  }
147  $shippingAddress->collectShippingRates();
148  $shippingRates = $shippingAddress->getGroupedAllShippingRates();
149  foreach ($shippingRates as $carrierRates) {
150  foreach ($carrierRates as $rate) {
151  $output[] = $this->converter->modelToDataObject($rate, $quote->getQuoteCurrencyCode());
152  }
153  }
154  return $output;
155  }
156 
160  public function set($cartId, $carrierCode, $methodCode)
161  {
163  $quote = $this->quoteRepository->getActive($cartId);
164  try {
165  $this->apply($cartId, $carrierCode, $methodCode);
166  } catch (\Exception $e) {
167  throw $e;
168  }
169 
170  try {
171  $this->quoteRepository->save($quote->collectTotals());
172  } catch (\Exception $e) {
173  throw new CouldNotSaveException(__('The shipping method can\'t be set. %1', $e->getMessage()));
174  }
175  return true;
176  }
177 
188  public function apply($cartId, $carrierCode, $methodCode)
189  {
191  $quote = $this->quoteRepository->getActive($cartId);
192  if (0 == $quote->getItemsCount()) {
193  throw new InputException(
194  __('The shipping method can\'t be set for an empty cart. Add an item to cart and try again.')
195  );
196  }
197  if ($quote->isVirtual()) {
198  throw new NoSuchEntityException(
199  __('The Cart includes virtual product(s) only, so a shipping address is not used.')
200  );
201  }
202  $shippingAddress = $quote->getShippingAddress();
203  if (!$shippingAddress->getCountryId()) {
204  // Remove empty quote address
205  $this->quoteAddressResource->delete($shippingAddress);
206  throw new StateException(__('The shipping address is missing. Set the address and try again.'));
207  }
208  $shippingAddress->setShippingMethod($carrierCode . '_' . $methodCode);
209  }
210 
214  public function estimateByAddress($cartId, \Magento\Quote\Api\Data\EstimateAddressInterface $address)
215  {
217  $quote = $this->quoteRepository->getActive($cartId);
218 
219  // no methods applicable for empty carts or carts with virtual products
220  if ($quote->isVirtual() || 0 == $quote->getItemsCount()) {
221  return [];
222  }
223 
224  return $this->getShippingMethods($quote, $address);
225  }
226 
230  public function estimateByExtendedAddress($cartId, AddressInterface $address)
231  {
233  $quote = $this->quoteRepository->getActive($cartId);
234 
235  // no methods applicable for empty carts or carts with virtual products
236  if ($quote->isVirtual() || 0 == $quote->getItemsCount()) {
237  return [];
238  }
239  return $this->getShippingMethods($quote, $address);
240  }
241 
245  public function estimateByAddressId($cartId, $addressId)
246  {
248  $quote = $this->quoteRepository->getActive($cartId);
249 
250  // no methods applicable for empty carts or carts with virtual products
251  if ($quote->isVirtual() || 0 == $quote->getItemsCount()) {
252  return [];
253  }
254  $address = $this->addressRepository->getById($addressId);
255 
256  return $this->getShippingMethods($quote, $address);
257  }
258 
271  protected function getEstimatedRates(
272  \Magento\Quote\Model\Quote $quote,
273  $country,
274  $postcode,
275  $regionId,
276  $region,
277  $address = null
278  ) {
279  if (!$address) {
280  $address = $this->getAddressFactory()->create()
281  ->setCountryId($country)
282  ->setPostcode($postcode)
283  ->setRegionId($regionId)
284  ->setRegion($region);
285  }
286  return $this->getShippingMethods($quote, $address);
287  }
288 
296  private function getShippingMethods(Quote $quote, $address)
297  {
298  $output = [];
299  $shippingAddress = $quote->getShippingAddress();
300  $shippingAddress->addData($this->extractAddressData($address));
301  $shippingAddress->setCollectShippingRates(true);
302 
303  $this->totalsCollector->collectAddressTotals($quote, $shippingAddress);
304  $shippingRates = $shippingAddress->getGroupedAllShippingRates();
305  foreach ($shippingRates as $carrierRates) {
306  foreach ($carrierRates as $rate) {
307  $output[] = $this->converter->modelToDataObject($rate, $quote->getQuoteCurrencyCode());
308  }
309  }
310  return $output;
311  }
312 
319  private function extractAddressData($address)
320  {
321  $className = \Magento\Customer\Api\Data\AddressInterface::class;
322  if ($address instanceof \Magento\Quote\Api\Data\AddressInterface) {
323  $className = \Magento\Quote\Api\Data\AddressInterface::class;
324  } elseif ($address instanceof EstimateAddressInterface) {
325  $className = EstimateAddressInterface::class;
326  }
327  return $this->getDataObjectProcessor()->buildOutputDataArray(
328  $address,
329  $className
330  );
331  }
332 
339  private function getDataObjectProcessor()
340  {
341  if ($this->dataProcessor === null) {
342  $this->dataProcessor = ObjectManager::getInstance()
343  ->get(DataObjectProcessor::class);
344  }
345  return $this->dataProcessor;
346  }
347 }
estimateByAddress($cartId, \Magento\Quote\Api\Data\EstimateAddressInterface $address)
elseif(isset( $params[ 'redirect_parent']))
Definition: iframe.phtml:17
$quote
$shippingAddress
Definition: order.php:40
__construct(\Magento\Quote\Api\CartRepositoryInterface $quoteRepository, Cart\ShippingMethodConverter $converter, \Magento\Customer\Api\AddressRepositoryInterface $addressRepository, \Magento\Quote\Model\Quote\TotalsCollector $totalsCollector, AddressInterfaceFactory $addressFactory=null, QuoteAddressResource $quoteAddressResource=null)
__()
Definition: __.php:13
getEstimatedRates(\Magento\Quote\Model\Quote $quote, $country, $postcode, $regionId, $region, $address=null)
$address
Definition: customer.php:38
$cartId
Definition: quote.php:22
$shippingMethod
Definition: popup.phtml:12
estimateByExtendedAddress($cartId, AddressInterface $address)
if($currentSelectedMethod==$_code) $className
Definition: form.phtml:31