2012-05-17 28 views
5

İşte benim şimdiki sınıf tanımı ve Spec:Devlet Makinesi, Model Doğrulama ve RSpec

class Event < ActiveRecord::Base 

    # ... 

    state_machine :initial => :not_started do 

    event :game_started do 
     transition :not_started => :in_progress 
    end 

    event :game_ended do 
     transition :in_progress => :final 
    end 

    event :game_postponed do 
     transition [:not_started, :in_progress] => :postponed 
    end 

    state :not_started, :in_progress, :postponed do 
     validate :end_time_before_final 
    end 
    end 

    def end_time_before_final 
    return if end_time.blank? 
    errors.add :end_time, "must be nil until event is final" if end_time.present? 
    end 

end 

describe Event do 
    context 'not started, in progress or postponed' do 
    describe '.end_time_before_final' do 
     ['not_started', 'in_progress', 'postponed'].each do |state| 
     it 'should not allow end_time to be present' do 
      event = Event.new(state: state, end_time: Time.now.utc) 
      event.valid? 
      event.errors[:end_time].size.should == 1 
      event.errors[:end_time].should == ['must be nil until event is final'] 
     end 
     end 
    end 
    end 
end 

Ben spec çalıştırdığınızda, iki arızaları ve bir başarı elde. Neden olduğuna dair hiçbir fikrim yok. Durumların ikisi için end_time_before_final yöntemindeki return if end_time.blank? ifadesi, her seferinde yanlış olması gerektiğinde doğru olarak değerlendirilir. 'ertelendi' geçecek gibi görünen tek durumdur. Burada neler olabileceğine dair bir fikrin var mı?

+0

'before_transition: => tarih: game_ended' eksik görünüyor – apneadiving

+0

nesneleri başarısız özellikleri geçerli midir? – apneadiving

+0

Before_transition kaldırıldı. Nesnelerden ikisi şu adresten geçerlidir: end_time ve bir tanesi şu adresten geçerlidir: end_time. – keruilin

cevap

13

Eğer documentation belirtildiği bir uyarı yaşamaya devam edip anlaşılıyor: Burada

Bir önemli uyarı, yani nedeniyle ActiveModel en doğrulama çerçevesinde bir kısıtlama olduğunu, özel doğrulayıcılar olarak çalışmayacaktır Birden çok durumda çalıştırmak için tanımlandığında bekleniyor. Örneğin: Bu durumda

class Vehicle 
    include ActiveModel::Validations 

    state_machine do 
    ... 
    state :first_gear, :second_gear do 
     validate :speed_is_legal 
    end 
    end 
end 

: second_gear devlet: speed_is_legal doğrulama yalnızca çalıştırmak alacak. Bunu önlemek için, bu kadar sevdiği özel doğrulama tanımlayabilirsiniz:

class Vehicle 
    include ActiveModel::Validations 

    state_machine do 
    ... 
    state :first_gear, :second_gear do 
     validate {|vehicle| vehicle.speed_is_legal} 
    end 
    end 
end 
+0

Sweet! Okumak için öder. Benden daha çok gözlemci olduğun için teşekkürler. – keruilin