Reputation: 445
Is there a way how to filter data with an enum property using a string?
This is my function in service layer which takes 2 arguments for paging feature and 3rd argument is for filtering projects by their status.
I want to do something like this projects.Where(x => x.Status == status)
but it throws error because I cannot compare enum with string. Is there some workaround for this?
public async Task<ListResult<ProjectDTO>> GetListedProjects(int pageSize, int pageNumber, string status)
{
var projects = await unitOfWork.ProjectRepository.Get();
//i cannot filter like this
projects.Where(x => x.Status == status);
var orderedProjects = projects.OrderBy(x => x.Name);
var projectList = orderedProjects.ToPagedList(pageNumber, pageSize);
var data = projectList.Select(x => ToDTO.ProjectBuild(x)).ToList();
return new ListResult<ProjectDTO> { Data = data, TotalCount = projectList.TotalItemCount };
}
Here is my project model:
public class Project : ManagementBaseClass
{
[Key]
public int Id { get; set; }
public Status Status { get; set; }
public Priority Priority { get; set; }
//etc just deleted more properties to make this cleaner
}
This is my enum which i use for assigning status to projects, tasks etc
public enum Status
{
New = 1,
Active = 2,
OnHold = 3,
Testing = 4,
Finished = 5,
Dropped = 6
}
Upvotes: 1
Views: 7786
Reputation: 354
You can easily convert the Status enum to String and filter it. You can even search by part of the Status name if you use the Contains method:
projects.Where(x => x.Status.ToString() == status); //To filter by exact input value
projects.Where(x => x.Status.ToString().Contains(status)); //To filter by part of the name search, for example if the input status is any of "N" or "Ne" or "New", the query returns the row with Status = 1
Upvotes: 0
Reputation: 1847
You can parse the string value:
private static TEnum? GetEnum<TEnum>(string value) where TEnum : struct
{
TEnum result;
return Enum.TryParse<TEnum>(value, out result) ? (TEnum?)result : null;
}
public async Task<ListResult<ProjectDTO>> GetListedProjects(int pageSize, int pageNumber, string status)
{
var projects = await unitOfWork.ProjectRepository.Get();
//i cannot filter like this
projects.Where(x => x.Status == GetEnum<Status>(status));
var orderedProjects = projects.OrderBy(x => x.Name);
var projectList = orderedProjects.ToPagedList(pageNumber, pageSize);
var data = projectList.Select(x => ToDTO.ProjectBuild(x)).ToList();
return new ListResult<ProjectDTO> { Data = data, TotalCount = projectList.TotalItemCount };
}
Upvotes: 2
Reputation: 1500
Before you call projects.Where(x => x.Status == status);
you should try and parse that string value of status
into the Status Enum.
You can use either Enum.Parse
which throws an exception if the parse fails or you can use Enum.TryParse
that returns a bool based on the success/failure of the parsing operation.
Upvotes: 1
Reputation: 1
You're passing string
as such:
public async Task<ListResult<ProjectDTO>> GetListedProjects(int pageSize, int pageNumber, string status)
{
var projects = await unitOfWork.ProjectRepository.Get();
//i cannot filter like this
projects.Where(x => x.Status == status);
var orderedProjects = projects.OrderBy(x => x.Name);
var projectList = orderedProjects.ToPagedList(pageNumber, pageSize);
var data = projectList.Select(x => ToDTO.ProjectBuild(x)).ToList();
return new ListResult<ProjectDTO> { Data = data, TotalCount = projectList.TotalItemCount };
}
When you should be passing the enum
public async Task<ListResult<ProjectDTO>> GetListedProjects(int pageSize, int pageNumber, Status status)
You could also pass in string, and create a Status
variable and with some switch statement, you could set it to the correct enum. I don't like converting a string
to an enum
as some of the answers show. Error prone in my opinion, you're better off trying to either A) resolve the string to a Status
or B) just pass in the Status
enum to avoid any conflict.
Upvotes: 1
Reputation: 2681
You can parse the string to the enum equivalent
Obviously this code is a rough draft to give you an idea and set you on the right track, you'd have to do null checks on the Parse to prevent exceptions, or use TryParse.
public async Task<ListResult<ProjectDTO>> GetListedProjects(int pageSize, int pageNumber, string status)
{
var projects = await unitOfWork.ProjectRepository.Get();
//i cannot filter like this
projects.Where(x => x.Status == (Status)Enum.Parse(typeof(Status), status));
var orderedProjects = projects.OrderBy(x => x.Name);
var projectList = orderedProjects.ToPagedList(pageNumber, pageSize);
var data = projectList.Select(x => ToDTO.ProjectBuild(x)).ToList();
return new ListResult<ProjectDTO> { Data = data, TotalCount = projectList.TotalItemCount };
}
Upvotes: 2