rspec 测试子类 sti 方法 rails 4
rspec testing subclass sti methods rails 4
我正在尝试为 sti 子类上的方法构建 rspec 测试,而该测试仅读取父模型的方法。该方法适用于应用程序,但不适用于 rspec 测试。我不知道我错过了什么
models/animals/animal.rb
class Animal < ActiveRecord::Base
def favorite
"unicorn"
end
end
models/animals/mammal_animal.rb
class MammalAnimal < Animal
def favorite
"whale"
end
end
models/animals/cat_mammal_animal.rb
class CatMammalAnimal < MammalAnimal
def favorite
"tabby"
end
end
mammal_animal_spec.rb
require 'rails_helper'
RSpec.describe MammalAnimal, type: :model do
let(:cat_mammal_animal) {FactoryGirl.create(:cat_factory)}
subject(:model) { cat_mammal_animal }
let(:described_class){"MammalAnimal"}
describe "a Cat" do
it "should initialize successfully as an instance of the described class" do
expect(subject).to be_a_kind_of described_class
end
it "should have attribute type" do
expect(subject).to have_attribute :type
end
it "has a valid factory" do
expect(cat_mammal_animal).to be_valid
end
describe ".favorite " do
it 'shows the favorite Cat' do
expect(cat_mammal_animal.type).to eq("CatMammalAnimal")
expect(cat_mammal_animal.favorite).to include("tabby")
expect(cat_mammal_animal.favorite).not_to include("whale")
expect(cat_mammal_animal.favorite).not_to include("unicorn")
print cat_mammal_animal.favorite
end
end
end
end
错误
Failures:
1) MammalAnimal.favorite and .favorite shows the favorite Cat
Failure/Error: expect(cat_mammal_animal.type).to include("tabby")
expected "unicorn" to include "tabby"
# ./spec/models/mammal_animal_spec.rb:82:in `block (3 levels) in <top (required)>'
更新
animals.rb
FactoryGirl.define do
factory :animal do
type 'Animal'
name "dragon"
trait :mammal do
type 'MammalAnimal'
name "zebra"
end
trait :cat do
type 'CatMammalAnimal'
name "calico"
end
factory :mammal_factory, traits: [:mammal]
factory :cat_factory, traits: [:cat]
end
end
根据建议,我在测试中添加了以下行
期望(cat_mammal_animal.class.constantize).eq(CatMammalAnimal)
遇到这个错误
1) MammalAnimal.favorite 和 .favorite 显示最喜欢的猫
Failure/Error: expect(cat_animal_mammal.class.constantize).to eq(CatMammalAnimal)
NoMethodError:
undefined method `constantize' for #<Class:0x007f8ed4b8b0e0>
Did you mean? constants
我认为与其使用 trait
创建子类的对象,不如为它们创建单独的工厂。
factory :animal do
name 'dragon'
end
factory :mammal, class: MammalAnimal do
name 'zebra'
end
factory :cat, class: CatMammalAnimal do
name 'calico'
end
所有这些都可以在animals.rb
中定义
然后你可以像
一样创建你的对象
create(:animal)
create(:mammal)
create(:cat)
我正在尝试为 sti 子类上的方法构建 rspec 测试,而该测试仅读取父模型的方法。该方法适用于应用程序,但不适用于 rspec 测试。我不知道我错过了什么
models/animals/animal.rb
class Animal < ActiveRecord::Base
def favorite
"unicorn"
end
end
models/animals/mammal_animal.rb
class MammalAnimal < Animal
def favorite
"whale"
end
end
models/animals/cat_mammal_animal.rb
class CatMammalAnimal < MammalAnimal
def favorite
"tabby"
end
end
mammal_animal_spec.rb
require 'rails_helper'
RSpec.describe MammalAnimal, type: :model do
let(:cat_mammal_animal) {FactoryGirl.create(:cat_factory)}
subject(:model) { cat_mammal_animal }
let(:described_class){"MammalAnimal"}
describe "a Cat" do
it "should initialize successfully as an instance of the described class" do
expect(subject).to be_a_kind_of described_class
end
it "should have attribute type" do
expect(subject).to have_attribute :type
end
it "has a valid factory" do
expect(cat_mammal_animal).to be_valid
end
describe ".favorite " do
it 'shows the favorite Cat' do
expect(cat_mammal_animal.type).to eq("CatMammalAnimal")
expect(cat_mammal_animal.favorite).to include("tabby")
expect(cat_mammal_animal.favorite).not_to include("whale")
expect(cat_mammal_animal.favorite).not_to include("unicorn")
print cat_mammal_animal.favorite
end
end
end
end
错误
Failures:
1) MammalAnimal.favorite and .favorite shows the favorite Cat
Failure/Error: expect(cat_mammal_animal.type).to include("tabby")
expected "unicorn" to include "tabby"
# ./spec/models/mammal_animal_spec.rb:82:in `block (3 levels) in <top (required)>'
更新
animals.rb
FactoryGirl.define do
factory :animal do
type 'Animal'
name "dragon"
trait :mammal do
type 'MammalAnimal'
name "zebra"
end
trait :cat do
type 'CatMammalAnimal'
name "calico"
end
factory :mammal_factory, traits: [:mammal]
factory :cat_factory, traits: [:cat]
end
end
根据建议,我在测试中添加了以下行
期望(cat_mammal_animal.class.constantize).eq(CatMammalAnimal)
遇到这个错误
1) MammalAnimal.favorite 和 .favorite 显示最喜欢的猫 Failure/Error: expect(cat_animal_mammal.class.constantize).to eq(CatMammalAnimal)
NoMethodError:
undefined method `constantize' for #<Class:0x007f8ed4b8b0e0>
Did you mean? constants
我认为与其使用 trait
创建子类的对象,不如为它们创建单独的工厂。
factory :animal do
name 'dragon'
end
factory :mammal, class: MammalAnimal do
name 'zebra'
end
factory :cat, class: CatMammalAnimal do
name 'calico'
end
所有这些都可以在animals.rb
然后你可以像
一样创建你的对象create(:animal)
create(:mammal)
create(:cat)