Деревья выражений в Linq To Entities - PullRequest
1 голос
/ 02 марта 2012

Я пытаюсь создать метод расширения, который принимает выражение, которое указывает на свойство объекта, и постоянную строку для сравнения с использованием String.Contains, которое сначала проверяет, является ли строка пустой или нулевой,и применяет фильтр, только если строка имеет значение.Это мой первый бред в Деревьях выражений, так что я не совсем уверен, что происходит, и теперь у меня есть исключение, которое я не знаю, как вылечить ...

Я в этомдо сих пор:

<System.Runtime.CompilerServices.Extension()>
    Public Function CheckAndFilter(Of T)(source As System.Linq.IQueryable(Of T), expressionField As System.Linq.Expressions.Expression(Of System.Func(Of T, String)), compareTo As String) As IQueryable(Of T)


        If String.IsNullOrEmpty(compareTo) Then
            Return source
        Else
            Dim memberExp As Expressions.MemberExpression = DirectCast(expressionField.Body, Expressions.MemberExpression)

            Dim param = Expressions.Expression.Parameter(GetType(T))
            Dim method As Reflection.MethodInfo = GetType(String).GetMethod("Contains")

            Dim compareToExpression = Expressions.Expression.Constant(compareTo)
            Dim finalExpr = Expressions.Expression.Call(memberExp, method, compareToExpression)

            Dim lambda = Expressions.Expression.Lambda(Of Func(Of T, Boolean))(finalExpr, param)
            Return source.Where(lambda)
        End If
    End Function

Я называю это так против DbContext, где у меня есть Customer сущность со строковым свойством FirstName:

Dim results = repository.Customers.CheckAndFilter(Function(c) c.FirstName, searchText)

И исключение:

{"The parameter 'c' was not bound in the specified LINQ to Entities query expression."}

Есть мысли?

1 Ответ

2 голосов
/ 02 марта 2012

А га!

Это потому, что я объявил новый параметр, а не повторно использовал параметр, переданный через выражение ...

<System.Runtime.CompilerServices.Extension()>
Public Function CheckAndFilter(Of T)(source As System.Linq.IQueryable(Of T), expressionField As System.Linq.Expressions.Expression(Of System.Func(Of T, String)), compareTo As String) As IQueryable(Of T)


    If String.IsNullOrEmpty(compareTo) Then
        Return source
    Else
        Dim memberExp As Expressions.MemberExpression = DirectCast(expressionField.Body, Expressions.MemberExpression)

        Dim method As Reflection.MethodInfo = GetType(String).GetMethod("Contains")

        Dim compareToExpression = Expressions.Expression.Constant(compareTo)
        Dim finalExpr = Expressions.Expression.Call(memberExp, method, compareToExpression)

        Dim lambda = Expressions.Expression.Lambda(Of Func(Of T, Boolean))(finalExpr, expressionField.Parameters)
        Return source.Where(lambda)
    End If
End Function
...