如何在Rails中的关联模型上配置pg_search multisearch?

时间:2012-05-09 09:04:54

标签: ruby-on-rails pg-search

我正在将pg_search添加到Rails应用程序中。我并不完全理解这种配置,并希望在正确的方向上轻轻推动。

首先,我已经在我的应用上或多或少地设置并运行了多模型网站。但我想扩展它以搜索相关模型。

例如,我有制造商,汽车,模型类。目前,如果我搜索“福特”,则只返回制造商。我还想退回所有相关的汽车(属于制造商)和模型(属于汽车)。

我可以看到如何将其作为范围搜索

class Car
  pg_search_scope :manufactured_by, :associated_against => {
    :manufacturer => [:name]
  }
end

但如果我尝试在多元游戏上执行此操作,则无效

class Car
  include PgSearch
  multisearchable :against => [:name], 
    :associated_against => {
        :manufacturer => [:name]
      }
end

它不会产生错误,它根本不会获取相关记录。

我有一种感觉,在我理解这一切如何融合在一起时,我缺少一些基本的东西。如果有人能帮助我理解这一点,或者指出一个良好的信息来源,我真的很感激。我已经浏览了github和相关Railscast的信息,但我仍然遗漏了一些东西。

1 个答案:

答案 0 :(得分:13)

由于多态关联在Rails和SQL中的工作方式,因此无法使用multisearch搜索关联记录。

我会添加一个错误来解释这种情况,以便将来不会让人感到困惑。

很抱歉这个混乱。

您可以做的是在Car上定义一个返回您要搜索的文本的方法。

class Car < ActiveRecord::Base
  include PgSearch
  multisearchable :against => [:name, manufacturer_name]
  belongs_to :manufacturer

  def manufacturer_name
    manufacturer.name
  end
end

或者更简洁,你可以代表:

class Car < ActiveRecord::Base
  include PgSearch
  multisearchable :against => [:name, manufacturer_name]
  belongs_to :manufacturer
  delegate :name, :to => :manufacturer, :prefix => true
end

但是,如果您对制造商实例进行了名称更改,则必须确保pg_search_documents表得到更新,因此您应该将:touch => true添加到其关联中:

class Manufacturer < ActiveRecord::Base
  has_many :cars, :touch => true
end

这样,当制造商更新时,它将调用所有Car记录上的Active Record回调,这将触发pg_search回调以更新存储在相应pg_search_documents条目中的可搜索文本。