使用 Sunspot/Solr 进行分组? [英] Group using Sunspot/Solr?

查看:46
本文介绍了使用 Sunspot/Solr 进行分组?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

在使用 Sunspot 时,我在按组搜索时遇到了一些问题.

I'm having some problem searching by group when using Sunspot.

这是一个例子:

# == Schema Information
#
# Table name: movies
#
#  id              :integer(4)      not null, primary key
#  title           :string(255)

class Movie < ActiveRecord::Base
  has_and_belongs_to_many :actors

  searchable do
    text :title

    integer :ages, multiple: true do
      actors.map(&:age)
    end

    text :names, multiple: true do
      actors.map(&:name)
    end
  end
end

# == Schema Information
#
# Table name: actors
#
#  id              :integer(4)      not null, primary key
#  name            :string(255)
#  age             :integer(30)

class Actor < ActiveRecord::Base
  has_and_belongs_to_many :movies

  searchable do
    integer :age
    text :name
  end
end

我想找到每部有 30 岁演员叫约翰的电影.

I want to find every movie that has an actor named John at age 30.

Movie.search do
  with(:names).equal_to("John")
  with(:ages).equal_to(30)
  with(:title).equal_to("...")
  # ...
end

问题就在这里,它可能会找到有两个演员的电影;一个叫约翰,一个在 30 岁.有没有办法以某种方式将它们组合在一起,以便电影发现有一个名叫约翰的演员在 30 岁?

The problem is here that it may find a movie that has two actors; one named John and one at age 30. Is there a way to somehow group this together so that the movie found have an actor named John at age 30?

推荐答案

解决方案,就像 Maurício Linhares在他的评论中写道,是通过演员模型和电影分组.

The solution, just like Maurício Linhares wrote in his comment, is to go through the actors model and group by movies.

问题是 Sunspot 不支持 Solr 3.3 或 4.0,这是唯一支持分组的 Solr 版本.

The problem is that Sunspot doesn't support Solr 3.3 or 4.0, which is the only Solr versions that support grouping.

这是我使用 Sunspot 1.2.1 和 Solr 3.3 的解决方案.

Here is my solution using Sunspot 1.2.1 and Solr 3.3.

在我的示例中,movie_id 被放置在 actor 表中,这在我的实际应用程序中没有完成.

In my example movie_id is placed in the actors table, this isn't done in my real application.

# == Schema Information
#
# Table name: actors
#
#  id              :integer(4)      not null, primary key
#  name            :string(255)
#  created_at      :datetime
#  updated_at      :datetime
#  movie_id        :integer(4)
#

class Actor < ActiveRecord::Base
  searchable do

    # We need to store the movie_id as an string
    # So it can be sorted. We also need to pass the
    # stored: true params
    string :movie_id, stored: true do
      movie_id.to_s
    end
  end

  def search_using_solr
    scoped = Sunspot.new_search(Actor)

    scoped.build do      
      adjust_solr_params do |params|
        params[:group]          = true
        params[:"group.field"]  = "movie_id_s"
        params[:"group.format"] = "simple"
      end
    end

    # Sunspot 1.2.1 doesn't support grouping, so we need to do some hacking.
    def scoped.hits
      @hits ||= @solr_result["grouped"].values.first["doclist"]["docs"].map do |doc|
        Sunspot::Search::Hit.new(doc, nil, self)
      end
    end

    def scoped.total
      @total ||= @solr_result["grouped"]["movie_id_s"]["matches"] || 0
    end

    # Here we'll only fetch the stored data from Solr it self, 
    # and then pass it manualy to ActiveRecord.
    Movie.where({
      id: scoped.execute.hits.map{ |h| h.stored(:movie_id) }
    })
  end
end

信任 alindeman示例要点.

这篇关于使用 Sunspot/Solr 进行分组?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆