C# 实体框架6-在调用SaveChanges之前,如何查看将为插入生成的SQL

C# 实体框架6-在调用SaveChanges之前,如何查看将为插入生成的SQL,c#,entity-framework,C#,Entity Framework,在Entity Framework 6中,是否可以在调用SaveChanges之前查看将为插入执行的SQL using (var db = new StuffEntities()){ db.Things.Add(new Thing({...}); //can I get the SQL insert statement at this point? db.SaveChanges(); } 我熟悉如何在执行前获取查询所生成的SQL,如下所示: var query = db

在Entity Framework 6中,是否可以在调用SaveChanges之前查看将为插入执行的SQL

using (var db = new StuffEntities()){
    db.Things.Add(new Thing({...});
    //can I get the SQL insert statement at this point?
    db.SaveChanges();
}
我熟悉如何在执行前获取查询所生成的SQL,如下所示:

var query = db.Thing.Where(x => x.ID == 9);
Console.WriteLine(query.ToString());
//this prints the SQL select statement

查询返回IQueryable,而insert返回DbSet,在DbSet上调用ToString只打印标准对象名

使用拦截器了解详细信息请参见此

将其添加到.config文件中


没有与
query.ToString()
AFAIK等价的函数。您最终可以使用属性:

db.Database.Log = s =>
{
    // You can put a breakpoint here and examine s with the TextVisualizer
    // Note that only some of the s values are SQL statements
    Debug.Print(s);
};
db.SaveChanges();
另一种选择(如果我正确理解您的问题的话)是使用一个实现,它似乎允许您在执行SQL命令之前检查它们(我对我的话避而不谈,因为我自己没有使用过这个)

大概是这样的:

public class CommandInterceptor : IDbCommandInterceptor
{
    public void NonQueryExecuting(
        DbCommand command, DbCommandInterceptionContext<int> interceptionContext)
    {
        // do whatever with command.CommandText
    }
}

在EF6中,在不更改代码的情况下使查询始终方便的最简单方法是将其添加到DbContext中,然后在调试时在VisualStudio的输出窗口中检查查询

protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
    Database.Log = (query)=> Debug.Write(query);
}
编辑


LINQPad也是调试Linq的一个很好的选项,它还可以显示SQL查询。

这不是在实际执行数据库操作之后才记录的吗,例如,在我调用SaveChanges之后?是的,如果需要了解更多信息,您可以查看此链接并覆盖用于自定义日志的>IDbConfigurationInterceptor。我的问题特别是在SQL执行之前查看SQL。我不知道它何时写入文件,但您可以在指定链接中的WriteThreadSafe方法中检查这一点,该方法在SQL执行之前事实上,它是有效的!您只需设置InterceptOnContext.Result,它就会停止数据库IO。谢谢DBD拦截不是吗DbInterceptor@Sven格罗森,你能给出一个有效的例子或链接吗?因为我有同样的问题,所以我试过你的方法,但没有工作。我可能遗漏了一些东西。@VishwajeetKulkarni,正如我在回答中所说的,我自己从来没有使用过这个,所以我不能提供一个有效的例子。许多其他人似乎已经根据反馈使其工作,请仔细检查您的实施情况。如果您仍然存在问题,请将其作为单独的问题提出,并参考此问题/答案。我不能代表EF6发言,但这在新的EF Core中似乎不起作用。请参阅:实体框架日志记录和拦截数据库操作(EF6以后的版本)此处:
static StuffEntities()
{
    Database.SetInitializer<StuffEntities>(null); // or however you have it
    System.Data.Entity.Infrastructure.Interception.DbInterception.Add(new CommandInterceptor());
}
protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
    Database.Log = (query)=> Debug.Write(query);
}