構成を読み取るときのMagento2循環依存性


8

ScopeConfigInterface $scopeConfig特定のオブジェクトを拡張するときに使用できない

di.xml

<preference for="Magento\Framework\Logger\Monolog" type="Foo\Log\Logger\FooLog" />

<virtualType name="helper" type="Foo\Log\Helper\Data" />

       <type name="Foo\Log\Logger\FooLog">
          <arguments>
             <argument name="helper" xsi:type="object">Foo\Log\Helper\Data</argument>
          </arguments>
       </type>

FooLog.php

    public function __construct(
     \Foo\Log\Helper\Data $dataHelper
   )
    {
        $this->_scopeConfig = $scopeConfig;
    }

Data.php

public function __construct(ScopeConfigInterface $scopeConfig)
{
    $this->_scopeConfig = $scopeConfig;
}

$this->_scopeConfig->getValue('dev/debug/foo_bar_config', 'default');

エラー:

Circular dependency: Magento\Store\Model\ResourceModel\Config\Collection\Scoped depends on Magento\Store\Model\ResourceModel\Config\Collection\Scoped and vice versa.

CreateOrder.phpのように既存の構成を取得することもできません。

 $this->scopeConfig->getValue(self::CONFIG_PATH_MERCHANT_ID, $this->sessionQuote->getStoreId());

問題は、次のScopeConfigInterface $scopeConfigような他のオブジェクトを拡張しようとすると、特定のオブジェクトにしか使用できないことです。

 <preference for="Magento\Cms\Controller\Index\Index" type="Foo\Log\Helper\Data" />

できます

*更新

プロキシクラスで試した-成功

<type name="Foo\Log\Helper\Data">
    <arguments>
        <argument name="configinterface" xsi:type="object">Magento\Framework\App\Config\ScopeConfigInterface\Proxy</argument>
    </arguments>
</type>

Data.php

        public function __construct(
    \Magento\Framework\App\Config\ScopeConfigInterface\Proxy $scopeConfig)
            {
                $this->_scopeConfig = $scopeConfig;
               $host =  $this->_scopeConfig->getValue('dev/debug/remote_server_host');
               // error after getValue
            }
}

回答:


17

あなたのエラーメッセージは:

循環依存:Magento \ Store \ Model \ ResourceModel \ Config \ Collection \ ScopedはMagento \ Store \ Model \ ResourceModel \ Config \ Collection \ Scopedに依存し、その逆も同様です。

何が起こるかを理解するには、エラーメッセージからクラスを確認する必要があります。 Magento\Store\Model\ResourceModel\Config\Collection\Scoped

そのコンストラクターには、 \Psr\Log\LoggerInterface

di.xmlで確認できるように、次の設定を作成しますMagento\Framework\Logger\Monolog<preference for="Magento\Framework\Logger\Monolog" type="Foo\Log\Logger\FooLog"/>

Magento\Framework\Logger\Monolog\Psr\Log\LoggerInterfaceそれ自体が好みです。したがって、の設定を効果的に作成する\Psr\Log\LoggerInterfaceと、作成されるたびにのFoo\Log\Logger\FooLogコンストラクタに提供\Magento\Store\Model\ResourceModel\Config\Collection\Scopedされます。

ScopeConfigInterfaceヘルパーによってリクエストされたの実装をさらに詳しく見てみると、それがに依存していることがわかり\Magento\Store\Model\ResourceModel\Config\Collection\Scopedます。

したがって、\Foo\Log\Logger\FooLogインスタンスを作成する必要がありScopedConfigInterface、それを必要とする状況を作成ScopedConfigInterfaceする必要\Magento\Store\Model\ResourceModel\Config\Collection\Scopedがありました\Foo\Log\Logger\FooLog。循環依存関係です。

これを解決するにScopeConfigInterfaceは、ヘルパーで使用しないか、それをProxy(レイジーオブジェクトロード)に置き換えて循環依存関係を解除する必要があります。

より情報的なメッセージを表示する、より良い循環依存検出アルゴリズムについて考えます。


うわー、これはたくさんのおかげでとても明確な説明です。これを解決するには:a)ScopeConfigInterfaceを使用せずに管理バックエンドから値を取得する別の方法はありますか?b)プロキシについて十分に理解していないと思います。ヘルパーでScopeConfigInterface \ Proxyを使用する必要がありますか、またはこれの意味は何ですか?それで、バックエンドから設定を使用したい場合、これを処理するために推奨される方法は何ですか?
xhallix 2015

回答にプロキシ/遅延読み込みのドキュメントへのリンクを追加
Anton Kril

ありがとう。最後に、プロキシを使用するか、scopeconfiginterfaceの使用を避け、代わりに他の方法を使用することをお勧めしますか?
xhallix

ScopeConfigInterfaceのプロキシを使用して、ロガーのインスタンス化中にScopeConfigInterfaceのインスタンス化を回避します
Anton Kril

私はScopeConfigInterfaceにプロキシを使用しましたが、これはこれを修正していないようです。最新の更新を参照してください
xhallix

2

di.xmlでは、di.xmlの循環依存チェックを行う設定または仮想タイプタグを使用できます。


答えてくれてありがとう、でも私はすでに好みを使いました。自分のモジュール内ではどういうわけか機能していません
xhallix '24
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.