首页 / C#开发 / 正文

[Entity Framework].NET/C#应用程序开发中如何查看EF(Entity Framework)生成的SQL语句?

4661 发布于: 2018-04-18 读完约需9分钟

问题描述

对于.NET/C#开发者来说,EF(Entity Framework)应该不会太陌生(如果不清楚什么是Entity Framework的同学,那么这篇文章可能不太适合你,请绕道)。

在使用Entity Framework的过程中,我们会很少与SQL正面接触了,因为最终的SQL语句是Entity Framework这个ORM组件帮助我们完成的。那么,我们如果需要查看Entity Framework生成的SQL语句,应该去哪里或者用什么方式来查看呢?

方案一

可以使用命名空间:System.Data.Objects下的ObjectQuery类的ToTraceString()方法,如下:

IQueryable query = from x in appEntities
             where x.id = 32
             select x;

var sql = ((System.Data.Objects.ObjectQuery)query).ToTraceString();

当然,如果在EF6或者更高版本中,我们可以使用类:System.Data.Entity.Core.Objects.ObjectQueryToTraceString()方法,如下:

var sql = ((System.Data.Entity.Core.Objects.ObjectQuery)query)
            .ToTraceString();

方案二

EF6或者更高版本中,提供了另外一种查看EF生成相应SQL语句的方式,即:设置context.Database.Log这个属性,这个属性可以设置SQL语句输出的方式(控制台,文件…),比如:

using (var context = new BlogContext()) 
{ 
    context.Database.Log = Console.Write; 

    var blog = context.Blogs.First(b => b.Title == "One Unicorn"); 

    blog.Posts.First().Title = "Green Eggs and Ham"; 

    blog.Posts.Add(new Post { Title = "I do not like them!" }); 

    context.SaveChangesAsync().Wait(); 
}

输出结果:

SELECT TOP (1)
    [Extent1].[Id] AS [Id],
    [Extent1].[Title] AS [Title]
    FROM [dbo].[Blogs] AS [Extent1]
    WHERE (N'One Unicorn' = [Extent1].[Title]) AND ([Extent1].[Title] IS NOT NULL)
-- Executing at 10/8/2013 10:55:41 AM -07:00
-- Completed in 4 ms with result: SqlDataReader

SELECT
    [Extent1].[Id] AS [Id],
    [Extent1].[Title] AS [Title],
    [Extent1].[BlogId] AS [BlogId]
    FROM [dbo].[Posts] AS [Extent1]
    WHERE [Extent1].[BlogId] = @EntityKeyValue1
-- EntityKeyValue1: '1' (Type = Int32)
-- Executing at 10/8/2013 10:55:41 AM -07:00
-- Completed in 2 ms with result: SqlDataReader

UPDATE [dbo].[Posts]
SET [Title] = @0
WHERE ([Id] = @1)
-- @0: 'Green Eggs and Ham' (Type = String, Size = -1)
-- @1: '1' (Type = Int32)
-- Executing asynchronously at 10/8/2013 10:55:41 AM -07:00
-- Completed in 12 ms with result: 1

INSERT [dbo].[Posts]([Title], [BlogId])
VALUES (@0, @1)
SELECT [Id]
FROM [dbo].[Posts]
WHERE @@ROWCOUNT > 0 AND [Id] = scope_identity()
-- @0: 'I do not like them!' (Type = String, Size = -1)
-- @1: '1' (Type = Int32)
-- Executing asynchronously at 10/8/2013 10:55:41 AM -07:00
-- Completed in 2 ms with result: SqlDataReader

注:使用此方式输出EF生成的SQL语句时,请确保你的项目程序处于调式模式(Debug Mode)。

当然,我们也可以将SQL语句输出到指定的文件中,如下:

using (var context = new BlogContext()) 
{  
    using (var sqlLogFile = new StreamWriter("C:\\temp\\LogFile.txt"))
    {          
         context.Database.Log = sqlLogFile.Write;     
         var blog = context.Blogs.First(b => b.Title == "One Unicorn"); 
         blog.Posts.First().Title = "Green Eggs and Ham"; 
         context.SaveChanges();
   }
}

方案三

直接使用IQueryable.ToString()方法,如下:

var result = from i in myContext.appEntities
             select new Model
             {
                 field = i.stuff,
             };
var sql = result.ToString();

注:此方法会直接生成一些变量(比如:plinq0),而不是具体的参数值。

版权声明:本作品系原创,版权归码友网所有,如未经许可,禁止任何形式转载,违者必究。

上一篇: [LINQ].NET/C#应用程序开发中如何使用LINQ实现查询集合List<T>中属性某个属性最大值的实体对象?

下一篇: [Entity Framework].NET/C#应用程序开发中如何获取由EF(Entity Framework)写入数据后生成的自增ID呢?

本文永久链接码友网 » [Entity Framework].NET/C#应用程序开发中如何查看EF(Entity Framework)生成的SQL语句?

分享扩散:

发表评论

登录用户才能发表评论, 请 登 录 或者 注册