【问题标题】:using Observer pattern with a MVC/Codeigniter web site在 MVC/Codeigniter 网站上使用观察者模式
【发布时间】:2011-08-10 18:20:36
【问题描述】:

我有一个网站要转换为 Codeigniter,我想简化和解耦。我喜欢我所读到的关于观察者模式的内容,例如“创建新调查”(触发新的帮助票证、触发电子邮件等)。

但是我如何在 Code Igniter 中实现这样的事情呢?我看到了 Symfony 组件,但此时我并不关心理解系统,而是关心如何在控制器和模型中使用它。由于其他原因,我已经扩展了 CI_Model 和 CI_Controller。将观察者模式代码放在那里是最好的吗?

我想像这样的一点:有人点击网站并产生一个请求,该请求被路由到控制器/动作:http://localhost/test/save_changes

// warning, pseudo-code!

class Test extends MY_Model
{
    public function __construct ()
    {
        // do I put this here?!? - or maybe in MY_Model?
        // Should it be a singleton?
        $this->load->library('dispatcher'); 
        // where do I attach what I want... here?
        $this->load->library('emailer');
        $this->dispatcher->attach($this->emailer); 
        // what if I have 50 possible things that might happen
        // based on any given event, from adding a user to 
        // deleting a survey or document? There has got to be a
        // way to attach a bunch of observers that trickle
        // down to each object, right?
    }

    public function save_changes ()
    {
         $this->load->model('user');
         $this->user->init($this->session->userdata('user.id'))->save();            
    }
}



class User extends MY_Model
{
    public function __construct ()
    {
        parent::__construct ();
        // do I put this here?!?
        $this->load->library('dispatcher'); // just something to call it
    }

    public function init($id)
    {
        if($this->_loadUser ($id))
        {
            $this->dispatcher->notify($this, 'user.loaded');
        }
    }

    public function save($id)
    {
        if(parent::save())
        {
            $this->dispatcher->notify($this, 'user.saved');
        }
    }



}

class Emailer
{
    public function update ($caller,$msg) 
    {
        switch ($msg)
        {
            case 'user.saved':
        // send user an email
        // re-cache some stuff
        // other things that we might want to do, including more of these:
        $this->dispatch->notify('user-saved-email-sent'); 
            break;
        }
    }
}

class Dispatcher
{
    public function notify ($caller, $msg) { ...foreach attached do $obj->update($caller,$msg) ...}
    public function attach ($obj) { ... }
    public function detach ($obj) { ... }
}

我可以看到那将是多么强大。但我不确定如何简化所有这些侦听器/观察器的设置和附加。

也许我应该有一个工厂来创建它们?看起来是的,它们将与当前的工作方式分离,但似乎管理我必须在每个控制器或方法中“附加”的所有不同对象将以不同的方式耦合。

谢谢, 汉斯

【问题讨论】:

    标签: codeigniter observer-pattern


    【解决方案1】:

    您提议的结构必须类似于:

    $this->load->library('observer_factory', 'of'); // factory for creating observers
    // Observer_factory would have knowledge/access to different classes which relate
    // to the pattern.
    $ync = $this->of->getNotifier( $some_variable ) );
    $ync->attach( $this->of->getObserver( $some_other_variable ) );
    $ync->attach( $this->of->getObserver( $some_final_variable ) );
    
    $ync->someMethod(); // someMethod calls notify
    

    但我想知道。您将拥有一个慢慢变得无所不知的工厂课程。它开始篡夺 Loader 的功能。当我的Observer_factory 可以通过做完全相同的事情来处理它时,为什么还要加载一个库?

    我认为你最好使用一个知道它应该做什么并且设计良好的库或模型,然后添加这个类结构。我认为收益不会超过成本。

    【讨论】:

    • 是的,我喜欢可以指导所有这些事件的应用程序核心的想法,但实际上我认为这不会那么容易。我想过走静态方法路线,并试图找出 Kohana 是如何做到的(但还没有时间详细查看)
    • 看起来 Kohana 从 3.0 中删除了它。唔。猜猜这意味着他们认为它效果不佳?人们仍然支持它,作为一个静态类,但它不再是一个核心模块。
    猜你喜欢
    • 2010-09-23
    • 2012-09-02
    • 1970-01-01
    • 2014-02-23
    • 1970-01-01
    • 2015-02-12
    • 2013-03-11
    • 2014-05-15
    • 2016-02-20
    相关资源
    最近更新 更多