RSpec - 模型唯一性测试问题

时间:2014-03-25 21:08:25

标签: ruby-on-rails rspec

我正在尝试进行一些简单的模型测试:

/app/models/album.rb:

class Album < ActiveRecord::Base
    has_many :slides, dependent: :restrict_with_exception
    validates :name, presence: true
end

/spec/model/album_spec.rb:

require 'spec_helper'

describe Album do
    before do
        @album = Album.new(name: 'Example Album')
    end

    describe "when album name is already taken" do
        before do
            another_album = @album.dup
            another_album.save
        end

        it { should_not be_valid }
    end
end

我原本期望它首先失败(因为我没有validates :uniqueness并且名字字段上有索引)但是它已经通过了。所以我改变了:

it { should_not be_valid }it { should be_valid }

要了解发生了什么,这就是我得到的:

 1) Album when album name is already taken should be valid
     Failure/Error: it { should be_valid }
       expected #<Album id: nil, name: nil, created_at: nil, updated_at: nil> to be valid, but got errors: Name can't be blank
     # ./spec/models/album_spec.rb:14:in `block (3 levels) in <top (required)>'

我想问你我做错了什么。

还有一件事是,我是否可以/应该使用expect而不是should语法?我在某处读到should有点弃用,而不是expect,但我不知道如何使用它进行模型测试(我在我的Controller / View测试中以{{{ 1}}或expect(page)。我可以为模型使用什么参数?

2 个答案:

答案 0 :(得分:2)

我从未见过您正在使用的it语法。首先,我会查看此处提供的快速入门文档:https://github.com/rspec/rspec-rails#model-specs,然后确保您熟悉这组文档:http://rspec.info/

来自github的例子:

require "spec_helper"

describe User do
  it "orders by last name" do
    lindeman = User.create!(first_name: "Andy", last_name: "Lindeman")
    chelimsky = User.create!(first_name: "David", last_name: "Chelimsky")

    expect(User.ordered_by_last_name).to eq([chelimsky, lindeman])
  end
end

您可能希望将第二个describe更改为it,然后使用一个或多个expect来确定测试是否通过。 it采用出现在测试输出中的字符串。所以一般来说你想要表达一些东西。此外,这里不需要使用前面的块。您可以在it区块中执行所有操作:

require 'spec_helper'

describe Album do
  it "fails validation when album name is already taken" do
    album = Album.new(name: 'Example Album')
    another_album = album.dup
    expect {another_album.save!}.to  raise_error(ActiveRecord::RecordInvalid,'Validation failed: This question is no longer active.')
  end
end

答案 1 :(得分:1)

在您的示例之前设置explicit subject

subject {@album}
it { should_not be_valid }

目前,根据失败错误#<Album id: nil, name: nil, created_at: nil, updated_at: nil>,在示例之前找不到Album的隐式空白实例。