2012-01-26 5 views
1

타이어로 쿼리를 다시 쓰려고합니다.타이어로 SQL 쿼리 다시 작성

class User < ActiveRecord::Base 
    has_many :bookmarks, :dependent => :destroy 
    has_many :followed_venues, :through => :bookmarks, :source => :bookmarkable, :source_type => 'Venue' 
end 

사용자는 장소에 따라 할 수 있습니다

는 내가 가지고있는 모델입니다. 특정 사용자가 따라 다니는 장소를 검색해야합니다.

@user.followed_venues.where(["venues.title LIKE ?", "%"+params[:q]+"%"]) 

이 분명 좋지 않은, 그래서 나는 타이어 내 응용 프로그램에 elasticsearch를 추가 :

지금까지 내가 액티브 함께 해왔습니다.

타이어가있는 경기장을 검색하는 방법은 다음과 같습니다.

답변

1

나는 내 자신의 질문에 대한 답변을 게시 할 것입니다.

따라서 장소를 검색하는 것은 매우 쉽습니다. 표준 Venue.tire.search {...} 문제는 장소를 따라 오는 사용자별로 필터링하는 방법입니다. 검색을 위해 Venue 모델을 사용하는 대신 북마크를 색인하기로 결정했습니다.

이 내가 USER_ID 인덱스에 장소 이름이 내 북마크 모델이 후

class Bookmark < ActiveRecord::Base 
    belongs_to :bookmarkable, :polymorphic => true 

    def to_indexed_json 
    { 
     :title => bookmarkable.display_name, 
     :user_id => user_id 
    }.to_json 
    end 
end 

입니다. 이제 검색은 다음과 같이 간단 해집니다.

Bookmark.tire.search :load => {:include => 'bookmarkable'}, :page => page, :per_page => per_page do 
    query do 
    fuzzy :title => { :value => query.downcase, :min_similarity => 0.6, :prefix_length => 2} 
    end 
    filter :terms, {:bookmarkable_type => ["Venue"], :user_id => [user.id]} 
end 

이제 완벽한 해결책이 아닙니다. 그리고 내가 심지어 filter :terms을 올바르게 사용하기를 바랍니다. 지금 내가 얻은 결과는 실제로 북마크의 배열이다. 하지만 실제 장소를로드하기가 쉽고, 프론트 엔드의 페이지 매김을 높이기 위해 WillPaginate 컬렉션으로 둘러 쌀 수도 있습니다.

이 솔루션에 문제가 있습니까? 사용자 ID를 장소 색인에 넣을 때 제시 한 것과 phoet의 제안 내용을 비교하면 어떨까요?

+0

솔루션의 문제점은 쿼리에서'load'를 사용하면 데이터베이스에 도달한다는 것입니다. 물론 elasticsearch 지수 만 사용하는 것보다 빠릅니다. – tommasop

+0

예, 이해합니다. 하지만 AR 객체가 필요합니다. – egze

+0

퍼지 방법이 없습니다. 이 코드는 제대로 작동하지 않습니다. –

0

나는 각 장소에 대한 문서를 만들고 다음에 나오는 모든 사용자 ID 배열로 필드를 추가합니다.

정말로 이것이 elasticsearch에 적절한 작업인가요?

나는 장소의 이름에 대한 색인을 검색 한 다음 관계형 데이터베이스에서 필요한 데이터를 찾는 것이 더 쉬울 것이라고 생각합니다.

+0

나는 elasticsearch에 대한 작업이라고 생각합니다. 왜냐하면 장소 이름에 퍼지 (fuzzy) 일치를 원하기 때문입니다. 나는 그것에 대해 어떻게 접근해야하는지 또 다른 접근법을 시도하고있다. 장소를 색인하는 대신 user_id가있는 책갈피를 색인화하고 색인에 장소 이름을 추가합니다. 나는 그 해결책을 초에 올릴 것이다. – egze

+0

@phoet 그렇습니다. elasticsearch 질의 자체에서'filter'를 사용하는 것이 바람직하다고 생각합니다. 왜냐하면 데이터베이스 질의는 매우 간단하고 빠르기 때문입니다. 분명히 한 가지 단점은 데이터베이스와 인덱스를 동기화하여 사용자간에 레코드가 섞이지 않아야한다는 것입니다. – karmi