删除数据

class Cake\ORM\Table
Cake\ORM\Table::delete(Entity $entity, $options = [])

加载实体后,可以通过调用源表的 delete 方法来删除它。

// In a controller.
$entity = $this->Articles->get(2);
$result = $this->Articles->delete($entity);

删除实体时,会发生以下几件事。

  1. 将应用 删除规则。如果规则失败,将阻止删除。

  2. 将触发 Model.beforeDelete 事件。如果此事件被阻止,则删除将中止,并将返回事件的结果。

  3. 将删除实体。

  4. 将删除所有关联的依赖关系。如果关联被删除为实体,则将调度其他事件。

  5. 将删除 BelongsToMany 关联的所有联接表记录。

  6. 将触发 Model.afterDelete 事件。

默认情况下,所有删除都发生在事务中。可以使用 atomic 选项禁用事务。

$result = $this->Articles->delete($entity, ['atomic' => false]);

$options 参数支持以下选项。

  • atomic 默认值为 true。如果为 true,则删除将发生在事务中。

  • checkRules 默认值为 true。在删除记录之前检查删除规则。

级联删除

删除实体时,也可以删除关联数据。如果你的 HasOne 和 HasMany 关联被配置为 dependent,则删除操作也将级联到这些实体。默认情况下,关联表中的实体使用 Cake\ORM\Table::deleteAll() 删除。可以通过将 cascadeCallbacks 选项设置为 true 来选择让 ORM 加载相关实体并单独删除它们。启用这两个选项的 HasMany 关联示例如下所示。

// In a Table's initialize method.
$this->hasMany('Comments', [
    'dependent' => true,
    'cascadeCallbacks' => true,
]);

注意

cascadeCallbacks 设置为 true,与批量删除相比,会导致删除速度明显变慢。仅当应用程序有事件监听器处理的重要工作时,才应启用 cascadeCallbacks 选项。

批量删除

Cake\ORM\Table::deleteMany($entities, $options = [])

如果要删除一组实体,可以使用 deleteMany() 在单个事务中删除它们。

// Get a boolean indicating success
$success = $this->Articles->deleteMany($entities);

// Will throw a PersistenceFailedException if any entity cannot be deleted.
$this->Articles->deleteManyOrFail($entities);

这些方法的 $optionsdelete() 相同。使用这些方法删除记录**将**触发事件。

Cake\ORM\Table::deleteAll($conditions)

有时,逐行删除行效率不高或无用。在这种情况下,使用批量删除一次删除多行会更高效。

// Delete all the spam
function destroySpam()
{
    return $this->deleteAll(['is_spam' => true]);
}

如果删除了 1 行或多行,则批量删除将被视为成功。函数以整数形式返回已删除记录的数量。

警告

deleteAll 不会触发 beforeDelete/afterDelete 事件。如果需要触发回调,请先使用 find() 加载实体,然后在循环中删除它们。

严格删除

Cake\ORM\Table::deleteOrFail($entity, $options = [])

使用此方法将在以下情况下抛出 Cake\ORM\Exception\PersistenceFailedException

  • 实体是新的。

  • 实体没有主键值。

  • 应用程序规则检查失败。

  • 删除被回调中止。

如果要跟踪未删除的实体,可以使用 Cake\ORMException\PersistenceFailedException::getEntity() 方法。

try {
    $table->deleteOrFail($entity);
} catch (\Cake\ORM\Exception\PersistenceFailedException $e) {
    echo $e->getEntity();
}

由于它在内部执行 Cake\ORM\Table::delete() 调用,因此将触发所有相应的删除事件。