2009-12-31 48 views
18

我有一個Trip模型,其中包含start_odometer和end_odometer值。 在我的模型中,我想驗證結束里程錶比起始里程錶大。 結束里程錶也可以是空白的,因爲行程可能尚未完成。Rails greater_than對模型屬性的模型驗證

但是,我無法弄清楚如何將一個屬性與另一個屬性進行比較。

在trip.rb:

對符號進行比較:

validates_numericality_of :end_odometer, :greater_than => :start_odometer, :allow_blank => true 

給我的錯誤:

ArgumentError in TripsController#index

:greater_than must be a number

對變量進行比較:

validates_numericality_of :end_odometer, :greater_than => start_odometer, :allow_blank => true 

NameError in TripsController#index

undefined local variable or method `start_odometer' for #

+1

我覺得這會是這樣Rails中非常有用。也許向Lighthouse提交一張票:http://rails.lighthouseapp.com呢? – 2009-12-31 04:07:12

回答

18

你可能需要寫在你的模型這是一個自定義的驗證方法...

validate :odometer_value_order 

def odometer_value_order 
    if self.end_odometer && (self.start_odometer > self.end_odometer) 
    self.errors.add_to_base("End odometer value must be greater than start odometer value.") 
    end 
end 
+0

謝謝,效果很棒! – Ryan 2009-12-31 01:11:54

-4

這是一個有點缺憾,但這似乎工作:

validates_numericality_of :end_odometer, :greater_than => :start_odometer.to_i, :allow_blank => true 
+0

您需要一個proc或lambda來運行這個例子。 – holden 2011-08-21 11:37:39

+3

絕對不行,將符號':start_odometer'轉換爲整數並將其傳遞給':greater_than'。 **不要使用此代碼,它是完全錯誤的**。 – meagar 2012-08-03 17:25:04

32

你不」對於這種情況,一定需要定製的驗證方法。事實上,當你只用一條線就可以做到這一點有點矯枉過正。 jn80842的建議很接近,但您必須將其包裝在Proc或Lambda中才能使用。

validates_numericality_of :end_odometer, :greater_than => Proc.new { |r| r.start_odometer }, :allow_blank => true 
+0

正在尋找相同的東西,這種方法對我很好。 – Sg1team 2013-04-06 08:23:38

+4

不需要'Proc',只需':start_odometer'就可以工作。 – 2014-04-30 20:29:42

6

如果您使用Proc,則可以針對模型屬性進行驗證。

在rails4你會做這樣的事情:

class Trip < ActiveRecord::Base 
    validates_numericality_of :start_odometer, less_than: ->(trip) { trip.end_odometer } 
    validates_numericality_of :end_odometer, greater_than: ->(trip) { trip.start_odometer } 
end