执行扩展是否抛出 DbUpdateException?

Does Execute extension throw DbUpdateException?

我正在我的通用存储库中添加一个新方法来直接从数据库中删除一条记录,而不是通过 DbConext 然后调用它的 SaveChanges.

所以我做了:

    public virtual void Delete(int id)
    {
        var connection = dataContext.GetDatabase().Connection;
        var query = string.Format("DELETE FROM {0} WHERE id = {1}", tableName, id);

        connection.Execute(query);
    }

我当前使用 DbContext 句柄删除实体的代码 DbUpdateException,并且此异常冒泡到客户端。

Dapper 的 Execute 扩展是否也抛出此异常?

我知道这不是对实际问题的回答,但是恕我直言,你应该去

Finding the reason for DbUpdateException

这样,您就可以覆盖 Execute 方法,找到根本原因并彻底解决它。

  1. 不,不是;如果需要,您应该在 tsql 中的 delete 之后执行 select @@rowcount 之类的操作,使用 ExecuteScalar<int>,并检查返回的数字是否为 1。如果您想要时间戳检查,您可以将其包含在 where 子句中并作为参数

  2. 从不,从不,从不 将输入连接到 SQL 的数据部分;它会产生 SQL 注入风险,并破坏所有查询/操作缓存 - 不过,第一个原因是您应该需要的。这里有一些关于 table 名称的警告,但你应该在那里列入白名单。请注意,dapper 支持完全参数化(简单的参数处理是使用它的主要原因之一!)

例如,我会做类似的事情:

public YourType(string tableName) { // constructor
    WhiteList.AssertValid(tableName); // throws if not allowed
    deleteCommand = $"DELETE FROM [{tableName}] WHERE id = @id; SELECT @@ROWCOUNT;";
}
private readonly string deleteCommand;
public virtual void Delete(int id)
{
    var connection = dataContext.GetDatabase().Connection;
    int count = connection.ExecuteScalar<int>(deleteCommand, new { id });
    if(count != 0) throw new DbUpdateException();
}

或者,使用诸如 dapper-contrib 之类的附加工具,它可以为您完成所有这些工作。