繁体   English   中英

在Phalcon中附加一个相关的模型

[英]append a related Model in Phalcon

我在PHP中用Phalcon编写了一个vcard类。 vCard模型初始化如下。

// Inside the BS_VCard class
public function initialize(){
    $this->hasMany("id","BS_VCardElement","vCardId",array(
        "alias" => "elements",
        'foreignKey' => array(
            'action' => Phalcon\Mvc\Model\Relation::ACTION_CASCADE
        )
    ));
}

它的元素是这样初始化的

// Inside the BS_VCardElement class
public function initialize(){
    $this->belongsTo("vCardId","BS_VCard","id",array("alias" => "vCard"));
    ...
}

如果用户读取vCard并添加另一个元素,则它无法按预期工作。 为了简化使用,我添加了一些像这样的fascade方法

public function addDateOfBirth($date){
    $element = new BS_VCardElement();
    $element->setName("BDAY");
    $element->addValue($date);
    // This doesn't work
    $this->elements[] = $element;
}

Docs / Storing相关记录没有解释如何将这样的新数据附加到相关表中。

我也尝试过这个

$this->elements[] = array_merge($this->elements,array($element));

但是save方法似乎忽略了添加的元素。 Save()返回true。

这个问题已在几个月前被问过,但自从我遇到类似的问题后,我决定分享我的结果。

这就是我发现的。 小写别名('elements')似乎不起作用,而大写别名('Elements')则起作用。

要添加一个元素,您可以执行此操作;

$this->Elements = $element;

要添加多个元素,您可以执行此操作;

$elements = array($element1, $element2);
$this->Elements = $elements;

之后,您必须在再次访问元素之前保存vcard。 如果不这样做,phalcon将只返回一个只包含数据库中已有元素的结果集。 (不确定这是否可以某种方式改变。)

这里是文档(没有提到所有这些): http//docs.phalconphp.com/en/latest/reference/models.html#storing-related-records

根据Phalcon源代码 ,Resultset对象是不可移植的。

/**
 * Resultsets cannot be changed. It has only been implemented to 
 * meet the definition of the ArrayAccess interface
 *
 * @param int index
 * @param \Phalcon\Mvc\ModelInterface value
 */
public function offsetSet(var index, var value)
{
    throw new Exception("Cursor is an immutable ArrayAccess object");
}

看来用数组替换元素是实现“追加”或修改结果集的唯一方法(除了支持IS的删除)。

当然这打破了\\Phalcon\\Mvc\\Model::_preSaveRelatedRecords()因为该函数忽略了类属性并从模型管理器中重新获取相关(并在最后重置了model::$element属性)。

我对此感到沮丧,因为将对象附加到集合看起来像是一个非常常见的任务,并且没有一个明确的方法向父母添加新项目似乎是一个设计缺陷。

我认为相关元素在设置属性时可能会调用一些神奇的功能,所以简单地使用$ this-> elements [](显然)不起作用。 也许尝试重新设置整个变量:

public function addDateOfBirth($date){
    $element = new BS_VCardElement();
    $element->setName("BDAY");
    $element->addValue($date);

    $elements = $this->elements;
    $elements[] = $element;
    $this->elements = $elements;
}

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM