PHP的Yii架構中行為的定義與Binder 方法講解,yii架構_PHP教程

來源:互聯網
上載者:User

PHP的Yii架構中行為的定義與Binder 方法講解,yii架構


定義行為

要定義行為,通過繼承 yii\base\Behavior 或其子類來建立一個類。如:

namespace app\components;use yii\base\Behavior;class MyBehavior extends Behavior{  public $prop1;  private $_prop2;  public function getProp2()  {    return $this->_prop2;  }  public function setProp2($value)  {    $this->_prop2 = $value;  }  public function foo()  {    // ...  }}

以上代碼定義了行為類 app\components\MyBehavior 並為要附加行為的組件提供了兩個屬性 prop1 、 prop2 和一個方法 foo()。注意屬性 prop2 是通過 getter getProp2() 和 setter setProp2() 定義的。能這樣用是因為 yii\base\Object 是 yii\base\Behavior 的祖先類,此祖先類支援用 getter 和 setter 方法定義屬性

提示:在行為內部可以通過 yii\base\Behavior::owner 屬性訪問行為已附加的組件。

靜態方法綁定行為

靜態繫結行為,只需要重載 yii\base\Component::behaviors() 就可以了。 這個方法用於描述類所具有的行為。如何描述呢? 使用配置來描述,可以是Behavior類名,也可以是Behavior類的配置數組:

namespace app\models;use yii\db\ActiveRecord;use app\Components\MyBehavior;class User extends ActiveRecord{  public function behaviors()  {    return [      // 匿名的行為,僅直接給出行為的類名稱      MyBehavior::className(),      // 名為myBehavior2的行為,也是僅給出行為的類名稱      'myBehavior2' => MyBehavior::className(),      // 匿名行為,給出了MyBehavior類的配置數組      [        'class' => MyBehavior::className(),        'prop1' => 'value1',        'prop3' => 'value3',      ],      // 名為myBehavior4的行為,也是給出了MyBehavior類的配置數組      'myBehavior4' => [        'class' => MyBehavior::className(),        'prop1' => 'value1',        'prop3' => 'value3',      ]    ];  }}

還有一個靜態綁定辦法,就是通過設定檔來綁定:

[  'as myBehavior2' => MyBehavior::className(),  'as myBehavior3' => [    'class' => MyBehavior::className(),    'prop1' => 'value1',    'prop3' => 'value3',  ],]

動態方法綁定行為

動態綁定行為,需要調用 yii\base\Compoent::attachBehaviors():

$Component->attachBehaviors([  'myBehavior1' => new MyBehavior, // 這是一個命名行為  MyBehavior::className(),     // 這是一個匿名行為]);

這個方法接受一個數組參數,參數的含義與上面靜態繫結行為是一樣一樣的。

在上面的這些例子中,以數組的鍵作為行為的命名,而對於沒有提供鍵名的行為,就是匿名行為。

對於命名的行為,可以調用 yii\base\Component::getBehavior() 來取得這個綁定好的行為:

$behavior = $Component->getBehavior('myBehavior2');

對於匿名的行為,則沒有辦法直接引用了。但是,可以擷取所有的綁定好的行為:

$behaviors = $Component->getBehaviors();

綁定的內部原理

只是重載一個 yii\base\Component::behaviors() 就可以這麼神奇地使用行為了? 這隻是冰山的一角,實際上關係到綁定的過程,有關的方面有:

yii\base\Component::behaviors()yii\base\Component::ensureBehaviors()yii\base\Component::attachBehaviorInternal()yii\base\Behavior::attach()

4個方法中,Behavior只佔其一,更多的代碼,是在Component中完成的。

yii\base\Component::behaviors() 上面講靜態方法綁定行為時已經提到了,就是返回一個數組用於描述行為。 那麼 yii\base\Component::ensuerBehaviors() 呢?

這個方法會在Component的諸多地方調用 __get() __set() __isset() __unset() __call() canGetProperty() hasMethod() hasEventHandlers() on() off() 等用到,看到這麼多是不是頭疼?一點都不複雜,一句話,只要涉及到類的屬性、方法、事件這個函數都會被調用到。

這麼眾星拱月,被諸多凡人所需要的 ensureBehaviors() 究竟是何許人也? 就像名字所表明的,他的作用在於“ensure” 。其實只是確保 behaviors() 中所描述的行為已經進行了綁定而已:

public function ensureBehaviors(){  // 為null表示尚未綁定  // 多說一句,為空白數組表示沒有綁定任何行為  if ($this->_behaviors === null) {    $this->_behaviors = [];    // 遍曆 $this->behaviors() 返回的數組,並綁定    foreach ($this->behaviors() as $name => $behavior) {      $this->attachBehaviorInternal($name, $behavior);    }  }}

這個方法主要是對子類用的, yii\base\Compoent 沒有任何預先注入的行為,所以,這個調用沒有用。 但是對於子類,你可能重載了 yii\base\Compoent::behaviros() 來預先注入一些行為。 那麼,這個函數會將這些行為先注入進來。

從上面的代碼中,自然就看到了接下來要說的第三個東東, yii\base\Component\attachBehaviorInternal():

private function attachBehaviorInternal($name, $behavior){  // 不是 Behavior 執行個體,說是只是類名、配置數組,那麼就建立出來吧  if (!($behavior instanceof Behavior)) {    $behavior = Yii::createObject($behavior);  }  // 匿名行為  if (is_int($name)) {    $behavior->attach($this);    $this->_behaviors[] = $behavior;  // 命名行為  } else {    // 已經有一個同名的行為,要先解除,再將新的行為綁定上去。    if (isset($this->_behaviors[$name])) {      $this->_behaviors[$name]->detach();    }    $behavior->attach($this);    $this->_behaviors[$name] = $behavior;  }  return $behavior;}

首先要注意到,這是一個private成員。其實在Yii中,所有尾碼為 *Internal 的方法,都是私人的。 這個方法幹了這麼幾件事:

如果 $behavior 參數並非是一個 Behavior 執行個體,就以之為參數,用 Yii::createObject() 建立出來。
如果以匿名行為的形式綁定行為,那麼直接將行為附加在這個類上。
如果是命名行為,先看看是否有同名的行為已經綁定在這個類上,如果有,用後來的行為取代之前的行為。
在 yii\base\Component::attachBehaviorInternal() 中, 以 $this 為參數調用了 yii\base\Behavior::attach() 。 從而,引出了跟綁定相關的最後一個傢伙 yii\base\Behavior::attach() , 這也是前面我們講行為的要素時沒講完的。先看看代碼:

public function attach($owner){  $this->owner = $owner;  foreach ($this->events() as $event => $handler) {    $owner->on($event, is_string($handler) ? [$this, $handler] :      $handler);  }}

上面的代碼幹了兩件事:

  • 設定好行為的 $owner ,使得行為可以訪問、操作所依附的對象
  • 遍曆行為中的 events() 返回的數組,將準備響應的事件,通過所依附類的 on() 綁定到類上

總結

說了這麼多,關於綁定,做個小結:

  • 綁定的動作從Component發起;
  • 靜態繫結通過重載 yii\base\Componet::behaviors() 實現;
  • 動態綁定通過調用 yii\base\Component::attachBehaviors() 實現;
  • 行為還可以通過為 Component 配置 as 配置項進行綁定;
  • 行為有匿名行為和命名行為之分,區別在於綁定時是否給出命名。 命名行為可以通過其命名進行標識,從而有針對性地進行解除等操作;
  • 綁定過程中,後綁定的行為會取代已經綁定的同名行為;
  • 綁定的意義有兩點,一是為行為設定 $owner 。二是將行為中擬響應的事件的handler綁定到類中去。

您可能感興趣的文章:

  • PHP的Yii架構中移除組件所綁定的行為的方法
  • 詳解在PHP的Yii架構中使用行為Behaviors的方法
  • 深入講解PHP的Yii架構中的屬性(Property)
  • PHP的Yii架構中使用資料庫的配置和SQL操作執行個體教程
  • 深入解析PHP的Yii架構中的event事件機制
  • 全面解讀PHP的Yii架構中的日誌功能
  • Yii使用find findAll尋找出指定欄位的實現方法
  • 解析yii資料庫的增刪查改
  • Yii PHP Framework實用入門教程(詳細介紹)
  • 詳解PHP的Yii架構中組件行為的屬性注入和方法注入

http://www.bkjia.com/PHPjc/1111897.htmlwww.bkjia.comtruehttp://www.bkjia.com/PHPjc/1111897.htmlTechArticlePHP的Yii架構中行為的定義與Binder 方法講解,yii架構 定義行為 要定義行為,通過繼承 yii\base\Behavior 或其子類來建立一個類。如: namespace a...

  • 聯繫我們

    該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

    如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

    A Free Trial That Lets You Build Big!

    Start building with 50+ products and up to 12 months usage for Elastic Compute Service

    • Sales Support

      1 on 1 presale consultation

    • After-Sales Support

      24/7 Technical Support 6 Free Tickets per Quarter Faster Response

    • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.