编程开源技术交流,分享技术与知识

网站首页 > 开源技术 正文

Entity Framework Core执行存储过程

wxchong 2024-07-11 01:08:22 开源技术 10 ℃ 0 评论

这节讲解EF Core中使用FromSqlRaw()& ExecuteCommand() 反复执行存储过程

1 存储过程

下面存储过程返回指定 name和standard 所有学生,name&standard值通过存储过程的输入参数提供

CREATE PROCEDURE [dbo].[sp_GetStudents] @Name VARCHAR(50), @Standard INTASBEGIN SELECT * FROM Student Where Name=@Name AND Standard=@StandardEND

Entity Framework Core 使用FromSqlRaw() 方法执行存储过,使用FromSqlRaw()方法时必须为存储过程提供两个参数,因此我们必须使用SqlParameter 数组设置参数

SqlParameter类位于Microsoft.Data.SqlClient命名空间内,下面代码执行存储过程
var param = new SqlParameter[] { new SqlParameter() { ParameterName = "@Name", SqlDbType = System.Data.SqlDbType.VarChar, Size = 100, Direction = System.Data.ParameterDirection.Input, Value = "Tony" }, new SqlParameter() { ParameterName = "@Standard", SqlDbType = System.Data.SqlDbType.Int, Direction = System.Data.ParameterDirection.Input, Value = 10 }};List<Student> studentList = context.Student.FromSqlRaw("[dbo].[sp_GetStudents] @Name, @Standard", param).ToList();

2 存储过程返回多个数据集

.FromSqlRaw()方法将从存储过程中获取一条记录,如果存储过程返回多个数据集,我们使用 ExecuteReader() 方法

下面存储过程返回两组数据集,一个是Student表,另一个是StudentAddress表

CREATE PROCEDURE [dbo].[sp_MultiRecordSets] @IdStu INT, @IdAdd INT ASBEGIN SELECT * FROM Student Where Id=@IdStu  SELECT * FROM StudentAddress WHERE Id=@IdAddEND
下面代码显示了如何使用ExecuteReader() 方法从这两组数据中获取值
var param = new SqlParameter[] { new SqlParameter() { ParameterName = "@IdStu", SqlDbType = System.Data.SqlDbType.Int, Direction = System.Data.ParameterDirection.Input, Value = 5 }, new SqlParameter() { ParameterName = "@IdAdd", SqlDbType = System.Data.SqlDbType.Int, Direction = System.Data.ParameterDirection.Input, Value = 10 }};var context = new SchoolContext();using (var cnn = context.Database.GetDbConnection()){ var cmm = cnn.CreateCommand(); cmm.CommandType = System.Data.CommandType.StoredProcedure; cmm.CommandText = "[dbo].[sp_MultiRecordSets]"; cmm.Parameters.AddRange(param); cmm.Connection = cnn; cnn.Open(); var reader = cmm.ExecuteReader(); while (reader.Read()) { // name from student table  string studentName= Convert.ToString(reader["Name"]);  } reader.NextResult(); //move the next record set while (reader.Read()) { // city from student address table string city = Convert.ToString(reader["City"]);  }}
注意使用NextResult()移动到下一组数据集

EF Core中三个最重要的概念:

1 DbContext类

2 Migrations

3 Fluent APIs

3 使用ExecuteSqlRawAsync()执行存储过程和原生SQL

EF Core使用ExecuteSqlRawAsync() 方法执行存储过程和原生SQL,但是不像FromSqlRaw()方法,它返回受影响的行数,注意也有一个ExecuteSqlRaw() 同步版本类型的方法
var rowsAffected = await context.Database.ExecuteSqlRawAsync("Update Students set Name = 'Donald Trump' where Id = 5");

4 使用ExecuteSqlRawAsync()输出存储过程参数

我们使用存储过程返回生总个数(@TotalStudents)

CREATE PROCEDURE [dbo].[sp_GetStudentsNew] @Name VARCHAR(50), @Standard INT, @TotalStudents INT OUTPUTASBEGIN SELECT * FROM Student Where Name=@Name AND Standard=@Standard SET @TotalStudents= (SELECT COUNT(*) FROM Student)END
为了执行存储过程在EF Core,我们需要指定SqlParameter参数的输出方向
new SqlParameter() { ParameterName = "@TotalStudents", SqlDbType = System.Data.SqlDbType.Int, Direction = System.Data.ParameterDirection.Output, // direction output}
每次执行存储过程时,我们能通过输出参数获取到返回的值:
int totalStudents = Convert.ToInt32(Convert.ToString(param[2].Value));
注意:参数的开始索引是0,总共有三个参数,最后一个参数是输出参数
var context = new SchoolContext();var param = new SqlParameter[] { new SqlParameter() { ParameterName = "@Name", SqlDbType = System.Data.SqlDbType.VarChar, Size = 100, Direction = System.Data.ParameterDirection.Input, Value = "Tony" }, new SqlParameter() { ParameterName = "@Standard", SqlDbType = System.Data.SqlDbType.Int, Direction = System.Data.ParameterDirection.Input, Value = 10 }, new SqlParameter() { ParameterName = "@TotalStudents", SqlDbType = System.Data.SqlDbType.Int, Direction = System.Data.ParameterDirection.Output, }};int affectedRows = await context.Database.ExecuteSqlRawAsync("[dbo].[sp_GetStudentsNew] @Name, @Standard, @TotalStudents out", param);int totalStudents = Convert.ToInt32(param[2].Value); 

本文暂时没有评论,来添加一个吧(●'◡'●)

欢迎 发表评论:

最近发表
标签列表