[SQL] 어떻게 NHibernate에 단지 그것을 실행하지 않고 SQL을 생성 할 수 있습니다?
SQL어떻게 NHibernate에 단지 그것을 실행하지 않고 SQL을 생성 할 수 있습니다?
나는 show_sql 구성 옵션을 사용하여 런타임에 log4net / NLog에 SQL / 추적 창을 로그인하는 방법을 알고있다.
내가 찾고주고 쿼리
나는 Persister 클래스, 드라이버, 다른 인터셉터 및 이벤트를 통해 보았습니다. 에도 큰 도움이 될 것입니다 내 검색 범위를 좁혀 보면 너무 많은 장소가있다.
해결법
-
==============================
1.다음과 같은 방법으로 실행하지 않고 생성 된 SQL 쿼리를 얻을 수 있습니다 :
다음과 같은 방법으로 실행하지 않고 생성 된 SQL 쿼리를 얻을 수 있습니다 :
NHibernate.Linq 쿼리 :
public String GetGeneratedSql(System.Linq.IQueryable queryable, ISession session) { var sessionImp = (ISessionImplementor) session; var nhLinqExpression = new NhLinqExpression(queryable.Expression, sessionImp.Factory); var translatorFactory = new ASTQueryTranslatorFactory(); var translators = translatorFactory.CreateQueryTranslators(nhLinqExpression, null, false, sessionImp.EnabledFilters, sessionImp.Factory); return translators[0].SQLString; }
기준 쿼리 :
public String GetGeneratedSql(ICriteria criteria) { var criteriaImpl = (CriteriaImpl) criteria; var sessionImpl = (SessionImpl) criteriaImpl.Session; var factory = (SessionFactoryImpl) sessionImpl.SessionFactory; var implementors = factory.GetImplementors(criteriaImpl.EntityOrClassName); var loader = new CriteriaLoader((IOuterJoinLoadable) factory.GetEntityPersister(implementors[0]), factory, criteriaImpl, implementors[0], sessionImpl.EnabledFilters); return loader.SqlString.ToString(); }
QueryOver 쿼리 :
public String GetGeneratedSql(IQueryOver queryOver) { return GetGeneratedSql(queryOver.UnderlyingCriteria); }
HQL 질의의 경우 :
public String GetGeneratedSql(IQuery query, ISession session) { var sessionImp = (ISessionImplementor)session; var translatorFactory = new ASTQueryTranslatorFactory(); var translators = translatorFactory.CreateQueryTranslators(query.QueryString, null, false, sessionImp.EnabledFilters, sessionImp.Factory); return translators[0].SQLString; }
-
==============================
2.NHibernate에 5.2를 들어 경우에 당신이 (당신이 cmd.Parameters 모두 cmd.CommandText에서 SQL 및 제공된 매개 변수를 확인할 수 있도록) 실제 DbCommand 쿼리 준비보고 싶어 :
NHibernate에 5.2를 들어 경우에 당신이 (당신이 cmd.Parameters 모두 cmd.CommandText에서 SQL 및 제공된 매개 변수를 확인할 수 있도록) 실제 DbCommand 쿼리 준비보고 싶어 :
//For LINQ public IEnumerable<DbCommand> GetDbCommands<T>(IQueryable<T> query, ISession s) { return GetDbCommands(LinqBatchItem.Create(query), s); } //For HQL public IEnumerable<DbCommand> GetDbCommands(IQuery query, ISession s) { return GetDbCommands(new QueryBatchItem<object>(query), s); } //For QueryOver public IEnumerable<DbCommand> GetDbCommands(IQueryOver query, ISession s) { return GetDbCommands(query.RootCriteria, s); } //For Criteria public IEnumerable<DbCommand> GetDbCommands(ICriteria query, ISession s) { return GetDbCommands(new CriteriaBatchItem<object>(query), s); } //Adapted from Loader.PrepareQueryCommand private static IEnumerable<DbCommand> GetDbCommands(IQueryBatchItem item, ISession s) { var si = s.GetSessionImplementation(); item.Init(si); var commands = item.GetCommands(); foreach (var sqlCommand in commands) { var sqlString = sqlCommand.Query; sqlCommand.ResetParametersIndexesForTheCommand(0); var command = si.Batcher.PrepareQueryCommand(System.Data.CommandType.Text, sqlString, sqlCommand.ParameterTypes); RowSelection selection = sqlCommand.QueryParameters.RowSelection; if (selection != null && selection.Timeout != RowSelection.NoValue) { command.CommandTimeout = selection.Timeout; } sqlCommand.Bind(command, si); IDriver driver = si.Factory.ConnectionProvider.Driver; driver.RemoveUnusedCommandParameters(command, sqlString); driver.ExpandQueryParameters(command, sqlString, sqlCommand.ParameterTypes); yield return command; } }
-
==============================
3.NHibernate에 버전 3.4을 기반으로 LINQ 표현하는 방법은 다음과 같습니다
NHibernate에 버전 3.4을 기반으로 LINQ 표현하는 방법은 다음과 같습니다
public String GetGeneratedSql(System.Linq.IQueryable queryable, ISession session) { var sessionImp = (ISessionImplementor)session; var nhLinqExpression = new NhLinqExpression(queryable.Expression, sessionImp.Factory); var translatorFactory = new ASTQueryTranslatorFactory(); var translators = translatorFactory.CreateQueryTranslators(nhLinqExpression.Key, nhLinqExpression, null, false, sessionImp.EnabledFilters, sessionImp.Factory); var sql = translators.First().SQLString; var formamttedSql = FormatStyle.Basic.Formatter.Format(sql); int i = 0; var map = ExpressionParameterVisitor.Visit(queryable.Expression, sessionImp.Factory).ToArray(); formamttedSql = Regex.Replace(formamttedSql, @"\?", m => map[i++].Key.ToString().Replace('"', '\'')); return formamttedSql; }
-
==============================
4.다음은 NH 5.2 (상단의 HQL 부분이 해결되지 않는 투표를하게 나타났다 NH 4.0.4의 주요 변경)으로 HQL에서 SQL을 생성하는 방법을 수 있습니다 :
다음은 NH 5.2 (상단의 HQL 부분이 해결되지 않는 투표를하게 나타났다 NH 4.0.4의 주요 변경)으로 HQL에서 SQL을 생성하는 방법을 수 있습니다 :
public string HqlToSql(string hql, ISession session) { var sessionImp = (ISessionImplementor)session; var translatorFactory = new ASTQueryTranslatorFactory(); var translators = translatorFactory.CreateQueryTranslators(new NHibernate.Hql.StringQueryExpression(hql), null, false, sessionImp.EnabledFilters, sessionImp.Factory); var hqlSqlGenerator = new HqlSqlGenerator(((QueryTranslatorImpl)translators[0]).SqlAST, sessionImp.Factory); hqlSqlGenerator.Generate(); return hqlSqlGenerator.Sql.ToString(); }
from https://stackoverflow.com/questions/10704462/how-can-i-have-nhibernate-only-generate-the-sql-without-executing-it by cc-by-sa and MIT license
'SQL' 카테고리의 다른 글
[SQL] 데이터베이스에 섹스 (성별) 저장 (0) | 2020.04.13 |
---|---|
[SQL] MySQL의에서 관계를 만드는 방법 (0) | 2020.04.13 |
[SQL] 어떻게 먼저 특정 값으로 행을 반환합니까? (0) | 2020.04.13 |
[SQL] MySQL을 같이 여러 값 (0) | 2020.04.13 |
[SQL] MySQL의에서 기본 키를 제거 (0) | 2020.04.13 |