lft 2015-04-19 14:22:31 2420次浏览 0条回复 0 0 0

我希望教程像“依赖注入”那章的方式来程现,先讲理念,结合例子,最后再讨论yii如何应用这知识的。。。好评

实践中的运用

当在应用程序的入口脚本中引入 Yii.php 文件时,Yii 就创建了一个 DI 容器。这个 DI 容器可以通过 [[Yii::$container]] 访问。当调用 [[Yii::createObject()]] 时,此方法实际上会调用这个容器的 [[yii\di\Container::get()|get()]] 方法创建新对象。如上所述,DI 容器会自动解决依赖关系(如果有)并将其注入新创建的对象中。因为 Yii 在其多数核心代码中都使用了 [[Yii::createObject()]] 创建新对象,所以你可以通过 [[Yii::$container]] 全局性地自定义这些对象。

例如,你可以全局性自定义 [[yii\widgets\LinkPager]] 中分页按钮的默认数量:

\Yii::$container->set('yii\widgets\LinkPager', ['maxButtonCount' => 5]); 这样如果你通过如下代码在一个视图里使用这个挂件,它的 maxButtonCount 属性就会被初始化为 5 而不是类中定义的默认值 10。

echo \yii\widgets\LinkPager::widget(); 然而你依然可以覆盖通过 DI 容器设置的值:

echo \yii\widgets\LinkPager::widget(['maxButtonCount' => 20]); 另一个例子是借用 DI 容器中自动构造方法注入带来的好处。假设你的控制器类依赖一些其他对象,例如一个旅馆预订服务。你可以通过一个构造器参数声明依赖关系,然后让 DI 容器帮你自动解决这个依赖关系。

namespace app\controllers;

use yii\web\Controller;
use app\components\BookingInterface;

class HotelController extends Controller
{
    protected $bookingService;

    public function __construct($id, $module, BookingInterface $bookingService, $config = [])
    {
        $this->bookingService = $bookingService;
        parent::__construct($id, $module, $config);
    }
}

如果你从浏览器中访问这个控制器,你将看到一个报错信息,提醒你 BookingInterface 无法被实例化。这是因为你需要告诉 DI 容器怎样处理这个依赖关系。

\Yii::$container->set('app\components\BookingInterface', 'app\components\BookingService'); 现在如果你再次访问这个控制器,一个 app\components\BookingService 的实例就会被创建并被作为第三个参数注入到控制器的构造器中。

    没有找到数据。
您需要登录后才可以回复。登录 | 立即注册