Ransack:使用年龄而不是出生日期
我想使用ransack为用户构建一个高级搜索function。 我有一个小方法来计算从出生日期开始的年龄:
def age(dob) now = Time.now.utc.to_date now.year - dob.year - ((now.month > dob.month || (now.month == dob.month && now.day >= dob.day)) ? 0 : 1) end
这适用于正常显示( as in age(@user.date_of_birth)
)
但是当使用search_form_for时我不能这样做:
我的问题是:如何在搜索中使用年龄而不是出生日期?
添加如下所示的范围以查找给定年龄的日期。
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 }
对于ransacke语法:
ransacker :age, :formatter => proc {|v| Date.today - v.to_i.year} do |parent| parent.table[:date_of_birth] end
在视野中
<%= f.text_field :age_gteq %>
我个人并不认识ransacker,并试图使用ransacker,但找不到任何可以检查传入谓词的东西。因此我认为使用范围更好。
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的答案很酷,但是lteq
的逻辑就像gt
和gteq
一样,就像lt
一样。 我自己最近开始使用ruby和rails。 所以告诉我,如果我做错了什么。 :) 谢谢!
只是关于@siddick答案的更新(完美无缺)。 您现在需要使用ransack提供的白名单范围。 在@siddick的答案中你需要这样做:
def self.ransackable_scopes(auth_object = nil) %i(age_between) end
有关更多信息,请参阅文档 – https://github.com/activerecord-hackery/ransack#using-scopesclass-methods
- Rails Gemfile默认为’https’ – ‘bundle install’失败
- Gem-idea:当HTTP方法发布,放置或删除时,在before_filter中使用validation码自动保护垃圾邮件