我想在我的Rails 5项目中使用ThinkingSphinx(带有SQL支持的索引)。ThinkingSphinx:SQL支持索引上的动态索引?
我需要一些动态运行时索引来搜索。
我有一个Message
模型:
class Message < ApplicationRecord
belongs_to :sender, class_name: 'User', :inverse_of => :messages
belongs_to :recipient, class_name: 'User', :inverse_of => :messages
end
及其索引:
ThinkingSphinx::Index.define :message, :with => :active_record, :delta => true do
indexes text
indexes sender.email, :as => :sender_email, :sortable => true
indexes recipient.email, :as => :recipient_email, :sortable => true
indexes [sender.email, recipient.email], :as => :messager_email, :sortable => true
has sender_id, created_at, updated_at
has recipient_id
end
schema.rb:
create_table "messages", force: :cascade do |t|
t.integer "sender_id"
t.integer "recipient_id"
t.text "text"
t.datetime "created_at", null: false
t.datetime "updated_at", null: false
t.boolean "read", default: false
t.boolean "spam", default: false
t.boolean "delta", default: true, null: false
t.index ["recipient_id"], name: "index_messages_on_recipient_id", using: :btree
t.index ["sender_id"], name: "index_messages_on_sender_id", using: :btree
end
问题是关于所谓的 “对话”。它们不存在于数据库中 - 它们是在运行时确定的。对话框 - 这是2个用户之间的一组消息,每个用户可能是发送者或接收者。
任务是搜索我的对话框,并通过通讯录电子邮件找到对话框(对话框的消息)。太复杂了!
这里是我的努力:
conditions = {messager_email: search_email}
with_current_user_dialogs =
"*, IF(sender_id = #{current_user.id} OR recipient_id = #{current_user.id}, 1, 0) AS current_user_dialogs"
messages = Message.search search_email, conditions: conditions,
select: with_current_user_dialogs,
with: {'current_user_dialogs' => 1}
这几乎是罚款 - 但仍然没有。此查询仅在我的对话框(在我发送或接收的消息内)内正确搜索,并且仅在:sender
和:recipient
字段中同时发生(这不是最佳的)。
说我的电子邮件是“[email protected]”。其他电子邮件如“[email protected]”,“[email protected]”,“[email protected]”。
麻烦的是,当我搜索“client1”时 - 我收到了我是发件人或收件人的所有消息。但我不应该得到任何回应 - 我只需要在我的记者电子邮件中搜索 - 而不是我的。
甚至在查询“客户端”时也会发生更糟糕的事情 - 我通过“[email protected]”,“[email protected]”取回正确的通讯记录,但结果被错误地改为“client1 @ example”。 COM”。
我需要一种方法来在运行时选择 - 在哪个索引子集中进行搜索。
我的意思是这个条件是不够的,我说:
indexes [sender.email, recipient.email], :as => :messager_email, :sortable => true
它搜索(对于“客户”)内所有的sender.email和所有的recipient.email一次。
但我需要动态地选择,如:“搜索仅内sender.email
值符合if sender.id != current_user.id
”或“搜索仅内recipient.email
符合if recipient.id != current_user.id
”(因为我可以作为一个发送者作为接收器)。
这就是我所说的“动态指数”。
如何做到这一点?这样的“动态指标”肯定取决于当前的价值 - 所以即使在相同的总消息集中,不同用户也会有所不同。
很明显,我不能申请任何后搜索截止(什么切断?) - 我需要以某种方式限制搜索本身。
我试图搜索一些范围 - 但得到的错误是“搜索范围不可能” - 类似的东西。
也许我应该使用实时索引而不是SQL支持索引?
对不起我的问题的复杂性。
我需要一个“实时搜索” - 当用户输入一个搜索词(逐个字母)时,搜索结果会立即缩小。所以我需要一个搜索引擎 - 只需ActiveRecord是不够的。 – prograils
我可以有一些模型带有实时索引,并且一些带有SQL支持索引**吗?那么我应该如何应用 - 'rake ts:regenerate'或'rake ts:rebuild'? – prograils
恐怕,您目前无法混合使用SQL支持的索引和实时支持的索引。 – pat