Reputation: 6841
I have a question in regards to Rails params. I currently have only one filter on one of my views that allows users to filter data by a date range. I am adding two more filters to that view so that users can filter by code and country. However, I want those filters to be optional.
My current query looks something like this:
@data = Games
.where("date BETWEEN ? AND ?", *date_range_array)
.includes(:synced_country)
.order(sort_column + " " + sort_direction)
.page(params[:page])
The params for code and country will be something like, params[:code] and params[:country]. I would like to put them in the query like:
@data = Games
.where("date BETWEEN ? AND ?", *date_range_array)
.where("unique_code in ?" params[:code])
.where("country in ?" params[:country])
.includes(:synced_country)
.order(sort_column + " " + sort_direction)
.page(params[:page])
The issue I am having is that if the user does not input anything for params[:code] and params[:country] I get an error because they are nil. Any idea on how to handle this kind of situation?
Upvotes: 0
Views: 562
Reputation: 21
I usually use the same method with Agis. But sometimes I trend to use scope(as arieljuod said):
class Games
scope :in_contry, lambda{|contry| where("contry in ?", contry) if contry.present?}
scope :in_code, lambda{|code| where("unique_code in ?", code) if code.present?}
//other codes
end
//call lambdas as follows:
@data = Games.where("date BETWEEN ? AND ?", *date_range_array)
.in_code(params[:code])
.in_contry(params[:country])
.includes(:synced_country)
.order(sort_column + " " + sort_direction)
.page(params[:page])
Upvotes: 0
Reputation: 33626
I would build it incrementally:
@data = Games.where("date BETWEEN ? AND ?", *date_range_array)
@data = @data.where("unique_code in ?", params[:code]) if params[:code]
@data = @data.where("country in ?", params[:country]) if params[:country]
@data = @data.includes(:synced_country)
.order(sort_column + " " + sort_direction)
.page(params[:page])
Note that you are missing two commas right before params[:code]
and params[:country]
which I've fixed in the above code.
Upvotes: 1
Reputation: 15838
@data = Games.where("date BETWEEN ? AND ?", *date_range_array).scoped
@data = @data.where("unique_code in ?" params[:code]).scoped if params[:code].present?
@data = @data.where("country in ?" params[:country]).scoped if params[:coutry].present?
@data = @data.includes(:synced_country)
.order(sort_column + " " + sort_direction)
.page(params[:page])
Anyway, I would move that complex query to a named scope or something inside the Game Model.
EDIT: added the "scoped" method, i'm not sure if needed, try it without .scoped if you want
Upvotes: 0