I am able to get all the available sizes of configurable product calling
getJsonConfig()
of below class
Magento\ConfigurableProduct\Block\Product\View\Type\Configurable;
But I need stock of each options.
You can simple get total stock of configurable products using objectManager.
$_product = $block->getProduct();
$objectManager = \Magento\Framework\App\ObjectManager::getInstance();
$StockState = $objectManager->get('\Magento\CatalogInventory\Api\StockStateInterface');
$total_stock = 0;
if($_product->getTypeID() == 'configurable'){
$productTypeInstance = $_product->getTypeInstance();
$usedProducts = $productTypeInstance->getUsedProducts($_product);
foreach ($usedProducts as $simple) {
$total_stock += $StockState->getStockQty($simple->getId(), $simple->getStore()->getWebsiteId());
}
}
echo $total_stock;
Thanks
Try following way:
app/code/SR/Stackexchange/etc/frontend/di.xml
<?xml version="1.0"?>
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:ObjectManager/etc/config.xsd">
<type name="Magento\ConfigurableProduct\Block\Product\View\Type\Configurable">
<plugin name="sr_configurable_product_configurable" type="SR\Stackexchange\Plugin\Block\ConfigurableProduct\Product\View\Type\Configurable" sortOrder="1"/>
</type>
</config>
app/code/SR/Stackexchange/Plugin/Block/ConfigurableProduct/Product/View/Type/Configurable.php
<?php
namespace SR\Stackexchange\Plugin\Block\ConfigurableProduct\Product\View\Type;
use Magento\Framework\Json\EncoderInterface;
use Magento\Framework\Json\DecoderInterface;
class Configurable
{
/**
* @var EncoderInterface
*/
protected $jsonEncoder;
/**
* @var DecoderInterface
*/
protected $jsonDecoder;
/**
* @var \Magento\CatalogInventory\Api\StockRegistryInterface
*/
protected $stockRegistry;
/**
* Configurable constructor.
*
* @param EncoderInterface $jsonEncoder
* @param DecoderInterface $jsonDecoder
* @param \Magento\CatalogInventory\Api\StockRegistryInterface $stockRegistry
*/
public function __construct(
EncoderInterface $jsonEncoder,
DecoderInterface $jsonDecoder,
\Magento\CatalogInventory\Api\StockRegistryInterface $stockRegistry
) {
$this->jsonDecoder = $jsonDecoder;
$this->jsonEncoder = $jsonEncoder;;
$this->stockRegistry = $stockRegistry;
}
public function aroundGetJsonConfig(
\Magento\ConfigurableProduct\Block\Product\View\Type\Configurable $subject,
\Closure $proceed
) {
$config = $proceed();
$config = $this->jsonDecoder->decode($config);
$productsCollection = $subject->getAllowProducts();
$stockInfo = array();
foreach ($productsCollection as $product) {
$productId = $product->getId();
$stockItem = $this->stockRegistry->getStockItem($product->getId());
if ($stockItem->getQty() <= 0 || !($stockItem->getIsInStock())) {
$stockInfo[$productId] = array(
"stockLabel" => __('Out of stock'),
"stockQty" => intval($stockItem->getQty()),
"is_in_stock" => false
);
} else {
$stockInfo[$productId] = array(
"stockLabel" => __('In Stock'),
"stockQty" => intval($stockItem->getQty()),
"is_in_stock" => true
);
}
}
$config['stockInfo'] = $stockInfo;
return $this->jsonEncoder->encode($config);
}
}
For multi-source inventory, above all code will give product QTY from default source. It will give problem when you have assigned different source to your website. Specially in Magento 2.3 and later.
Using MSI we can solve this problem.
app/code/[Vendor]/[Module]/etc/frontend/di.xml
<?xml version="1.0"?>
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:ObjectManager/etc/config.xsd">
<type name="Magento\ConfigurableProduct\Block\Product\View\Type\Configurable">
<plugin name="[vendor]_configurable_product_configurable"
type="[Vendor]\[Module]\Block\ConfigurableProduct\Product\View\Type\Configurable"
sortOrder="1"/>
</type>
</config>
[Vendor]/[Module]/Block/ConfigurableProduct/Product/View/Type/Configurable.php
<?php
namespace [Vendor]\[Module]\Block\ConfigurableProduct\Product\View\Type;
// To encode and decode config
use Magento\Framework\Json\EncoderInterface;
use Magento\Framework\Json\DecoderInterface;
// To get stock id for the website
use Magento\InventoryConfigurationApi\Api\GetStockItemConfigurationInterface;
use Magento\InventorySalesApi\Api\StockResolverInterface;
use Magento\Store\Model\StoreManagerInterface;
use Magento\InventorySalesApi\Api\Data\SalesChannelInterface;
// To get salable qty of product based on stock id
use Magento\InventorySalesApi\Api\GetProductSalableQtyInterface;
class Configurable
{
protected $jsonEncoder;
protected $jsonDecoder;
protected $getStockItemConfiguration;
protected $productSalableQty;
protected $stockResolver;
protected $storeManager;
public function __construct(
EncoderInterface $jsonEncoder,
DecoderInterface $jsonDecoder,
GetStockItemConfigurationInterface $getStockItemConfiguration,
GetProductSalableQtyInterface $productSalableQty,
StockResolverInterface $stockResolver,
StoreManagerInterface $storeManager
) {
$this->jsonDecoder = $jsonDecoder;
$this->jsonEncoder = $jsonEncoder;
$this->getStockItemConfiguration = $getStockItemConfiguration;
$this->productSalableQty = $productSalableQty;
$this->stockResolver = $stockResolver;
$this->storeManager = $storeManager;
}
// Adding Quantitites (product=>qty)
public function aroundGetJsonConfig(
\Magento\ConfigurableProduct\Block\Product\View\Type\Configurable $subject,
\Closure $proceed
)
{
$quantities = [];
$config = $proceed();
$config = $this->jsonDecoder->decode($config);
// get stock id
$websiteCode = $this->storeManager->getWebsite()->getCode();
$stock = $this->stockResolver->execute(SalesChannelInterface::TYPE_WEBSITE, $websiteCode);
$stockId = $stock->getStockId();
foreach ($subject->getAllowProducts() as $product) {
// get salable qty for each simple product for stockid
$quantities[$product->getId()] = $this->productSalableQty->execute($product->getSku(), $stockId);
}
$config['quantities'] = $quantities;
return $this->jsonEncoder->encode($config);
}
}