-
Notifications
You must be signed in to change notification settings - Fork 9.4k
Description
Preconditions (*)
- Magento 2.3.0
- NewRelic module enabled (and configured)
(you can cheat around enabling the module, if set the newrelic enabled setting to true in the core_config_table and flush the cache afterwards)
Steps to reproduce (*)
- Run magento_newrelicreporting_cron cron job
Expected result (*)
- magento_newrelicreporting_cron cron job successful
Actual result (*)
- magento_newrelicreporting_cron throws error "Warning: Invalid argument supplied for foreach() in /var/www/shop_test/src/www/vendor/magento/module-configurable-product/Model/ResourceModel/Product/Type/Configurable/Product/Collection.php on line 83"
Explanation
The newrelic cron tries to get the amount of configurable products (or at least the given children) calling the getCount function of the ConfigurableProductManagementInterface.
In this process a configurable collection object is created (magento/module-configurable-product/Model/ResourceModel/Product/Type/Configurable/Product/Collection.php).
There the getSize function (in AbstractDB parent class) is called and as a consequence the _renderFilters function in the magento/module-configurable-product/Model/ResourceModel/Product/Type/Configurable/Product/Collection.php class.
Since 2.3.0 the product filter functionality seems to have been partly moved there with the probable intention to enable several product filters to be applicable at the same time.
Here the _renderFilters() function code:
protected function _renderFilters()
{
parent::_renderFilters();
$metadata = $this->getProductEntityMetadata();
$parentIds = [];
foreach ($this->products as $product) {
$parentIds[] = $product->getData($metadata->getLinkField());
}
$this->getSelect()->where('link_table.parent_id in (?)', $parentIds);
return $this;
}
The cause of the problem should be quite clear, if you look at the code. If no product filter is applied to the configurable product collection $this-products is null, but without any checks it is used in the given foreach-loop.
Proposed fix:
protected function _renderFilters()
{
parent::_renderFilters();
if ($this->products) {
$metadata = $this->getProductEntityMetadata();
$parentIds = [];
foreach ($this->products as $product) {
$parentIds[] = $product->getData($metadata->getLinkField());
}
$this->getSelect()->where('link_table.parent_id in (?)', $parentIds);
}
return $this;
}
A simple and reasonable if-clause does the trick without touching the changed (or "enhanced") product filter functionality.