【问题标题】:Dynamic conjunction building for Nhibernate QueryOver in c#C# 中 Nhibernate QueryOver 的动态连接构建
【发布时间】:2016-01-05 09:21:54
【问题描述】:

我正在尝试为我的收藏构建一些过滤器构建器。

public static NHibernate.Criterion.Conjunction CreateConjunction<T>(this IEnumerable<FilterDescriptor> _filters)
        {
            NHibernate.Criterion.Conjunction conjunction = new NHibernate.Criterion.Conjunction();

            foreach (var filter in _filters)
            {
                PropertyInfo propertyInfoObj = typeof(T).GetProperty(filter.Member);
                conjunction.Add<T>(x => propertyInfoObj.GetValue(x, null) == filter.Value);
            }

            return conjunction;
        }

我当然可以说在调用连线时。Add 会抛出一个错误“变量 x”,类型为“Foo”,从范围“”引用,但它没有定义为 nhibernate queryOver'。

如何构建可以被 queryOver.Where() 接受的连词或表达式?

我正在寻找相当通用的解决方案来向我的 QueryOvers 添加过滤,有什么建议吗?

【问题讨论】:

  • 我现在没有时间创建完整的答案,但this post(免责声明:这是我的个人博客)可能会有所帮助。
  • 已经红了 :D 我决定改变我的方法,只使用基本表达式创建表达式构建器,因为没有像我上面介绍的那样使用 PropertyInfo 的选项。谢谢你关心安德鲁。
  • 好的--如果你弄明白了,在这里发布你的问题的答案肯定会有所帮助,以便其他人可以找到它

标签: c# nhibernate queryover nhibernate-criteria


【解决方案1】:

我确实使用标准 ald 构建了简单的表达式,看起来像这样:

public static void AddFilterCriteria<T>(this NHibernate.IQueryOver<T,T> _this, IEnumerable<Filter> _filters)
{
    foreach (var filter in _filters)
    {
        _this.And(GetCriterion(filter));
    }
}

public static NHibernate.Criterion.ICriterion GetCriterion(Filter _filter)
{
    if (_filter.Value is string)
    {
        return GetCriterionForString(_filter);
    }

    switch (_filter.Operator)
    {
        case eFilterOperator.IsEqualTo:
            {
                return NHibernate.Criterion.Expression.Eq(_filter.Member, _filter.Value);
            }
        case eFilterOperator.IsNotEqualTo:
            {
                return NHibernate.Criterion.Expression.Not(NHibernate.Criterion.Expression.Eq(_filter.Member, _filter.Value));
            }
        case eFilterOperator.IsGreaterThan:
            {
                return NHibernate.Criterion.Expression.Gt(_filter.Member, _filter.Value);
            }
        case eFilterOperator.IsGreaterThanOrEqualTo:
            {
                return NHibernate.Criterion.Expression.Ge(_filter.Member, _filter.Value);
            }
        case eFilterOperator.IsLessThan:
            {
                return NHibernate.Criterion.Expression.Lt(_filter.Member, _filter.Value);
            }
        case eFilterOperator.IsLessThanOrEqualTo:
            {
                return NHibernate.Criterion.Expression.Le(_filter.Member, _filter.Value);
            }
        default:
            throw new InvalidOperationException();
    }
}

字符串标准的构建有一些特殊的逻辑,但它的类比性和其余部分一样简单。 您可以构建连词、析取词并将它们作为 ICriteria 返回,例如:

case eFilterOperator.Contains:
                    {
                        NHibernate.Criterion.Conjunction conjunction = new NHibernate.Criterion.Conjunction();
                        conjunction.Add(NHibernate.Criterion.Expression.IsNotNull(_filter.Member)); 
                        conjunction.Add(NHibernate.Criterion.Expression.InsensitiveLike(_filter.Member, _filter.Value.ToString(), NHibernate.Criterion.MatchMode.Anywhere));
                        return conjunction;
                    }

一切正常,我不需要在应用过滤器之前从数据库中读取整个数据,这是我的目标。

PS Filter.Member 是字符串 Filter.Value 是对象 和运算符是枚举

【讨论】:

  • GetCriterionForString 在哪里??
猜你喜欢
  • 2023-03-20
  • 2011-12-19
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多