【问题标题】:Sending parameter to Ransack from Active Admin filter从 Active Admin 过滤器向 Ransack 发送参数
【发布时间】:2015-12-03 15:19:43
【问题描述】:

我正在尝试在 Active Admin 中对单个输入字段中客户的名字和姓氏进行过滤。 first_name 和 last_name 是单独的字段。

如果您有中间名,我的解决方案将失败。如果客户的名字是“John H. Smith”,那么“John”和“Smith”会给出正确的结果,但“John Smith”会因为多余的“H.”而找不到任何东西。

ActiveAdmin.register Customer do
  ...
  filter :full_name_cont, label: 'Name', as: :string
end

# In the Customer model:

ransacker :full_name, formatter: proc { |full_name| full_name.downcase.to_s } do |parent|
     Arel::Nodes::InfixOperation.new('||',
          Arel::Nodes::InfixOperation.new('||',
             parent.table[:first_name], ' '
          ),
          parent.table[:last_name]
     )
end

所以现在我尝试将搜索词“John H. Smith”作为参数发送给 ransacker,这样我就可以将名称分成多个部分并搜索其中任何一个与名字或姓氏匹配:

ransacker :full_name, args: [:parent, :ransacker_args] do |parent, args|
   full_name = args.first
   search_items = full_name.split(" ")
   condition = "concat_ws(first_name, ' ', last_name) LIKE '%#{search_items.first}%'"
   search_items.each do |item|
      condition += " OR concat_ws(first_name, ' ', last_name) LIKE '%#{item}%'" if item != search_items.first
   end
   Arel.sql(condition)
end

很遗憾,args 始终为空。

有谁知道如何向 ransacker 发送参数?

【问题讨论】:

标签: ruby-on-rails ruby filter activeadmin arel


【解决方案1】:

解决方案是创建一个新的 Ransack 谓词,将空格视为通配符。

本期也提出了这个想法:Make an OR with ransack

# In config/initializers/ransack.rb

Ransack.configure do |config|
  config.add_predicate 'contains',
         :arel_predicate => 'matches', # so we can use the SQL wildcard "%"
         # Format the incoming value: add the SQL wildcard character "%" to the beginning and the end of
         # the string, replace spaces by "%", and replace multiple occurrences of "%" by a single "%".
         # For using * and ? instead as wild cards use this #{Ransack::Constants.escape_wildcards(v).gsub("*", "%").gsub('?','_')}
         :formatter => proc {|v| ("%#{v.gsub(" ", "%")}%").squeeze("%")}
end

然后在模型中,我使用了https://github.com/activerecord-hackery/ransack/wiki/using-ransackers#5-search-on-a-concatenated-full-name-from-first_name-and-last_name-several-examples 中示例中的这个洗劫代码:

# ActiveAdmin - customers.rb
# I re-open the model 
class Customer
  ransacker :full_name do |parent|
       Arel::Nodes::InfixOperation.new('||',
          Arel::Nodes::InfixOperation.new('||',
              parent.table[:first_name], ' '),
                  parent.table[:last_name])
  end
end

ActiveAdmin.register Customer do
...
end

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2012-05-16
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-04-02
    相关资源
    最近更新 更多