2012-03-02 5 views
2

Railsアプリケーションでフィルタリングに問題があります。ユーザーはタグを使用して項目をフィルタリングする必要があります。これは問題ありません。名前付きスコープを使用しています。しかし、タグはこのように、ユーザーが選択できるボックスに来る:RailsクエリでANDとORでフィルタリングする

Size 
    [XS] 
    [S] 

Color 
    [Red] 
    [Blue] 

タグ、「タグセット」に多くのタグに1個のタグセットです。

質問:ユーザーが検索の絞り込みを行うときに、複数のフィルタクエリを連鎖させるにはどうすればよいですか?

ユーザが最初のボックスからXSを選択すると、そのタグだけで結果セットがフィルタリングされます。ユーザーがXSとSを選択すると、フィルターに追加されてより多くの結果が得られます。まだ名前付きスコープに問題はありません。しかし、ユーザーが2番目のボックスからXSとSをフィルタリングし、次に赤色をフィルタリングしたい場合はどうなりますか?それは物事が毛むくじゃらするとき - 私はそのタグのために別のItem.by_tag( "tagname")をタックすることはできません、私が既に持っている結果のタグフィルタである必要があります、結果を狭める。

同じタグセットボックス内に複数のチェックボックスがあります。別のタグセットボックスのチェック - 少ない結果。私は、各タグセットボックスに対して1つのSELECTを実行してから、すべてのセットに含まれていたヒットのみを表示するためにルビの結果セットをマージしましたが、結果が返される回数は決して分からないので、これは1つのクエリである必要があり、それはおそらく何らかの結合であると感じますが、私はSQLではそれほど素晴らしいものではなく、わかりません。

create_table "items" do |t| 
    t.string "title" 
end 

create_table "items_tags", :id => false do |t| 
    t.integer "item_id" 
    t.integer "tag_id" 
end 

create_table "tags" do |t| 
    t.string "title" 
    t.integer "tagset_id" 
end 

create_table "tagsets" do |t| 
    t.string "title" 
end 

答えて

0

RailsはORクエリを作成する方法を提供していないようです。だから、あなたはそれを自分で行う必要があります。 スキーマによれば、アイテムhas_and_belongs_to_many:タグ、そうですか? Rails 2.3では、named_scopesの次に動作するはずです。 Rails 3を使用している場合は、それを書き直す必要があります。

named_scope :having_tags, lambda { |tagsets| {:joins => :tags, :select => "DISTINCT items.*", 
    :conditions => ([Array.new(tagsets.size, "tags.title IN (?)").join(' OR ')] + tagsets) } 

は、その後、あなたはこのようにそれを呼び出す:

Item.having_tags([['XS', 'S'], ['Red', 'Blue']]) 

私はMySQLを使っていると仮定しています。

+0

うまくいった。ありがとう! – straffaren

関連する問題