Reputation: 5898
Given the Following basic Structure
public class Project
{
public int ProjectId {get;set;}
ICollection<SubProject> SubProjects {get;set;}
}
public class SubProject
{
public int SubProjectId {get;set;}
public int SubProjectId {get;set;}
public int PrinterId {get;set;}
public int AgencyId {get;set;}
public int Status
//Oodles more properties
}
public class ProjectSearchResult
{
public int ProjectId {get;set;}
public int NoOfSubProjects {get;set;}
//Loads more properties
}
I need to get a list of projects and a count of how many sub-projects they have, sometimes by Agency, Sometimes by Printer, and Sometimes by Status,
Instead of doing something like the below
public IQueryable<ProjectSearchResult> GetProjects(int? status, int? agencyId, int? printerId)
{
var projects = db.Projects.Include(x=>x.SubProjects);
if(status.HasValue)
return projects.Select(proj=> new ProjectSearchResult
{
ProjectId = proj.ProjectId,
NoOfSubProjects = proj.SubProjects.Count(s=>s.Status = status)
};
if(agency.HasValue)
return projects.Select(proj=> new ProjectSearchResult
{
ProjectId = proj.ProjectId,
NoOfSubProjects = proj.SubProjects.Count(s=>s.AgencyId= agency)
};
if(printer.HasValue)
return projects.Select(proj=> new ProjectSearchResult
{
ProjectId = proj.ProjectId,
NoOfSubProjects = proj.SubProjects.Count(s=>s.PrinterId= printer)
};
Is there any way I can make it more generic and keep it as an IQueryable
, without returning all the sub projects and doing the count in memory?
Upvotes: 2
Views: 305
Reputation: 12077
You could do it like this:
public IQueryable<ProjectSearchResult> GetProjects(Expression<Func<SubProject, bool>> predicate)
{
return
from p in db.Projects
select new ProjectSearchResult {
ProjectId = p.ProjectId,
NoOfSubProjects = p.SubProjects.Count(predicate),
};
}
In case it's not obvious, you can then do something like this:
var projects = GetProjects(_ => _.Status == projectStatus);
Upvotes: 2