使用thinking_sphinx进行搜索并过滤结果

我有这种情况,我认为这将是非常基本的,但发现我无法真正实现我所需要的。 这就是为什么我有一个think_sphinx专家的问题。

场景是这样的:我需要在公司列表中进行搜索,只返回那些拥有地址的公司(公司可以有很多地址)属于某个特定城市或根本没有(我可以做)。

我有以下型号:

class Company < ActiveRecord::Base has_many :company_addresses define_index indexes :name indexes :description indexes :keywords end end 

 class CompanyAddress < ActiveRecord::Base end 

CompanyAddress有一个city_id属性。 如果不通过sphinx搜索循环所有返回的记录,有没有办法更容易地实现同样的事情?

我正在使用Rails 3.0.3和thinking_sphinx。

您需要添加指向公司的city_id值的属性:

 has company_addresses.city_id, :as => :city_ids 

然后,您可以筛选属于特定城市的公司:

 Company.search 'foo', :with => {:city_ids => @city.id} 

如果你想要匹配特定城市没有城市,这有点棘手,因为属性filter的OR逻辑充其量只是有点棘手。 理想情况下,您需要的是包含0或所有城市ID的单个属性。 这样做取决于您的数据库,因为MySQL和Postgresfunction各不相同。

但是,作为一个粗略的想法 – 这可能适用于MySQL:

 has "IF(COUNT(city_id) = 0, '0', GROUP_CONCAT(city_id SEPARATOR ',')", :as => :city_ids, :type => :multi 

Postgres非常相似,但您可能需要使用CASE语句而不是IF ,并且您肯定希望使用几个函数进行组连接:

 array_to_string(array_accum(city_id, '0')), ',') 

(array_accum由Thinking Sphinx提供,因为在PostgreSQL中没有直接等效的GROUP_CONCAT)。

无论如何,如果你需要这种方法,并得到所有想出来的SQL,那么你的查询看起来像:

 Company.search 'foo', :with => {:city_ids => [0, @city.id]} 

这将匹配0(代表没有城市)或特定城市。

最后:如果您没有在普通字段和属性中的任何位置引用company_addresses关联,则需要强制加入define_index

 join company_addresses 

希望这提供了足够的线索 – 随时可以继续在这里或谷歌集团进行讨论。