Jesse
Jesse

Reputation: 8393

Creating a generic extension method to provide filtering functionality

I'm working on an extension method to provide filtering capabilities for several entities. The entities involved are of different types but have common fields that can be searched on.

The below is working at the moment, however I was wondering if this could be "genericized" so that the casting from generic to explicit type doesn't need to occur?

public static IQueryable<T> PriceLow<T>(this IQueryable<T> query, decimal? priceLow)
{
    if (typeof(T) == typeof(Entity1))
    {
        var innerQuery = (IQueryable<Entity1>) query;
        var results = priceLow.HasValue ? innerQuery.Where(o => (o.ListPrice > priceLow.Value)) : innerQuery;
        return (IQueryable<T>) results;
    }

    if (typeof(T) == typeof(Entity2))
    {
        var innerQuery = (IQueryable<Entity2>)query;
        var results = priceLow.HasValue ? innerQuery.Where(o => (o.ListPrice > priceLow.Value)) : innerQuery;
        return (IQueryable<T>)results;
    }

    return null;
}

Example usage:

    var foo = _repository.GetAllEntity1().PriceLow(_searchCritera.PriceLow);

Upvotes: 3

Views: 798

Answers (3)

Jonathan Wood
Jonathan Wood

Reputation: 67283

One approach is to define an interface and add that interface as one of the things your class inherits from. The interface doesn't need to contain anything at all. It could just be used as a marker.

Then make your extension method require the argument is that interface.

Upvotes: 1

Paul Phillips
Paul Phillips

Reputation: 6259

If you can change the two entity types to implement a common interface which has the shared properties/methods, then you can use a generic type constraint. This would also work with a shared base class.

Do that, and then your signature looks like this (cluttering details omitted):

public static IQueryable<T> PriceLow<T>(...)
  where T : ICommonInterface

Upvotes: 3

AUSteve
AUSteve

Reputation: 3258

How about making your entities inherit from a base type that holds the searchable fields. That way your filter method only needs to know about the one base type.

Upvotes: 2

Related Questions