Rails和Rspec - 在表单提交失败时检查是否存在错误

时间:2011-10-20 20:39:13

标签: ruby-on-rails ruby-on-rails-3 rspec rspec2

我有一个Foo模型,创建时需要:name

我正在编写一个规范来测试验证

it 'should not create an invalid Foo' do
  fill_in "Name", :with=>""
  # an error message will be displayed when this button is clicked
  click_button "Create Foo"
end

如何确认页面上是否显示错误消息?

我试过page.errors.should have_key(:name)但这不对。

我想我可以做page.should have_content("Name can't be blank")但我宁愿避免将我的集成测试与内容强烈耦合

3 个答案:

答案 0 :(得分:12)

如果您在单元测试级别正确测试验证,则可以轻松地为所需的错误消息添加另一个测试:

describe Foo do
  describe "validations" do
    describe "name" do
      before { @foo = FactoryGirl.build(:foo) } # or Foo.new if you aren't using FactoryGirl

      context "when blank" do
        before { @foo.name = "" }

        it "is invalid" do
          @foo.should_not be_valid
        end

        it "adds the correct error message" do
          @foo.valid?
          @foo.errors.messages[:name].should include("Name cannot be blank")
        end
      end # positive test case omitted for brevity
    end
  end
end

这样,您已经隔离了错误生成并复制到模型,并且可靠地进行了测试,这允许您实现某种全局错误显示(例如,使用flash[:error],而无需测试在视图级别明确显示每条错误消息。

答案 1 :(得分:6)

你说你正在编写一个规范来测试验证,但是我看到你用“fill_in”测试了水豚(或类似的)

相反,我强烈建议您编写单元测试来测试模型。

规格/模型/ your_model_spec.rb

require 'spec_helper'
describe YourModel do

  it "should not allow a blank name" do
    subject.name = ""
    subject.should_not be_valid
    subject.should have(1).error_on(:name)
  end

end

这样,你就是在隔离测试 - 只测试你需要测试的内容,而不是控制器是否正常工作,或是视图,甚至是通过闪存循环。

这样,您的测试快速,耐用且隔离。

答案 2 :(得分:1)

你的it块说'不应该创建一个无效的Foo',如果你正在测试它真的是对模型Foo进行单元测试而不是集成测试。

但是,如果您正在测试页面上的SPECIFIC错误消息,那么您需要检查内容。为了使测试更少耦合,您可以检查特定的html元素。例如,我的错误显示在flash消息中。我通过查找名为erroralert的类的div来检查它们。我忽略了实际的消息,只是检查以确保出现某种错误。