Yii-CComponent分析

— — — —Yii的CComponent是Yii的组件基础类。组件机制,是Yii整个体系的思想精髓,在使用Yii之前,最应该先了解其组件机制,如果不了解这个机制,那么阅读Yii源代码会非常吃力。组件机制给Yii框架赋予了无穷的灵活性和可扩展性,可以毫不夸张地说,Yii框架的基础结构就是组件。大到CApplication对象、控制器、路由管理器(urlManager),小到一些其它插件,均是以组件形式存在的。


—什么是Yii组件?

Yii中几乎所有可实例化并继承自CComponent的类,均可称为组件。


—组件的特点是什么?

继承自CComponent类(直接继承或间接继承),拥有事件及行为机制,可在配置文件中定义其各个属性。


—如何创建一个组件?

编写自定义类,并继承自CComponent/Component类即可。路径(\protected\components\***)。


————————CComponent getters和setters 的使用————————————————————————————————————————————————————————————————————

PHP属性的读和写


class MyClass
{
    // 隐藏属性
 
    private $property;
    // getter
    public function getProperty()
    {
        return $this->property;
    }
    
    // setter
    public function setProperty($value)
    {
        $this->property = $value;
    }
}
 
$object = new MyClass();
// 设置值
$object->setProperty('value');
 
// 获取值
echo $object->getProperty();

Yii 组件属性的读和写


class MyClass extends CComponent
{
    private $read = 'read only property';
    private $write = 'write only property';
    
    public function getRead()
    {
        return $this->read;
    }
    
    public function setWrite($value)
    {
        $this->write = $value;
    }
}
 
$object = new MyClass();
// 这里会报错,因为我们正试图写入只读属性。
$object->read = 'value';
 
// 显示 'read only property'
echo $object->read;
 
// 这里会报错,因为我们正试图读取只写属性。
echo $object->write;
 
// 将 'value' 写入私有变量 $write中去
$object->write = 'value';

为了允许像上面那种 属性风格 使用 getters 和 setters ,CComponent 使用PHP 魔术方法:__get,__set,__isset,和__unset

Yii深入地使用了这项技术。例如:当你调用Yii::app()->user->id 来获取当前登录用户id,实际上调用的是Yii::app()->getUser()->getId()。


__________________CComponent _事件的使用___________________________________________________________________________________________________


1. 定义事件名称,其实就是级组件定义一个on开头的方法,其中的代码是固定的,

public function onBeginRequest($event){
  
   //public void raiseEvent(string $name, CEvent $event)
   $this->raiseEvent('onBeginRequest',$event);

}

即函数名与事件名是一致的。此步的作用就是将绑定在此事件上的处理函数逐个执行。


2. 给组件对象绑定事件处理函数


$component->attachEventHandler($name, $handler);

$component->onBeginRequest = $handler ;


yii支持一个事件绑定多个回调函数,上述的两个方法都会在已有的事件上增加新的回调函数,而不会覆盖已有回调函数。$handler即是一个PHP回调函数。


3. 在需要触发事件的时候,直接激活组件的事件,即调用事件即可

________________________实例1_____________________________________________________


我们有一个博客应用程序,我们需要在有新评论(Comment)提交到博客(Post)的时候就发一份邮件。


Comment是个用Gii生成的标准AR模型。Post也同样是Gii生成的模型,除了一些自定义的方法。我们需要定义一个事件NewCommentEvent来存储Post和Comment 两个模型和句柄类Notifier,它将处理工作。


1.让我们开始创建protected/components/NewCommentEvent.php:


class NewCommentEvent extends CModelEvent {
    public $comment;
    public $post;
}

2.现在我们去看看protected/models/Post.php。为了突出显示添加了什么,我们省略了所有标准的AR方法。


class Post extends CActiveRecord {
    // 给添加评论到当前提交上定义方法
    function addComment(Comment $comment){
        $comment->post_id = $this->id;
 
        // 创建事件类实例
        $event = new NewCommentEvent($this);
        $event->post = $this;
        $event->comment = $comment;
        
        // 触发事件
        $this->onNewComment($event);
        return $event->isValid;
    }
 
    // 定义 onNewComment 事件
    public function onNewComment($event) {
        // 事实上事件是在这里触发的.这样的话我们可以使用
        // onNewComment 方法来取代 raiseEvent.
        $this->raiseEvent('onNewComment', $event);
    }
}

3.现在,实现Notifie。创建 protected/components/Notifier.php输入如下代码:


class Notifier {
    function comment($event){
        $text = "There was new comment from {$event->comment->author} 
on post {$event->post->title}";
        mail('[email protected]', 'New comment', $text);
    }
}

4.现在是时候在protected/controllers/PostController.php中一起进行操作了。


class PostController extends CController
{
    unction actionAddComment()
    {
        $post = Post::model()->findByPk(10);
        $notifier = new Notifier();
        
        // 附加事件句柄
        $post->onNewComment = array($notifier, 'comment');
        // 在真实的应用中,数据应来自$_POST
            $comment = new Comment();
            $comment->author = 'Sam Dark';
            $comment->text = 'Yii events are amazing!';
        // 添加评论
            $post->addComment($comment);
    }
}

5.所有的评论都将被添加后,管理员将会收到一份相关的邮件。














發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章