使用Rails进行高级搜索 - Active Record SQl查询问题

时间:2018-05-27 12:37:30

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

我在我的rails应用程序之上构建了一个搜索功能,我可以根据用户的名称进行搜索和过滤。性别。搜索工作正常,唯一不能正常工作!

例如,如果我搜索男性用户,搜索结果也会让我成为女性用户。我认为这是因为我使用ActiveRecord查询,我将users表的性别列与插入的参数进行比较&因为'女性'和男性'是两个非常相似的单词,它得到的结果与这两个属性有关。这是我使用的ActiveRecord查询&这工作(虽然不准确):

"gender LIKE ? ", "%#{params[:gender]}%"

所以我使用了不同的ActiveRecord查询:

"gender: %#{params[:gender]}%"

不幸的是,第二个查询打破了一切。我的终端出现了这个错误:

SQLite3::SQLException: unrecognized token: ":": SELECT "users".* FROM "users" WHERE (gender: %Male%))

那些ActiveRecord查询应该属于我的搜索'的search_controller。模型。这是我的控制者:

  def index
    if params[:username] || params[:gender].present?
        @search = User.where('true').paginate(page: params[:page], per_page: 10)
        @search = User.where("name LIKE ? ", "%#{params[:username]}%") unless params[:username].blank?
        @search = User.where("gender LIKE ? ", "%#{params[:gender]}%") unless params[:gender].blank?
    else
        @search = User.all.paginate(page: params[:page], per_page: 10)
    end
  end

  def create
     @search = Search.create(username: params[:username], gender: params[:gender])
     redirect to @search
  end

  private

  def search_params
    params.require(:search).permit(:users, :gender)
  end

这是我的搜索模型的索引,在那里我迭代搜索的内容(@search)并显示在搜索结果中:

<h1> Your Search Results </h1>

<% if @search.nil? %>
  <p> No Results Found </p>


<% else %>

<ul class="users">
  <% @search.each do |user| %>
    <%= user.name %>
    <%= user.gender %>
  <% end %>

</ul>

<% end %>

<p><%= link_to 'All Users',  users_path %></p>

这是一个小视频,我可以解释我想要做的事情:https://drive.google.com/file/d/1G5FYytvmdI6iKjmwlH16NeftGwsEnLQU/view?usp=sharing

2 个答案:

答案 0 :(得分:0)

两个问题: 1)完全匹配你可以做的参数

@search = User.where(gender: params[:gender]) unless params[:gender].blank?

你剩下的就是关于潜在的LIKE clausa,如果你想用LIKE这样做,这是正确的语法

@search = User.where("gender LIKE ? ", "#{params[:gender]}") unless params[:gender].blank?

2)您正在覆盖@search变量,因此如果您同时拥有该参数,则您的名称参数查询永远不会保留。最后试试这个

@search = User.all
@search = @search.where("name LIKE ? ", "%#{params[:username]}%") unless params[:username].blank?    
@search = @search.where("gender LIKE ? ", "%#{params[:gender]}%") unless params[:gender].blank?

答案 1 :(得分:-2)

使用LIKE ?会使您的代码容易受SQL injections影响,因此我绝对建议您更改方法。

我认为你会用

之类的东西解决问题
User.where("name = ? AND gender = ?", params[:username], params[:gender])

每次使用查询时,也请将Active Record Query Guideline作为参考。你会在那里找到很多有用的东西。