Thank you Gunnar. This makes more sense now. I modified *BuildHql()* like
this:
public override HqlTreeNode BuildHql(MethodInfo method, Expression
targetObject, ReadOnlyCollection<Expression> arguments, HqlTreeBuilder
treeBuilder, IHqlExpressionVisitor visitor)
{
var target = targetObject ?? arguments[1];
var arg = targetObject != null ? arguments[1] : arguments[0];
HqlAlias alias = treeBuilder.Alias("x");
ParameterExpression param = Expression.Parameter(target.Type, "x");
HqlWhere where =
treeBuilder.Where(visitor.Visit(Expression.Lambda(Expression.Equal(target,
param), param)).AsExpression());
return treeBuilder.Exists
(
treeBuilder.Query
(
treeBuilder.SelectFrom
(
treeBuilder.From(treeBuilder.Range(visitor.Visit(arg),alias))
),
where
)
);
}
Now I'm getting an exception:
System.NotSupportedException : Specified method is not supported.
at
NHibernate.Hql.Ast.ANTLR.PolymorphicQuerySourceDetector.GetClassName(IASTNode
querySource)
at
NHibernate.Hql.Ast.ANTLR.PolymorphicQuerySourceDetector.Process(IASTNode
tree)
at NHibernate.Hql.Ast.ANTLR.AstPolymorphicProcessor.Process()
at
NHibernate.Hql.Ast.ANTLR.ASTQueryTranslatorFactory.CreateQueryTranslators(IASTNode
ast, String queryIdentifier, String collectionRole, Boolean shallow,
IDictionary`2 filters, ISessionFactoryImplementor factory)
at
NHibernate.Engine.Query.QueryPlanCache.GetHQLQueryPlan(IQueryExpression
queryExpression, Boolean shallow, IDictionary`2 enabledFilters)
at NHibernate.Impl.AbstractSessionImpl.GetHQLQueryPlan(IQueryExpression
queryExpression, Boolean shallow)
at NHibernate.Impl.AbstractSessionImpl.CreateQuery(IQueryExpression
queryExpression)
at NHibernate.Linq.DefaultQueryProvider.PrepareQuery(Expression
expression, ref IQuery query, ref NhLinqExpression nhQuery)
at NHibernate.Linq.DefaultQueryProvider.Execute(Expression expression)
at NHibernate.Linq.DefaultQueryProvider.Execute(Expression expression)
Any suggestions?
On Monday, September 28, 2015 at 11:15:20 PM UTC-7, Gunnar Liljas wrote:
>
> CollectionContainsGenerator works with the instance method Contains,
> whereas your generator works with the extension method Contains. Target is
> null, since the extension method is static. The actual "target" is
> therefore args[0].
>
>
>
> 2015-09-29 2:53 GMT+02:00 Alexey <[email protected] <javascript:>>:
>
>> Hi,
>>
>> I am trying to create a custom Hql Generator for Collection Contains
>> which would allow generating Hql from Linq's Contains overload with
>> IEqualityComparer. It should behave same as CollectionContains on SQL
>> server, but when expression tree is compiled and executed in memory, I
>> would like to be able to compare stings
>> with StringComparer.OrdinalIgnoreCase.
>>
>> Essentially I have a working statement
>>
>> a => operatorIds.Contains(a.OperatorId);
>>
>> which I want to turn into
>>
>> a => operatorIds.Contains(a.OperatorId, StringComparer.OrdinalIgnoreCase
>> );
>>
>> I found source code for Collection Contains and modified it like this:
>>
>> public class CollectionContainsWithComparerGenerator :
>> BaseHqlGeneratorForMethod
>> {
>> public CollectionContainsWithComparerGenerator()
>> {
>> SupportedMethods = new[]
>> {
>> ReflectionHelper.GetMethodDefinition(() =>
>> Enumerable.Contains<object>(null, null, null)),
>> };
>> }
>> public override HqlTreeNode BuildHql(MethodInfo method, Expression
>> targetObject, ReadOnlyCollection<Expression> arguments, HqlTreeBuilder
>> treeBuilder, IHqlExpressionVisitor visitor)
>> {
>> // TODO - alias generator
>> HqlAlias alias = treeBuilder.Alias("x");
>>
>> ParameterExpression param = Expression.Parameter(targetObject.Type, "x");
>> HqlWhere where = treeBuilder.Where(visitor.Visit(Expression.Lambda(
>> Expression.Equal(param, arguments[0]), param))
>> .AsExpression());
>>
>> return treeBuilder.Exists(
>> treeBuilder.Query(
>> treeBuilder.SelectFrom(
>> treeBuilder.From(
>> treeBuilder.Range(
>> visitor.Visit(targetObject),
>> alias)
>> )
>> ),
>> where));
>> }
>> }
>>
>> Basically, I kept the *BuildHql() *method AS-IS and only modified
>> signature for *SupportedMethod*. However, this generator throws null
>> reference exception because *targetObject* is null.
>>
>> I noticed that some generators use *targetObject *while others only use
>> *arguments
>> *but I still can't figure out why my generator won't work although it's
>> identical to CollectionContainsGenerator and how to modify it to fix.
>>
>> Any suggestions will help. I couldn't find any documentation on how to
>> build custom Hql generators.
>>
>> Thanks
>>
>> --
>>
>> ---
>> You received this message because you are subscribed to the Google Groups
>> "nhibernate-development" group.
>> To unsubscribe from this group and stop receiving emails from it, send an
>> email to [email protected]
>> <javascript:>.
>> For more options, visit https://groups.google.com/d/optout.
>>
>
>
--
---
You received this message because you are subscribed to the Google Groups
"nhibernate-development" group.
To unsubscribe from this group and stop receiving emails from it, send an email
to [email protected].
For more options, visit https://groups.google.com/d/optout.