2

I created an API endpoint to use for shipping rate estimates.

However it only works for flat rates, neither free shipping, nor table rates show up.

I've added a product to the cart, and using the same country and zipcode, all rates show correctly.

My endpoint:

 public function getShippingEstimateCEP($sku, $qty, $cep)
    {
        $product = $this->productRepository->get($sku);
        $out = 'api GET: $sku ' . $sku . $cep;
        if($product->isSaleable())  {
            $store=$this->storeManager->getStore();
            $quote = $this->quoteFactory->create();
            $quote->setStoreId($this->getStoreId());
            $quote->setWebsiteId($this->getWebsiteId());
            $quote->setStore($store);

            $quote->getShippingAddress()->setCountryId('BR');
            $quote->getShippingAddress()->setPostcode($cep);
            $quote->setIsMultiShipping(false);    

            $quote->addProduct($product);
            $quote->collectTotals();
            $quote->getShippingAddress()->setCollectShippingRates(true);
            $quote->getShippingAddress()->collectShippingRates();
            $rates = $quote->getShippingAddress()->getShippingRatesCollection();

            foreach ($rates as $rate)
            {
                $out .= '[' . $rate->getPrice() . '||'.  $rate->getMethod() . '||'. $rate->getMethodTitle() . ']';
            }
        }

        return $out ;
    }
  • $quote = $this->checkoutSession->getQuote(); $address = $quote->getShippingAddress(); $address->collectShippingRates(); – Savan Patel May 1 at 13:07
0

Try this

I think you are missing getShippingAddress() in the collectTotals()

 public function getShippingEstimateCEP($sku, $qty, $cep)
    {
        $product = $this->productRepository->get($sku);
        $out = 'api GET: $sku ' . $sku . $cep;
        if($product->isSaleable())  {
            $store=$this->storeManager->getStore();
            $quote = $this->quoteFactory->create();
            $quote->setStoreId($this->getStoreId());
            $quote->setWebsiteId($this->getWebsiteId());
            $quote->setStore($store);

            $quote->getShippingAddress()->setCountryId('BR');
            $quote->getShippingAddress()->setPostcode($cep);
            $quote->setIsMultiShipping(false);    

            $quote->addProduct($product);
            $quote->collectTotals();
            $quote->getShippingAddress()->setCollectShippingRates(true);
            $quote->getShippingAddress()->collectShippingRates();
            $rates = $quote->getShippingAddress()->getAllShippingRates();

            foreach ($rates as $rate)
            {
                $out .= '[' . $rate->getPrice() . '||'.  $rate->getMethod() . '||'. $rate->getMethodTitle() . ']';
            }
        }

        return $out ;
    }
  • Doesn't work: Invalid method: ["Magento\\Quote\\Model\\Quote\\Address","collectTotals"] – localhost Apr 22 at 20:28
  • @localhost try updated answer – fmsthird Apr 22 at 22:57
  • Doesn't add the other methods. I directly edited the core ShippingMethodManagement.php file and used the quote instead of the cart and it failed just the same. Maybe the way the quote is created is wrong or missing something? – localhost Apr 23 at 12:53
0

Try this:

    $objectManager = \Magento\Framework\App\ObjectManager::getInstance();
    $api = $objectManager->create('Magento\Quote\Model\ShippingMethodManagement');       
    $listShipping = $api->estimateByExtendedAddress($quote->getId(), $quote->getShippingAddress());

To use this code, you need to save your quote first. Or you can look at the calculation in the ShippingMethodManagement for more detail.

  • I've tried copying ShippingMethodManagement model to my plugin and using it there, but it doesn't work. But if I edit the core ShippingMethodManagement, empty the current cart, add the product and address, don't save, then calculate the shipping, it works. But only by editing the vendor/magento/.../ShippingMethodManagement . – localhost May 2 at 12:36
  • I tried this and it works, however only for existing carts. So if there is no cart created in the session, it doesn't work. I could hardcode an old cart id, empty it then add products and calculate, but that's crazy. – localhost May 8 at 12:54
0

Creating a quote and getting an estimate in a REST API enpoint didn't work without hardcoding an old cart id, emptying it, then reusing it to get the estimates.

In the end I found it was better to use Magento's own API to:

  • Create a cart: POST rest/default/V1/guest-carts
  • Add items to cart: POST rest/default/V1/guest-carts/{cartId}/items
  • Get estimates: POST rest/default/V1/guest-carts/{cartId}/estimate-shipping-methods

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.