【问题标题】:Ordering elasticsearch results, elasticsearch-rails gem, Rails订购 elasticsearch 结果,elasticsearch-rails gem,Rails
【发布时间】:2015-07-13 20:19:14
【问题描述】:

我开始在我的项目中使用 Elasticsearh,但结果排序有问题。

事实上,我需要在已连接 (belongs_to) 模型中按 hstore 记录对我的记录进行排序。

更多细节:

所以,我有一个模型,我希望它可以被搜索。该模型与其他模型有联系,代码如下:

class PropertyObject < ActiveRecord::Base
  belongs_to :country, :counter_cache => true
  belongs_to :region, :counter_cache => true
  belongs_to :city, :counter_cache => true
  belongs_to :property_object_type, :counter_cache => true
  belongs_to :property_object_state, :counter_cache => true

  has_one :property_object_parameter_pack, dependent: :destroy
  has_one :property_object_feature_pack, dependent: :destroy
  has_one :property_object_description, dependent: :destroy
  has_one :property_object_seo_field, dependent: :destroy
end

我想在我的搜索结果中包含下一个字段:

模型属性对象:

  • :代码:字符串

示范国家

  • :title_translations :hstore

模型区域

  • :title_translations :hstore

模范城市

  • :title_translations :hstore

模型属性对象描述

  • :title_translations :hstore
  • :main_text_translations :hstore

模型 PropertyObjectParameterPack

  • :价格:hstore(例如:{min => 10, max=>100})

为了完成这项工作,我创建了可搜索的关注点并将其添加到我的模型 PropertyObject 中。 这里是它的代码:

module Searchable
  extend ActiveSupport::Concern

  included do
    include Elasticsearch::Model
    include Elasticsearch::Model::Callbacks

    mapping do
      indexes :property_object_parameter_pack, type: 'nested' do
        indexes :price do
          indexes :min, type: :integer
        end
      end
    end

    # Customize the JSON serialization for Elasticsearch
    def as_indexed_json(options={})
      self.as_json(
          include: {
              country: {only: :title_translations},
              region: {only: :title_translations},
              city: {only: :title_translations},
              property_object_description: {only: [:title_translations, :main_text_translations]},
              property_object_parameter_pack: {only: [:price, :area, :rooms]}
          })
    end


  end
end

搜索调用的控制器部分

def search
    pagen = params[:page] || 1
    @property_objects = PropertyObject.search(params[:q]).page(pagen).records

end

所以现在搜索工作,一切似乎都很好。但我需要按最低价格对搜索结果进行排序。

我尝试了适用于我的另一个订单的订购方法 - 但没有运气。

据我了解,我需要使用 Elasticsearch 排序来获得已经排序的结果 - 但花费大量时间尝试实现这一点并失败。

你能给我什么建议?

更新 试过这段代码:

 pagen = params[:page] || 1
      query = params[:q]
      params[:order] ||= 'asc'
      property_objects = PropertyObject.search(query) do |s|
        s.query do |q|
          q.string query
        end
        s.sort { by :property_object_parameter_pack.price.min, params[:sort]}
      end
      @property_objects = property_objects.page(pagen).records

有不同的变体

s.排序

  • 作者:价格
  • by :price.min
  • by :price[:min]
  • 作者:property_object_parameter_pack.price.min
  • by :property_object_parameter_pack.price[:min]

而且没有运气订购。

【问题讨论】:

    标签: ruby-on-rails sorting elasticsearch


    【解决方案1】:

    最后我决定了解 Elasticsearch 的工作原理,并开始阅读 Elasticsearch: The Definitive Guide - 找到答案的地方。

    首先我建议阅读本指南并安装Marvel .在这一切变得更加清晰之后,然后使用 CURL。事实上,我在 Marvel 中发现了我的索引结构,然后将其用于 elasticsearch-rails gem 的搜索查询。

    接下来我做了 - 我从 hstore 重建价格到单独的整数列:比如 price_min 和 price_max。 所以简而言之,答案代码是:

    sq = {
    "query": {
     "multi_match": {
        "query":    "Prague",
        "fields":   [ "country.title_translations.en",
                      "region.title_translations.en",
                      "city.title_translations.en",
                      "property_object_description.main_text_translations.en",
                      "property_object_description.title_translations.en"
                    ]
      }
    },
    "track_scores": true,
    "sort": {
      "property_object_parameter_pack.price_min": 
      { "order": "desc",
        "missing" : "_last"
      }
    }} PropertyObject.search (sq)
    

    事实上,我确信它可以与 hstore 一起使用。因为我将翻译存储在 hstore 中并且它的索引很好 - 只需要指向正确的字段(在这个任务中 Marvel 帮助自动完成)。

    【讨论】:

      【解决方案2】:

      你试过了吗?

      def search
        options = { :page => (params[:page] || 1) }
        @property_objects = PropertyObject.search, options do |f|
                              f.query { string params[:q] }
                              f.sort { by :price, 'desc' }
                            end
        @property_objects.records
      end
      

      【讨论】:

      • 嗨。感谢您的回答。您的代码在此视图中不起作用,经过一些重构,它看起来像:query = params[:q] property_objects = PropertyObject.search query,options do |f| f.query { string query } f.sort { by :price, 'asc' } end @property_objects = property_objects.records 但它仍然没有排序。我也试过link这个例子——但同样的事情——没有排序。想想我们发送的 :price 参数中的问题。开始认为我们在这里需要别的东西
      • 对不起我的回答...请查看此链接以获取信息。 elastic.co/guide/en/elasticsearch/guide/master/… ...我认为您必须使用nested_filter。我不确定 elasticsearch rails 是否支持nested_filter。您可以尝试以这种模式构造一个json查询并将其发送到elasticsearch。
      • 感谢您的链接。将尝试使用此过滤器。
      猜你喜欢
      • 2014-06-20
      • 1970-01-01
      • 2015-02-19
      • 1970-01-01
      • 2018-05-09
      • 1970-01-01
      • 2013-11-11
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多