CDbMigration::update 在 foreach 循环中不起作用

CDbMigration::update does not work inside foreach loop

关注 this question。在 foreach 循环中使用 CDbMigration::update() 时出现问题。

此代码无法正常工作:

//This is executed inside Yii migration, so $this is CDbMigration.

foreach($idMap as $menuId=>$pageId)
{
    $this->update
    (
        'menus_items',
        array('link'=>'/content/show?id='.$pageId),
        array('id = '.$menuId)
    );
}

对于 $idMap 中的每个项目,$pageId 的值始终相同 并且等于 最后一项 $idMap 数组中的值。因此,每个菜单项都指向相同的 URL.

这段代码很有魅力:

foreach($idMap as $menuId=>$pageId)
{
    $sql = "UPDATE `menus_items` SET link = '/content/show?id=".$pageId."' WHERE id = ".$menuId."; ";

    Yii::app()->db->createCommand($sql)->execute();
}

对于 $idMap 中的每个项目,$pageId 的值总是 不同 并且等于当前项$idMap数组中的值。因此,每个菜单项都指向正确的URL.

在一个 SQL 查询中执行所有语句时也是如此:

$sql = '';

foreach($idMap as $menuId=>$pageId)
{
    $sql .= "UPDATE `menus_items` SET link = '/content/show?id=".$pageId."' WHERE id = ".$menuId."; ";
}

Yii::app()->db->createCommand($sql)->execute();

再一次,一切正常。

为什么使用 CDbMigration::update() 会失败,而直接 SQL 执行却很有效?

我认为您没有正确提供条件参数@ array('id = '.$menuId) 。如果你想像那样发送它,你应该使用一个字符串,把它放在一个数组中假设你正在映射一个键=>值对中的条件。此外,您应该将值约束用引号括起来 id = "$menuId".