How to check if predicate expression was changed?

1.9k views Asked by At
 var predicate = PredicateBuilder.True<o_order>();

This is my predicate expression, where on some certain conditions I will append expressions with it.

Likewise

 if (!string.IsNullOrEmpty(param.sSearch))
                predicate = predicate.And(s => s.OrderID.ToString().Contains(param.sSearch));

Now my question is if this expression doesn't pass by this condition then would there be any expression? and how would I know if it returns no expression with it.

Simply I want to do-

if(predicate==null) or if(predicate contains no expression)

3

There are 3 answers

0
quetzalcoatl On BEST ANSWER

This is so easy, you probably didn't consider that. Since PredicateBuilder builds new predicate instances each time (notice that you must write predicate = predicate.And... so you are replacing the pred each time), then you can simply just remember the original value and eventually compare the final value against that.

var predicate = PredicateBuilder.True<o_order>();
var oldPredicate = predicate;

if (!string.IsNullOrEmpty(param.sSearch))
    predicate = predicate.And(s => ........... );  // replace!

if (!string.IsNullOrEmpty(....))
    predicate = predicate.And(s => ........... );  // replace!

if(predicate == oldPredicate)   // was it changed?
    ; // no filters applied
else
    ; // some filters applied

It'd be hard however to tell which filters were applied. If you need to know that, then you must store the information alongside (or you have to analyze the predicate tree, which can be harder):

var predicate = PredicateBuilder.True<o_order>();
var oldPredicate = predicate;

bool case1applied = !string.IsNullOrEmpty(....);
if (case1applied)
    predicate = predicate.And(s => ........... );

bool case2applied = !string.IsNullOrEmpty(....);
if (case2applied)
    predicate = predicate.And(s => ........... );

if(predicate == oldPredicate) // or the hard way: !case1applied && !case2applied
    ; // no filters applied
else
    if(case1applied && case2applied) // all filters applied
    else ....
0
sara On

From what I can tell, PredicateBuilder exposes no methods that return a list of the expressions used. You could however store the conditions used to add expressions to the PredicateBuilder

var predicate = PredicateBuilder.True<o_order>();
var cond1 = /* condition 1 */
var cond2 = /* condition 2 */
...
if (cond1) { /* add expression for condition 1 */ }
if (cond2) { /* add expression for condition 2 */ }
...
if (!cond1 && !cond2 && ...) { /* handle case of no expressions added */ }
0
tomRedox On

I've found that the IsStarted property seems to show if a predicate has been assigned.

In my code I've used that to build up composite search statements where the search parameters are optional. E.g.

var quoteDatePredicate= PredicateBuilder.New<SearchData>();

if (searchCriteria.QuoteFromDate.HasValue)
{
    quoteDatePredicate.And(x => x.QuoteDate >= searchCriteria.QuoteFromDate);
}

var saleDatePredicate = PredicateBuilder.New<SearchData>();

if (searchCriteria.SaleDate.HasValue)
{
    saleDatePredicate.And(x => x.SaleDate >= searchCriteria.SaleDateFrom);
}  

And then I create another predicate variable and use an If statement to add any predicates that were actually assigned to:

var datesPredicate = PredicateBuilder.New<SearchData>();

if (quoteDatePredicate.IsStarted) datesPredicate.Or(quoteDatePredicate);
if (saleDatePredicate.IsStarted) datesPredicate.Or(saleDatePredicate);

So far that seems to work fine in my code.

Alternatively, comparing an assigned and unassigned predicate variable in the debugger seems to suggest you could use this to check if a predicate has been assigned:

if (dueOutOfDatePredicate.Parameters[0].Name = "f")

I haven't tried that though.