Ransack: using age instead of date of birth

╄→尐↘猪︶ㄣ 提交于 2019-12-03 17:27:29

Add a Scope like below to find the date for the given age.

scope :age_between, lambda{|from_age, to_age|
  if from_age.present? and to_age.present?
    where( :date_of_birth =>  (Date.today - to_age.to_i.year)..(Date.today - from_age.to_i.year) )
  end
}

For ransacke syntax:

ransacker :age, :formatter => proc {|v| Date.today - v.to_i.year} do |parent|
  parent.table[:date_of_birth]
end   

In view

<%= f.text_field :age_gteq %>

I do not know ransacker personally and tried to use ransacker but couldn't find any thing that could check the predicate passed in. Hence I believe it's better to use scopes to do it.

def self.age_lteq(age)
  start_birth_year = Date.today.year - age
  where('date_of_birth >= ?', Date.new(start_birth_year))
end

def self.age_gteq(age)
  birth_year = Date.today.year - age
  end_of_birth_year = Date.new(birth_year + 1) - 1
  where('date_of_birth <= ?', end_of_birth_year)
end

private

def self.ransackable_scopes(auth_object = nil)
  %i(age_lteq age_gteq)
end

# In views just do the following (ransack default grouping queries is by AND)
# https://github.com/activerecord-hackery/ransack#grouping-queries-by-or-instead-of-and
<%= f.input :age_lteq %>
<%= f.input :age_gteq %>

@siddick answer is cool, but the logic of lteq acts like gt and gteq acts like lt. I myself is starting out ruby and rails recently. So do tell me if I did anything wrong. :) Thanks!

Just an update on @siddick answer (which works perfectly). You now need to white list scopes that ransack offers. In the case of the answer from @siddick you need to do this:

def self.ransackable_scopes(auth_object = nil)
  %i(age_between)
end

For more info see the docs - https://github.com/activerecord-hackery/ransack#using-scopesclass-methods

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!