Dapper for NET Core:插入表并返回插入行的 id
Posted
技术标签:
【中文标题】Dapper for NET Core:插入表并返回插入行的 id【英文标题】:Dapper for NET Core: Insert into a table and return id of inserted row 【发布时间】:2018-06-01 21:05:36 【问题描述】:我的存储库中有以下方法。到目前为止,我相信返回的 int 只是表明操作是否成功的一个值。我希望 int 是成功执行后要返回的 id (这是表的单列)。我如何做到这一点?
public async Task<int> AddNewGroup()
using(_connection)
_connection.Open();
var id = await _connection.ExecuteAsync("INSERT INTO groups").Single();
【问题讨论】:
This 是关于 MS Access,但其他的还是一样的。 【参考方案1】:您可以运行包含 2 个部分的查询,第一个是 INSERT 部分,第二个是 SELECT 部分。在 SELECT 部分,您可以返回(选择)您想要的任何列值。
例如,如果您的组表有一个名为GroupId
的主键列,并且您已将该列设置为标识值生成(自动值生成),则可以调用SCOPE_IDENTITY()
来获取生成的值。
我们将使用QueryAsync
方法。
public async Task<int> AddNewGroup()
using(_connection)
_connection.Open();
var q = @"INSERT INTO Groups(Name,Description) VALUES
(@name, @desc); SELECT CAST(SCOPE_IDENTITY() as int)"
var result = await _connection.QueryAsync<int>(q,
new @name="some name", @desc="some desc");
return result.Single();
【讨论】:
【参考方案2】:您不必手动创建插入查询,您可以使用 Dapper.Contrib
github 来帮助您管理 CRUD 操作。
使用 Dapper.Contrib 您可以执行以下操作:
public async Task<int> AddNewGroup(Group entity)
using (_connection)
_connection.Open();
var id = await _connection.InsertAsync(entity);
【讨论】:
当标识列是 GUID 而不是自增 int 时,您知道解决方案吗? Dapper.Contrib 似乎只有返回 int 或 long 的 Insert 方法,但如果您想获取 Guid 作为插入结果,您可以使用 _connection.QueryFirstAsync public static void Main()
string sql = @"INSERT INTO Customers (CustomerName, ContactName, Address, City, PostalCode, Country)
Values (@CustomerName, @ContactName, @Address, @City, @PostalCode, @Country);
SELECT CustomerID FROM Customers WHERE CustomerID = SCOPE_IDENTITY();";
using (var connection = new SqlConnection(GetConnectionString()))
Customer c = new Customer("Brian Adams", "Brian", "12 Jones Place", "New York", "NY12", "CA");
var id = connection.QueryFirstOrDefault<int>(sql, c);
Console.WriteLine("The Customer ID is " + id);
sql = "Select * FROM CUSTOMERS WHERE CustomerID = @ID";
var rc = connection.QueryFirstOrDefault<Customer>(sql, new @ID = id );
【讨论】:
纯代码答案是低质量的答案。【参考方案4】:如果您使用的是 SQL Azure / SQL Server,则需要使用类似的方法从查询中返回插入的值
INSERT INTO groups OUTPUT inserted.id VALUES (...)
然后使用ExecuteAsync
使用ExecuteScalarAsync
此处引用 OUTPUT 子句: https://docs.microsoft.com/en-us/sql/t-sql/queries/output-clause-transact-sql?view=sql-server-2017
【讨论】:
【参考方案5】:我采取的“正确”方式是(显示使用 Guid Id 返回的存储库方法):
public async Task<Guid> CreateClient(ClientEntity clientModel)
const string sql = @"
INSERT INTO dbo.Clients
(
ClientCode,
Name,
IsActive
)
OUTPUT Inserted.ClientId
VALUES
(
@ClientCode,
@Name,
@IsActive
)";
using var dbConnection = await _databaseProvider.GetConnection();
var result = await dbConnection.ExecuteScalarAsync(sql, new
ClientCode = clientModel.Code,
Name = clientModel.Name,
IsActive = clientModel.IsActive
);
if (result != null)
return Guid.Parse(result.ToString());
else
return Guid.Empty;
【讨论】:
以上是关于Dapper for NET Core:插入表并返回插入行的 id的主要内容,如果未能解决你的问题,请参考以下文章