Rails - RSpec应该无效

时间:2013-06-06 18:34:45

标签: ruby-on-rails rspec

我有一个具有开始日期和结束日期的用户事件的以下模型,我写了一些方法来验证开始和结束日期以及它们之间的关系

class Event < ActiveRecord::Base
  attr_accessible :start, :finish

  validate :must_start_now_or_in_future, 
  :must_have_a_start_if_has_an_end, 
  :start_and_end_must_not_be_equal,
  :must_have_valid_start,:must_have_valid_finish

  def must_start_now_or_in_future
    if start 
        if start.to_time.to_i < DateTime.now.to_time.to_i
            errors.add(:start,'Start date must be in the future')
        end
    end
  end

  def must_have_a_start_if_has_an_end
    if !start && finish
        errors.add(:end,'Start date must also be specified if finish date is specified')
    end
  end

  def start_and_end_must_not_be_equal
    if start && finish
        if start.to_time.to_i == finish.to_time.to_i
            errors.add(:start, 'Start and finish dates cannot be the same')
        end
    end
  end

  def must_have_valid_start
    if start
        begin
            DateTime.parse(start.to_s)
        rescue
            errors.add(:start, 'Start and finish dates must be valid')
        end
    end
  end

  def must_have_valid_finish
    if finish
        begin
            DateTime.parse(finish.to_s)
        rescue
            errors.add(:finish, 'Start and finish dates must be valid')
        end
    end
  end

end

我还写了RSpec测试,看看验证是否正确执行

require 'spec_helper'
require 'date'

describe Event do

    before(:each) do
        @attr = {:start=>DateTime.now, :finish=>2.days.from_now}
    end

    it "should create an instance with valid attributes" do
        event = Event.create!(@attr)
    end

    it "should create an instance if start and/or end are nil" do
        Event.create!(@attr.merge({:start=>nil,:finish=>nil}))
        Event.create!(@attr.merge({:finish=>nil}))
    end

    it "should start now or in the future" do
        past = Event.new(@attr.merge({:start=>2.days.ago}))
        past.should_not be_valid
    end

    it "should have a start if it has an end" do
        no_start_but_end_event = Event.new(@attr.merge({:start=>nil}))
        no_start_but_end_event.should_not be_valid
    end

    it "should not have equal start and end dates" do
        equal_start_and_end = Event.new(@attr.merge({:finish=>DateTime.now}))
        equal_start_and_end.should_not be_valid
    end

    it "should not have invalid start date" do
        invalid_start = Event.new(@attr.merge({:start=>'abcdef'}))
        invalid_start.should_not be_valid
    end

    it "should not have invalid finish date" do
        invalid_end = Event.new(@attr.merge({:finish=>'abcdef'}))
        invalid_end.should_not be_valid
    end

end

由于某种原因,“不应该有无效的完成日期”测试会一直失败,因为它将invalid_end变量视为有效。我只是无法弄清楚为什么,即使一切似乎都是正确的。我哪里错了?

1 个答案:

答案 0 :(得分:1)

我认为ActiveRecord会默默地丢弃您的无效日期信息,因此if finish阻止了:finish,因为nil仍然是{{1}}。尝试在该行之前和之后添加println或断点,以验证您是否实际进入该块。