How do I filter results by multiple fields?
I'm working on a ruby poll app on rails and results page where I want users to filter out responses to a bunch of demographic questions asked at the start of the poll.
For example, I asked users what their gender and career are. So I was thinking about having a dropdown for gender and career. Both dropdowns will be the default for everyone, but if the user selected a woman and a marketer, then my results page will only respond like this from female marketers.
I think the correct way to do this is to use named_scopes where I have a named_scope for each of my demographic questions, in this example gender and career, which will take sanitized value from the dropdown to be used in conditional but I'm not sure if how to dynamically create a named_scope chain as I have 5 demographic questions and probably some will be set for everyone.
a source to share
You can combine named areas together:
def index
@results = Results.scoped
@results = @results.gender(params[:gender]) unless params[:gender].blank?
@results = @results.career(params[:career]) unless params[:career].blank?
end
I prefer to use the has_scope gem:
has_scope :gender
has_scope :career
def index
@results = apply_scopes(Results).all
end
If you use has_scope with inherited_resources , you don't even need to define the index action.
a source to share
named_scope :gender,lambda { |*args|
unless args.first.blank?
{ :conditions => [ "gender = ?", args.first] }
end
}
If you write named scopes this way, you can copy them, and if one of your parameters is empty, it won't break.
Result.gender("Male") will return male results.
Result.gender("") will return male and female too.
And you can link all your methods like this. Finally, you can have:
Result.age(16).gender("male").career("beginer")
Result.age(nil).gender("").career("advanced") - will return results with advanced career, etc.
a source to share