Rails搜索多个条件

时间:2015-07-29 09:12:53

标签: ruby-on-rails ruby ruby-on-rails-4 rails-activerecord

我正在尝试使用以下条件搜索结果

  

主持人has_many事件

     

hosts(id,name,host_type,....)

     

事件(id,name,host_id,....)

  1. 默认显示所有活动结果
  2. 根据活动的inds_to_drop = [ i for i,dt in enumerate(b2.Date) if not pandas.np.where( b1.Date==dt)[0].size ] 显示结果
  3. 基于是否根据相关模型query
  4. 选择了host_type

    现在我正在做一个Hosts语句,但随着选项的增长,它将成为太多的条件代码。

    if else

    修改

    基于一些研究和我已修改的答案到以下

    if params[:query].blank?
          @events_results = Event.order('event_date ASC').all
        else
          @events_results = Event.where("name LIKE '%#{params[:query]}%'").order('event_date ASC').all
        end
    

    错误:

      

    Mysql2 ::错误:'where子句'中的未知列'Host.host_type':   SELECT def index @events_results ||= find_events end private def find_events events = Event.order('event_date ASC').all events = events.where("name LIKE '%#{params[:query]}%'") if params[:query].present? events = events.includes(:host).where("Host.host_type = ?", params[:host_type]) if params[:query].present? events end 。* FROM events WHERE(名称LIKE'%menu%')AND   (Host.host_type ='1')ORDER BY event_date ASC

6 个答案:

答案 0 :(得分:2)

你可以在你去的时候创建一个初始查询和链,从我可以看到order部分是常见的并且始终存在,所以将它用作基本查询

@event_results = Event.order(event_date: :asc)
@event_results = @event_results.where('event_results.name LIKE ?', "%#{params[:query]}%") if params[:query]
@event_results = @event_results.joins(:host).where(host_type: params[:host_type]) if proper_condition
@event_results = @event_results.more_methods if more_conditions
#etc

@event_results #the return

默认情况下,ruby将返回最后一个语句,因此您不需要使用return,除非最后一个语句返回true/false之类的内容,那么您应该只添加一个带有变量的新行{ {1}}

  

注意:永远不要将params中的输入直接用于您的查询,您允许人们将sql注入您的代码,使用替换   方法,以便@event_results为您清理输入。

     

<强>为:

ActiveRecord
     

不可

where("name LIKE '%#{params[:query]}%'")

答案 1 :(得分:1)

你可以使用if params [:query] .present?

@events_results = Event.order('event_date ASC').all

@events_results = Event.where("name LIKE '%#{params[:query]}%'").order('event_date ASC').all if params[:query].present?

答案 2 :(得分:1)

你可以通过条件保护条款:

def events_results
  return Event.order('event_date ASC').all if params[:query].blank?
  return Event.where("name LIKE '%#{params[:query]}%'").order('event_date ASC').all if host_type
  return something_else if_some_other_codn_met
end

通过这种方式,您无需担心if else / case语句,看起来更干净(imo)。

答案 3 :(得分:1)

你可以做的是先创建一个条件字符串,如下所示:

conditions = ""
if params[:query].present?
  conditions += " name LIKE '%#{params[:query]}%'"
elsif params[:anything].present?
  conditions += " query" #if you have OR condtion either the first parameter or this one
end
if params[:something_else].present?
  conditions += " AND query"
end
@events_results = Event.where(conditions).order('event_date ASC').all

此外,我还建议您使用elasticsearchsolr这类任务。

希望这有帮助。

答案 4 :(得分:1)

我遇到了必须根据查询参数创建不同搜索的问题,并创建了一个小宝石来帮助我。

https://github.com/fortytools/forty_facets

答案 5 :(得分:1)

在你的编辑中你应该第二次检查params [:query] .present吗?对于params [:host_type]?

同样在你有一个查询字符串的情况下,你首先调用.all然后立即过滤LIKE,所以你应该考虑重构它,因为它将是一个性能问题因为你不需要制作对.all的调用将导致额外的查询。