Skip to content

Commit

Permalink
FIX: out-of-stock options for configurable product visible on fronten…
Browse files Browse the repository at this point in the history
…d as sellable
  • Loading branch information
coderimus committed Jan 25, 2018
1 parent 5e4bb2b commit b349218
Show file tree
Hide file tree
Showing 3 changed files with 44 additions and 35 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -5,8 +5,8 @@
*/
namespace Magento\CatalogInventory\Model\ResourceModel\Stock;

use Magento\CatalogInventory\Model\Stock;
use Magento\CatalogInventory\Api\StockConfigurationInterface;
use Magento\CatalogInventory\Model\Stock;
use Magento\Framework\App\ObjectManager;

/**
Expand Down Expand Up @@ -46,19 +46,23 @@ class Status extends \Magento\Framework\Model\ResourceModel\Db\AbstractDb
* @param \Magento\Store\Model\WebsiteFactory $websiteFactory
* @param \Magento\Eav\Model\Config $eavConfig
* @param string $connectionName
* @param \Magento\CatalogInventory\Api\StockConfigurationInterface $stockConfiguration
*/
public function __construct(
\Magento\Framework\Model\ResourceModel\Db\Context $context,
\Magento\Store\Model\StoreManagerInterface $storeManager,
\Magento\Store\Model\WebsiteFactory $websiteFactory,
\Magento\Eav\Model\Config $eavConfig,
$connectionName = null
$connectionName = null,
$stockConfiguration = null
) {
parent::__construct($context, $connectionName);

$this->_storeManager = $storeManager;
$this->_websiteFactory = $websiteFactory;
$this->eavConfig = $eavConfig;
$this->stockConfiguration = $stockConfiguration ?: ObjectManager::getInstance()
->get(StockConfigurationInterface::class);
}

/**
Expand Down Expand Up @@ -204,7 +208,7 @@ public function getProductCollection($lastEntityId = 0, $limit = 1000)
*/
public function addStockStatusToSelect(\Magento\Framework\DB\Select $select, \Magento\Store\Model\Website $website)
{
$websiteId = $this->getStockConfiguration()->getDefaultScopeId();
$websiteId = $this->getWebsiteId($website->getId());
$select->joinLeft(
['stock_status' => $this->getMainTable()],
'e.entity_id = stock_status.product_id AND stock_status.website_id=' . $websiteId,
Expand All @@ -221,7 +225,7 @@ public function addStockStatusToSelect(\Magento\Framework\DB\Select $select, \Ma
*/
public function addStockDataToCollection($collection, $isFilterInStock)
{
$websiteId = $this->getStockConfiguration()->getDefaultScopeId();
$websiteId = $this->getWebsiteId();
$joinCondition = $this->getConnection()->quoteInto(
'e.entity_id = stock_status_index.product_id' . ' AND stock_status_index.website_id = ?',
$websiteId
Expand Down Expand Up @@ -255,7 +259,7 @@ public function addStockDataToCollection($collection, $isFilterInStock)
*/
public function addIsInStockFilterToCollection($collection)
{
$websiteId = $this->getStockConfiguration()->getDefaultScopeId();
$websiteId = $this->getWebsiteId();
$joinCondition = $this->getConnection()->quoteInto(
'e.entity_id = stock_status_index.product_id' . ' AND stock_status_index.website_id = ?',
$websiteId
Expand All @@ -277,6 +281,19 @@ public function addIsInStockFilterToCollection($collection)
return $this;
}

/**
* @param \Magento\Store\Model\Website $websiteId
* @return int
*/
private function getWebsiteId($websiteId = null)
{
if (null === $websiteId) {
$websiteId = $this->stockConfiguration->getDefaultScopeId();
}

return $websiteId;
}

/**
* Retrieve Product(s) status for store
* Return array where key is a product_id, value - status
Expand Down Expand Up @@ -335,18 +352,4 @@ public function getProductStatus($productIds, $storeId = null)
}
return $statuses;
}

/**
* @return StockConfigurationInterface
*
* @deprecated 100.1.0
*/
private function getStockConfiguration()
{
if ($this->stockConfiguration === null) {
$this->stockConfiguration = \Magento\Framework\App\ObjectManager::getInstance()
->get(\Magento\CatalogInventory\Api\StockConfigurationInterface::class);
}
return $this->stockConfiguration;
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -10,11 +10,11 @@
use Magento\Catalog\Api\Data\ProductInterface;
use Magento\Catalog\Api\Data\ProductInterfaceFactory;
use Magento\Catalog\Api\ProductRepositoryInterface;
use Magento\ConfigurableProduct\Model\Product\Type\Collection\SalableProcessor;
use Magento\Catalog\Model\Config;
use Magento\Catalog\Model\Product\Gallery\ReadHandler as GalleryReadHandler;
use Magento\ConfigurableProduct\Model\Product\Type\Collection\SalableProcessor;
use Magento\Framework\App\ObjectManager;
use Magento\Framework\EntityManager\MetadataPool;
use Magento\Catalog\Model\Product\Gallery\ReadHandler as GalleryReadHandler;

/**
* Configurable product type implementation
Expand Down Expand Up @@ -267,7 +267,6 @@ public function __construct(
$productRepository,
$serializer
);

}

/**
Expand Down Expand Up @@ -1277,6 +1276,8 @@ public function getSalableUsedProducts(\Magento\Catalog\Model\Product $product,
* Load collection on sub-products for specified configurable product
*
* Load collection of sub-products, apply result to specified configurable product and store result to cache
* Please note $salableOnly parameter is used for backwards compatibility because of deprecated method
* getSalableUsedProducts
* Number of loaded sub-products depends on $salableOnly parameter
* $salableOnly = true - result array contains only salable sub-products
* $salableOnly = false - result array contains all sub-products
Expand All @@ -1293,7 +1294,7 @@ private function loadUsedProducts(\Magento\Catalog\Model\Product $product, $cach
if (!$product->hasData($dataFieldName)) {
$usedProducts = $this->readUsedProductsCacheData($cacheKey);
if ($usedProducts === null) {
$collection = $this->getConfiguredUsedProductCollection($product);
$collection = $this->getConfiguredUsedProductCollection($product, false);
if ($salableOnly) {
$collection = $this->salableProcessor->process($collection);
}
Expand Down Expand Up @@ -1387,13 +1388,18 @@ private function getUsedProductsCacheKey($keyParts)
* Retrieve related products collection with additional configuration
*
* @param \Magento\Catalog\Model\Product $product
* @param bool $skipStockFilter
* @return \Magento\ConfigurableProduct\Model\ResourceModel\Product\Type\Configurable\Product\Collection
*/
private function getConfiguredUsedProductCollection(\Magento\Catalog\Model\Product $product)
{
private function getConfiguredUsedProductCollection(
\Magento\Catalog\Model\Product $product,
$skipStockFilter = true
) {
$collection = $this->getUsedProductCollection($product);
if ($skipStockFilter) {
$collection->setFlag('has_stock_status_filter', true);
}
$collection
->setFlag('has_stock_status_filter', true)
->addAttributeToSelect($this->getCatalogConfig()->getProductAttributes())
->addFilterByRequiredOptions()
->setStoreId($product->getStoreId());
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -8,20 +8,20 @@
use Magento\Catalog\Api\Data\ProductExtensionInterface;
use Magento\Catalog\Api\Data\ProductInterface;
use Magento\Catalog\Model\Config;
use Magento\ConfigurableProduct\Model\Product\Type\Configurable;
use Magento\Framework\EntityManager\EntityMetadata;
use Magento\Framework\EntityManager\MetadataPool;
use Magento\Customer\Model\Session;
use Magento\ConfigurableProduct\Model\ResourceModel\Product\Type\Configurable\Attribute\CollectionFactory;
use Magento\ConfigurableProduct\Model\ResourceModel\Product\Type\Configurable\Attribute\Collection;
use Magento\Catalog\Model\Product\Configuration\Item\Option\OptionInterface;
use Magento\Framework\Api\ExtensionAttribute\JoinProcessorInterface;
use Magento\ConfigurableProduct\Model\Product\Type\Collection\SalableProcessor;
use Magento\ConfigurableProduct\Model\Product\Type\Configurable;
use Magento\ConfigurableProduct\Model\Product\Type\Configurable\AttributeFactory;
use Magento\ConfigurableProduct\Model\ResourceModel\Product\Type\Configurable\Attribute\Collection;
use Magento\ConfigurableProduct\Model\ResourceModel\Product\Type\Configurable\Attribute\CollectionFactory;
use Magento\ConfigurableProduct\Model\ResourceModel\Product\Type\Configurable\Product\Collection as ProductCollection;
use Magento\ConfigurableProduct\Model\ResourceModel\Product\Type\ConfigurableFactory;
use Magento\Customer\Model\Session;
use Magento\Eav\Model\Entity\Attribute\Frontend\AbstractFrontend;
use Magento\Eav\Model\Entity\Attribute\Source\AbstractSource;
use Magento\ConfigurableProduct\Model\ResourceModel\Product\Type\Configurable\Product\Collection as ProductCollection;
use Magento\ConfigurableProduct\Model\Product\Type\Collection\SalableProcessor;
use Magento\Framework\Api\ExtensionAttribute\JoinProcessorInterface;
use Magento\Framework\EntityManager\EntityMetadata;
use Magento\Framework\EntityManager\MetadataPool;

/**
* @SuppressWarnings(PHPMD.LongVariable)
Expand Down

0 comments on commit b349218

Please sign in to comment.