【问题标题】:Is there a way to make table fields protected in Yii models to enforce getter/setters in the model?有没有办法在 Yii 模型中保护表字段以强制执行模型中的 getter/setter?
【发布时间】:2012-03-28 06:00:18
【问题描述】:

示例...

Person - 表格的字段:

  • id_person
  • 姓名

现在,假设我的代码中有模型 $person。我希望每次都被称为$person->name='TheName' Yii 调用我的自定义函数$person->setName('TheName'),强制执行setter。

有没有办法做到这一点?

我尝试将模型的属性设置为受保护/私有,但它不起作用。 Yii 似乎在之后调用 setter/getter 来检查该属性是否存在于表中。当属性存在时,yii 设置它并且不调用 setter。

提前致谢。

更新:原因是我已经在系统中多次使用 $model->attribX,但现在我需要根据 $model->attribX 以某种方式触发一些“链式”更新,但我没有想要通过类似 '$model->changeAttribX(...)' 的方式更改所有 '$model->attribX';

【问题讨论】:

    标签: php activerecord yii


    【解决方案1】:

    Yii 在CActiveRecord 中对__get__set 的实现与CComponent 中的“标准”不同;后者检查(并且更喜欢使用)属性的 getter 和 setter,而前者根本不这样做。

    要直接回答您的问题:您需要将此功能构建到您自己的类中,并以上述two implementations 作为指导,例如对于二传手来说有点像这样:

    public function setAttribute($name,$value)
    {
        $setter='set'.$name;
        if(method_exists($this,$setter))
            $this->$setter($value);
        else if(property_exists($this,$name))
            $this->$name=$value;
        else if(isset($this->getMetaData()->columns[$name]))
            $this->_attributes[$name]=$value;
        else
            return false;
    
        return true;
    }
    

    这个实现让 getter 和 setter 优先于裸属性,这可能是也可能不是你想要的。在像这样子类化CActiveRecord 之后,您将从子类中派生出您自己的模型。

    重要的考虑因素:同样,你没有说你想用这个功能实现什么,这会引发问题。例如,通常像这样的特性用于验证值,但 Yii 有自己的验证系统。 可能有更好(更像 Yii)的方式来做你想做的事。

    【讨论】:

    • 谢谢乔恩。我会仔细检查。它似乎解决了我的问题。关于原因,我已经更新了问题。
    【解决方案2】:

    我从您的问题中得到的是 - “我想在字段保存到数据库之前做一些事情”。如果这是问题所在,您可以覆盖 beforeSave() 方法。

    public function beforeSave() {
        if (count($this->name) > 100)
           echo "how come your name is so big?";
    
        return parent::beforeSave();
    }
    

    【讨论】:

      猜你喜欢
      • 2011-02-23
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2020-06-10
      • 2020-01-19
      相关资源
      最近更新 更多