使用zend模型使用级联删除时运行函数

时间:2012-07-12 19:13:05

标签: zend-framework models

大家下午好,我会直截了当地说。我在我的模型中有这个代码:

protected $_referenceMap = Array (
    "Imagens" => Array(
        "columns"       => Array (
            'paiId'
        ),
        "refTableClass" => "ModeloImagem",
        "refColumns"    => Array(
            "id"
        ),
        "onDelete" => self::CASCADE
    )
);

我必须删除将要在级联上调用的表格中的图像,所以我想知道是否有类似的内容:

protected $_referenceMap = Array (
    "Imagens" => Array(
        "columns"       => Array (
            'paiId'
        ),
        "refTableClass" => "ModeloImagem",
        "refColumns"    => Array(
            "id"
        ),
        "onDelete" => function() {
            foreach($image as $i) {
                unlink($i);
            }
            return self::CASCADE
        }
    )
);

1 个答案:

答案 0 :(得分:1)

没有这样的事情。你可以做的是扩展Zend_Db_Table的方法_cascadeDelete($parentTableClassname, array $primaryKey)来执行函数。

这是一种方式,虽然这是一个可怕的代码重复数量;您可能必须指定要传递给回调的自己的数据,或者根据回调或查询是否失败来修改行为:

class My_Db_Table extends Zend_Db_Table
{
    const ON_DELETE_CALLBACK = 'onDeleteCallback';

    /**
     * Called by parent table's class during delete() method.
     *
     * @param  string $parentTableClassname
     * @param  array  $primaryKey
     * @return int    Number of affected rows
     */
    public function _cascadeDelete($parentTableClassname, array $primaryKey)
    {
        $rowsAffected = 0;
        foreach ($this->_getReferenceMapNormalized() as $map) {
            if ($map[self::REF_TABLE_CLASS] == $parentTableClassname && isset($map[self::ON_DELETE])) {
                switch ($map[self::ON_DELETE]) {
                    case self::CASCADE:
                        for ($i = 0; $i < count($map[self::COLUMNS]); ++$i) {
                            $col = $this->_db->foldCase($map[self::COLUMNS][$i]);
                            $refCol = $this->_db->foldCase($map[self::REF_COLUMNS][$i]);
                            $type = $this->_metadata[$col]['DATA_TYPE'];
                            $where[] = $this->_db->quoteInto(
                                $this->_db->quoteIdentifier($col, true) . ' = ?',
                                $primaryKey[$refCol], $type);
                        }
                        $this->_executeCallback($map, $where);
                        $rowsAffected += $this->delete($where);
                        break;
                    default:
                        // no action
                        break;
                }
            }
        }
        return $rowsAffected;
    }

    private function _executeCallback($map, $where) {
        if (isset($map[self::ON_DELETE_CALLBACK]) && is_callable($map[self::ON_DELETE_CALLBACK])) {
            call_user_func($map[self::ON_DELETE_CALLBACK], $where);
        }
    }
}

然后使用它来定义回调函数。但是你不能在回调函数中定义级联;否则,每当Zend_Db_Table试图找出是否从图像表中删除条目时,所有图像都会被删除。

protected $_referenceMap = Array (
    "Images" => Array(
        "columns"       => Array (
            'paiId'
        ),
        "refTableClass" => "ModeloImagem",
        "refColumns"    => Array(
            "id"
        ),
        "onDelete" => self::CASCADE,
        "onDeleteCallback" => function($where) {
            // Determine which image to unlink
            unlink($image);
        }
    )
);