0

I have some entities that have a IsDeleted (logic delete) property and when I do queries, the standard would be to return all but deleted ones, like:

var query = collection.Where(e=> !e.IsDeleted);

I'm using predicate builder to create some predicates for reuse, so I have a search like this :

    public static Func<FakeEntity, bool> ContainsName(string keyword) {
        var predicate = NotDeleted();
        predicate = predicate.And(e => e.Name.Contains(keyword));
        return predicate;
    }

and a NotDeleted() predicate :

    public static Func<FakeEntity, bool> NotDeleted() {
        var predicate = PredicateBuilderDelegate.True<FakeEntity>();
        predicate = predicate.And(e => !e.IsDeleted);
        return predicate;
    }

what I want is to create another predicate that 'overrides' some how the NotDeleted() one, so in code I can call :

var result = collection.Where(FakeEntity.ContainsName("keyword")
                         .And(FakeEntity.IncludeDeleted()));

The idea beyond that is when I use the ContainsName it returns all entities that contains that string that are not deleted, but I want some way to explicitly say to include those deleted ones.

Is it clear?

What I tryied with no luck is :

    public static Func<FakeEntity, bool> IncludeDeleted() {
        var predicate = PredicateBuilderDelegate.True<FakeEntity>();
        predicate = predicate.And(e => e.IsDeleted);
        return predicate;
    }
Bart Calixto
  • 19,210
  • 11
  • 78
  • 114
  • Logically you are never going to get more results by adding predicates. – Ben Robinson Oct 29 '14 at 20:10
  • Your code isn't designed right. A `ContainsName` operation should filter items that contain a name, rather than items that contain a name and are not deleted. If you then want items that contain a name and are not deleted your query works as intended. If you want items that contain a name and are not deleted, then that's what you ask for. – Servy Oct 29 '14 at 20:11
  • @BenRobinson Sure you are. You use Or, not And. Not that it solves this particular problem. – Servy Oct 29 '14 at 20:11
  • FYI your continual AND-ing of a single predicate with `TRUE` is just pointless. You can just remove all of that code. – Servy Oct 29 '14 at 20:12
  • @Servy while agree, I will have all queries like : Where(NotDeleted().And(ContainsName('')) ... I'm trying to save me some NotDeleted() everywhere. – Bart Calixto Oct 29 '14 at 20:19
  • 1
    @Bart Then you need to have both a `ContainsName` and an `IsActiveAndContainsName` – Servy Oct 29 '14 at 20:21

1 Answers1

1

It'll be impossible to get exactly what you want. You'll need to do a more significant redesign of some sort for it to be possible.

Fundamentally if you want to be building up a predicate you should just not add in expressions that you don't want to be there, rather than adding them in and trying to pull them back out later. In your situation that means not unconditionally filtering out deleted items whenever you want to filter items where the name contains a value. Separate out those two operations if your requirements state that they sometimes need to be separate.

Servy
  • 202,030
  • 26
  • 332
  • 449