What causes the following error: Warning: Illegal string offset 'is_in_stock' … AdvancedInventory.php on line 87

magento.stackexchange https://magento.stackexchange.com/questions/181509

문제

During module development I've been writing a plugin which modifies the product options collection before it was loaded (adds a description field). Here is it:

etc/di.xml

<type name="Magento\Catalog\Model\ResourceModel\Product\Option\Collection">
    <plugin name="addOptionDescription" type="Vendor\Module\Plugin\Product\Option\Collection" sortOrder="10" disabled="false"/>
</type>

Code:

<?php
namespace Vendor\Module\Plugin\Product\Option;

use Vendor\Module\Model\OptionDescription;
use Magento\Catalog\Model\ResourceModel\Product\Option\Collection as OptionCollection;

class Collection
{
    /**
     * @var \Vendor\Module\Helper\Data
     */
    protected $helper;

    public function __construct(
        \Vendor\Module\Helper\Data $helper
    ) {
        $this->helper = $helper;
    }

    /**
     * @param OptionCollection $subject
     * @param bool $printQuery
     * @param bool $logQuery
     * @return array
     */
    public function beforeLoad($subject, $printQuery = false, $logQuery = false)
    {
        if (!$subject->isLoaded()) {
            $this->addDescriptionToResult($subject);
        }

        return [$printQuery, $logQuery];
    }

    /**
     * Add description to result
     *
     * If yo get error message "Warning: Illegal string offset 'is_in_stock' ... "
     * @see http://devdocs.magento.com/guides/v2.0/install-gde/trouble/php/tshoot_opcache.html
     *
     * @param OptionCollection $collection
     * @return OptionCollection $collection
     */
    private function addDescriptionToResult($collection)
    {
        $tableName = OptionDescription::TABLE_NAME;
        $joinDescriptionExpr = 'main_table.unique_option_id = option_description.unique_option_id AND option_description.store_id = 0';

        $collection->getSelect()->joinLeft(
            ['option_description' => $tableName],
            $joinDescriptionExpr,
            ['description' => 'description']
        );

        return $collection;
    }

    /**
     * Resolve current store id
     *
     * @return int
     */
    protected function getStoreId()
    {
        return $this->helper->resolveCurrentStoreId();
    }
}

Everything seems to be ok, but... When I try to load the existing product edit page (on backend) I see the following error:

Warning: Illegal string offset 'is_in_stock' in [...]/vendor/ magento/module-catalog-inventory/Ui/DataProvider/Product/Form/ Modifier/AdvancedInventory.php on line 87

In case I make changes as it is indicated in docs (set opcache.save_comments = 1 inside mine php-fpm config) everything works fine. But I can't understand, which code causes the error above and how can I prevent it without config modifications ?

도움이 되었습니까?

해결책

The ExtensionAttributesFactory (and not only) uses the dockblocks to determine "stuff". (not sure yet what exactly).
If you use OP cache, this means your php files will be cached, minified and will probably suffer other modifications.
By default the opcache does not save the comments in the minified version so $methodDocBlock = $methodReflection->getDocComment(); will return null and there is no way to find out meta data about the methods in a certain interface.

I know it's not a full answer, but the idea is in here. Magento uses the dockblocks to find out meta data about methods so you need to keep them.

라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 magento.stackexchange
scroll top