如何查看nHibernate生成的SQL?

时间:2008-09-24 18:59:18

标签: nhibernate

如何查看nHibernate生成的SQL?版本1.2

10 个答案:

答案 0 :(得分:42)

您可以在app.config / web.config文件中输入类似的内容:

在configSections节点中:

<section name="log4net" type="log4net.Config.Log4NetConfigurationSectionHandler,log4net"/>

在配置节点中:

<log4net>
  <appender name="NHibernateFileLog" type="log4net.Appender.FileAppender">
    <file value="logs/nhibernate.txt" />
    <appendToFile value="false" />
    <layout type="log4net.Layout.PatternLayout">
      <conversionPattern value="%d{HH:mm:ss.fff} [%t] %-5p %c - %m%n"  />
    </layout>
  </appender>
  <logger name="NHibernate.SQL" additivity="false">
    <level value="DEBUG"/>
    <appender-ref ref="NHibernateFileLog"/>
  </logger>
</log4net>

不要忘记致电

log4net.Config.XmlConfigurator.Configure();

在您的应用程序启动时,或者

[assembly: log4net.Config.XmlConfigurator(Watch=true)]
在assemblyinfo.cs中

在配置设置中,将“show_sql”属性设置为true。

答案 1 :(得分:17)

在配置设置中,将“show_sql”属性设置为true。 这将导致SQL在NHibernate的日志文件中输出,由log4net提供。

答案 2 :(得分:7)

我知道我有点晚了,但是这样做的伎俩是独立的工具/数据库/框架。 我使用NH Interceptors

而不是那些有效的选项

首先,实现一个扩展 NHibernate.EmptyInterceptor 的类并实现 NHibernate.IInterceptor

using NHibernate;

namespace WebApplication2.Infrastructure
{
    public class SQLDebugOutput : EmptyInterceptor, IInterceptor
    {
        public override NHibernate.SqlCommand.SqlString
           OnPrepareStatement(NHibernate.SqlCommand.SqlString sql)
        {
            System.Diagnostics.Debug.WriteLine("NH: " + sql);

            return base.OnPrepareStatement(sql);
        }
    }
}

然后,只需在打开会话时传递实例。一定要在DEBUG中执行此操作:

public static void OpenSession() {

#if DEBUG
    HttpContext.Current.Items[SessionKey] = _sessionFactory.OpenSession(new SQLDebugOutput());

#else
    HttpContext.Current.Items[SessionKey] = _sessionFactory.OpenSession();

#endif
}

就是这样。

从现在开始,你的sql命令就像这些......

 var totalPostsCount = Database.Session.Query<Post>().Count();

 var currentPostPage = Database.Session.Query<Post>()
        .OrderByDescending(c => c.CreatedAt)
        .Skip((page - 1) * PostsPerPage)
        .Take(PostsPerPage)
        .ToList();

..直接显示在“输出”窗口中:

  

NH:从帖子post0_中选择强制转换(count(*)为INT)为col_0_0_

     

NH:选择post0_.Id为Id3_,post0_.user_id为user2_3_,post0_.Title为   Title3_,post0_.Slug as Slug3_,post0_.Content as Content3_,   post0_.created_at as created6_3_,post0_.updated_at as updated7_3_,   post0_.deleted_at as deleted8_3_来自帖子post0_ order by   post0_.created_at desc limit?偏移?

答案 3 :(得分:6)

使用sql server profiler。

编辑(1年后):正如@Toran Billups在下面所述,NHibernate简介Ayende写的非常酷。

答案 4 :(得分:5)

你也可以尝试NHibernate Profiler(30天试用,如果没有别的话)。这个工具是恕我直言的最佳工具。

这不仅会显示生成的SQL,还会显示警告/建议等等

答案 5 :(得分:3)

NHibernate日志记录有一个很好的参考:How to configure Log4Net for use with NHibernate。它包含有关记录所有NHibernate生成的SQL语句的信息。

答案 6 :(得分:1)

Nhibernate Profiler是一种选择,如果你必须做任何严肃的事情。

答案 7 :(得分:1)

如果您使用的是SQL Server(而不是Express),则可以尝试使用SQL Server Profiler。

答案 8 :(得分:0)

或者,如果您想显示特定查询的SQL,请使用以下方法(由hereRicardo Peres的建议稍作改动):

private String NHibernateSql(IQueryable queryable)
{
  var prov = queryable.Provider as DefaultQueryProvider;
  var session = prov.Session as ISession;

  var sessionImpl = session.GetSessionImplementation();
  var factory = sessionImpl.Factory;
  var nhLinqExpression = new NhLinqExpression(queryable.Expression, factory);
  var translatorFactory = new NHibernate.Hql.Ast.ANTLR.ASTQueryTranslatorFactory();
  var translator = translatorFactory.CreateQueryTranslators(nhLinqExpression, null, false, sessionImpl.EnabledFilters, factory).First();
  var sql = translator.SQLString;

  var parameters = nhLinqExpression.ParameterValuesByName;
  if ( (parameters?.Count ?? 0) > 0)
  {
    sql += "\r\n\r\n-- Parameters:\r\n";
    foreach (var par in parameters)
    {
      sql += "-- " + par.Key.ToString() + " - " + par.Value.ToString() + "\r\n";
    }
  }

  return sql;
}

并向其传递NHibernate查询,即

var query = from a in session.Query<MyRecord>()
  where a.Id == "123456" 
  orderby a.Name
  select a;

var sql = NHibernateSql(query);

答案 9 :(得分:0)

您只是要求查看;但是这个答案解释了如何将它记录到文件中。登录后,您可以在任何文本编辑器中查看。

NHibernate 的最新版本支持通过代码启用日志记录。以下是演示这一点的示例代码。请阅读评论以更好地理解。

Configuration configuration = new Configuration();

configuration.SetProperty(NHibernate.Cfg.Environment.Dialect, ......);
//Set other configuration.SetProperty as per need
configuration.SetProperty(NHibernate.Cfg.Environment.ShowSql, "true"); //Enable ShowSql
configuration.SetProperty(NHibernate.Cfg.Environment.FormatSql, "true"); //Enable FormatSql to make the log readable; optional.

configuration.AddMapping(......);
configuration.BuildMappings();

ISessionFactory sessionFactory = configuration.BuildSessionFactory();

//ISessionFactory is setup so far. Now, configure logging.
Hierarchy hierarchy = (Hierarchy)LogManager.GetRepository(Assembly.GetEntryAssembly());
hierarchy.Root.RemoveAllAppenders();

FileAppender fileAppender = new FileAppender();
fileAppender.Name = "NHFileAppender";
fileAppender.File = logFilePath;
fileAppender.AppendToFile = true;
fileAppender.LockingModel = new FileAppender.MinimalLock();
fileAppender.Layout = new PatternLayout("%d{yyyy-MM-dd HH:mm:ss}:%m%n%n");
fileAppender.ActivateOptions();

Logger logger = hierarchy.GetLogger("NHibernate.SQL") as Logger;
logger.Additivity = false;
logger.Level = Level.Debug;
logger.AddAppender(fileAppender);

hierarchy.Configured = true;

您可以根据需要进一步使用 FileAppenderLogger。有关详细信息,请参阅 this 答案和 this 资源。这解释了与 XML 配置相同的内容;但这同样适用于代码。