簡體   English   中英

Activeadmin:如何過濾匹配兩個或多個搜索詞的字符串

[英]Activeadmin: how to filter for strings that match two or more search terms

假設我有一個帶有:email字段的User類。 我們假設我使用activeadmin來管理用戶。

制作一個返回與一個字符串匹配的電子郵件的過濾器,例如“smith”,非常簡單。 admin/user.rb ,我只包含該行

filter :email 

這給了我一個完成工作的過濾器小部件。

但是,此過濾器不允許我搜索多個項的交集。 我可以搜索包含“smith”的電子郵件,但不能搜索包含“smith”和“.edu”的電子郵件。

Google告訴我,activerecord在引擎蓋下使用Ransack ,而Ransack演示具有允許多個術語搜索的“高級”模式。

將多項搜索小部件放入activeadmin的最簡單方法是什么?

理想情況下,我想要一個小部件,允許我輸入smith .edusmith AND .edu來過濾包含這兩個術語的電子郵件。

使用可運行的范圍有簡單的解決方案

所以在你的模型中加入這樣的東西

class User < ActiveRecord::Base
    ....
    scope :email_includes, ->(search) {
       current_scope = self
       search.split.uniq.each do |word|
         current_scope = current_scope.where('user.email ILIKE ?', "%#{word}%")  
       end
       current_scope
    }

    def self.ransackable_scopes(auth_object = nil)
      [ :email_includes]
    end
end

在此之后,您可以添加AA DSL過濾器

喜歡

  filter :email_includes, as: :string, label: "Email"

UPD

如果將email_contains_any更改為email_includes應該有效

我已經找到了解決方案,但它並不漂亮。

好消息是,Ransack在多項搜索方面沒有任何問題。 這些搜索使用“斷言” cont_all 以下行用於查找包含“smith”和“.edu”的電子郵件。

User.ransack(email_cont_all: ['smith','.edu'] ).result

由於這些搜索在Ransack中很容易,因此在Activeadmin中它們可能很簡單,對吧? 錯誤! 為了讓他們工作,我需要做三件事。

  1. 我把一個自定義的洗劫方法(又名ransacker )到User.rb 我將email_multiple_terms命名為email_multiple_terms

     class User < ActiveRecord::Base # ... ransacker :email_multiple_terms do |parent| parent.table[:path] end 
  2. 我在activeadmin儀表板中聲明了一個過濾器,並將其與ransacker相關聯。 請注意,搜索謂詞cont_all將附加到搜索引擎名稱。

admin/User.rb

ActiveAdmin.register User do

# ...

filter :email_multiple_terms_cont_all, label: "Email", as: :string 

此行在Activeadmin中創建過濾器小部件。 我們快到了。 剩下的一個問題是:Activeadmin將搜索查詢作為單個字符串發送到ransack(例如"smith .edu" ),而我們的搜索者希望將搜索項作為數組。 在某個地方,我們需要將單個字符串轉換為搜索字詞數組。

  1. 我修改了activeadmin以在某些條件下拆分搜索字符串。 邏輯在我添加到lib / active_admin / resource_controller / data_access.rb的方法中。

     def split_search_params(params) params.keys.each do |key| if key.ends_with? "_any" or key.ends_with? "_all" params[key] = params[key].split # turn into array end end params end 

然后我在apply_filtering調用了這個方法。

    def apply_filtering(chain)
      @search = chain.ransack split_search_params clean_search_params params[:q]
      @search.result
    end

這段代碼存在於我自己的activeadmin分支中,這里是: https//github.com/dH-/activeadmin

因此,要使多項術語搜索工作,請按照上面的步驟1和2,在我的Gemfile中包含我的AA分支:

  gem 'activeadmin', :git => 'git://github.com/d-H-/activeadmin.git'

HTH。

如果有人有更簡單的方法,請分享!

只需在模型中添加三個過濾器:

filter :email_cont
filter :email_start
filter :email_end

它為您提供了一種靈活的方式來管理您的搜索。

在此輸入圖像描述

此過濾器執行下一個sql代碼:

SELECT  "admin_users".* FROM "admin_users"
WHERE ("admin_users"."email" ILIKE '%smith%' AND 
       "admin_users"."email" ILIKE '%\.edu')
ORDER BY "admin_users"."id" desc LIMIT 30 OFFSET 0

我希望你正是在找什么。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM