2012-04-30 34 views

回答

2

我會把這一切都在一個地方塊。例如,下面是基於類似的複雜「其中」第一個「範圍」:

class Foo < ActiveRecord::Base 
    def self.my_complex_where(args) 
    where("(col1 = ? AND col2 = ?) OR (col3 = ? AND col4 = ?)", 
      args[:val1], args[:val2], args[:val3], args[:val4]) 
    end 
end 

或者,你使用這個符號可以做到這一點:

class Foo < ActiveRecord::Base 
    def self.my_complex_where(args) 
    where("(col1 = :val1 AND col2 = :val2) OR (col3 = :val3 AND col4 = :val4)", 
      :val1 => args[:val1], 
      :val2 => args[:val2], 
      :val3 => args[:val3], 
      :val4 => args[:val4]) 
    end 
end 
+0

這是不是最好的Arel解決方案,因爲您仍然需要編寫SQL。 – rxgx

+0

它甚至不是一個arel解決方案 –

1

除了已經給出了答案,你可能也想看看寶石 '​​'

例子:

Person.where{(name =~ 'Ernie%') & (salary < 50000) | (name =~ 'Joe%') & (salary > 100000)} 
+0

鏈接的squeel已損壞。 請參閱https://rubygems.org/gems/squeel – kuboon

2

您需要下降到更原始AREL

t = Model.arel_table 
a = (t[:a].eq(nil).and(t[:b].eq(nil))) 
b = (t[:a].not_eq(nil).and(t[:b].not_eq(nil))) 
Model.where(a.and(b)) 
+0

這並不反映所要求的邏輯 –

+0

良好的捕獲,將upvote你的。這就是我在同一時間回答2個類似問題的結果。 –

7

小李的答案基本上是你在找什麼

class Model < ActiveRecord::Base 
    def self.this_or_that(a1, a2, a3, a4) 
    t = Model.arel_table 
    q1 = t[:a].eq(a1).and(t[:b].eq(a2)) 
    q2 = t[:c].eq(a3).and(t[:d].eq(a4)) 
    where(q1.or(q2)) 
    end 
end 

一些slides我放在一起的阿雷爾

+1

通過使用t.grouping選項,我能夠使其工作(在v4.0.1中)。在上面的示例中,我仍然得到(a和b或c和d)。第12頁上的幻燈片具有按預期工作的分組語法((a和b)或(c和d))。 – NotDan