using (var command = this.DbContext.Database.GetDbConnection().CreateCommand())
{
command.CommandText = "SELECT ... WHERE ...> @p1)";
command.CommandType = CommandType.Text;
var parameter = new SqlParameter("@p1",...);
command.Parameters.Add(parameter);
this.DbContext.Database.OpenConnection();
using (var result = command.ExecuteReader())
{
while (result.Read())
{
.... // Map to your entity
}
}
}
public static class Helper
{
public static List<T> RawSqlQuery<T>(string query, Func<DbDataReader, T> map)
{
using (var context = new DbContext())
{
using (var command = context.Database.GetDbConnection().CreateCommand())
{
command.CommandText = query;
command.CommandType = CommandType.Text;
context.Database.OpenConnection();
using (var result = command.ExecuteReader())
{
var entities = new List<T>();
while (result.Read())
{
entities.Add(map(result));
}
return entities;
}
}
}
}
用法:
public class TopUser
{
public string Name { get; set; }
public int Count { get; set; }
}
var result = Helper.RawSqlQuery(
"SELECT TOP 10 Name, COUNT(*) FROM Users U"
+ " INNER JOIN Signups S ON U.UserId = S.UserId"
+ " GROUP BY U.Name ORDER BY COUNT(*) DESC",
x => new TopUser { Name = (string)x[0], Count = (int)x[1] });
result.ForEach(x => Console.WriteLine($"{x.Name,-25}{x.Count}"));
18条答案
按热度按时间avwztpqn16#
目前,在efcore有新功能之前,我会使用命令并手动Map它
尝试使用sqlparameter来避免sql注入。
fromsql不适用于完整查询。例如,如果您想包含where子句,它将被忽略。
一些链接:
使用实体框架核心执行原始sql查询
原始sql查询
pexxcrt217#
在efcore中,您不能再执行“free”原始sql。您需要定义一个poco类和一个
DbSet
为了那个班。在您的情况下,您需要定义等级:因为它肯定是只读的,所以包含
.AsNoTracking()
打电话。编辑-ef core 3.0中的突破性变化:
dbquery()现在已经过时,应该(再次)使用dbset()。如果您有一个无键实体,即它不需要主键,则可以使用hasnokey()方法:
更多信息可以在这里找到
k2arahey18#
在其他答案的基础上,我编写了这个帮助程序来完成任务,包括示例用法:
用法:
我计划在添加了内置支持后立即将其删除。根据来自ef核心团队的arthur vickers的一份声明,这是2.0后的一个高度优先事项。这个问题正在这里追踪。