Rails 使用 rspec 进行测试

Rails testing with rspec

我在 rails 和 rspec 中的测试有问题。总而言之,我有 4 个模型之间的结构,但目前我尝试解决其中两个模型的测试问题。我正在使用 faker 和 FactoryGirl 并拥有以下工厂:

 require 'faker'

 FactoryGirl.define do
   factory :user do |f|
     f.name { Faker::Name}
     f.email { Faker::Internet.email}
     f.password {Faker::Internet.password}
     f.role {"Kindergarten"}
   end
 end




 require 'faker'

 FactoryGirl.define do
   factory :child do |f|
     f.name { Faker::Name}
     f.city { Faker::Address.city}
     f.postalcode {Faker::Number.between(30000,35000)}
     f.streed {Faker::Address.street_name}
     f.add_number {Faker::Address.secondary_address}
     f.disability { Faker::Boolean.boolean}
     f.halal { Faker::Boolean.boolean}
     f.koscha {Faker::Boolean.boolean}
     f.vegetarian {Faker::Boolean.boolean}
     f.vegan {Faker::Boolean.boolean}
     f.allday { Faker::Boolean.boolean}
     f.gender { Faker::Number.between(0,1)}
     f.user_id {Faker::Number.between(1,10)}
   end
 end

我的控制器测试看起来像那样

 require 'rails_helper'
 require 'factory_girl_rails'

 describe UsersController do

   before do
     3.times { FactoryGirl.create(:child)}
   end

   describe "GET #show" do
     let(:user) { FactoryGirl.create(:user) }
     before { get :show, id: user.id}
     it "assigns the requested user to @user" do
       assigns(:user).should eq user
     end
     it "renders  the :show template"
   end

   describe "GET #new" do
     let(:user) { FactoryGirl.create(:user) }
     it "assigns a new User to @user" do
       get :new, id: user.id
       assigns(:user).should be_a_new(User)
     end
     it "renders  the :new template"
   end

 end

当我尝试 运行 测试时,收到此错误消息

  UsersController GET #new assigns a new User to @user
      Failure/Error: 3.times { FactoryGirl.create(:child)}

      ActiveRecord::RecordInvalid:
        Validation failed: User can't be blank

我在模型中的关系和验证如下

 class Child < ApplicationRecord

   has_many :relations, :dependent => :destroy
   accepts_nested_attributes_for :relations
   belongs_to :user
   validates :user, presence: true
   validates :name, presence: true, length: { maximum: 50 }
   validates :city, presence: true, :on => :create
     validates :postalcode, presence: true, numericality: true
       validates :streed, presence: true
         validates :add_number, presence: true

 validates :disability, inclusion: { in: [true, false] }
 validates :halal, inclusion: { in: [true, false] }
 validates :koscha, inclusion: { in: [true, false] }
 validates :vegetarian, inclusion: { in: [true, false] }
 validates :vegan, inclusion: { in: [true, false] }
 validates :allday, inclusion: { in: [true, false] }

 validates :gender, presence: true

 end


 class User < ApplicationRecord
   attr_accessor :remember_token, :activation_token, :reset_token
   has_many :children, dependent: :destroy
   has_many :kindergartens, dependent: :destroy
   has_many :relations, dependent: :destroy
   before_save   :downcase_email
   before_create :create_activation_digest
   validates :name, presence: true, length: { maximum: 50 }
   VALID_EMAIL_REGEX = /\A[\w+\-.]+@[a-z\d\-.]+\.[a-z]+\z/i
   validates :email, presence: true, length: { maximum: 255 },
                     format: { with: VALID_EMAIL_REGEX },
                     uniqueness: { case_sensitive: false }

 validates :role, presence: true


   has_secure_password
   validates :password, presence: true, length: { minimum: 6 }, allow_nil: true
 end

我的问题是,我不确定我的 rspec 代码是否有错误,或者我是否在正常模型的验证和关系中犯了错误。有人可以帮助我吗?

我觉得还是post整个工厂给你比较好。如果 Gemfile 中有它,我认为你不需要 require faker

FactoryGirl.define do
  factory :child do 
    name { Faker::Name}
    city { Faker::Address.city}
    postalcode {Faker::Number.between(30000,35000)}
    streed {Faker::Address.street_name}
    add_number {Faker::Address.secondary_address}
    disability { Faker::Boolean.boolean}
    halal { Faker::Boolean.boolean}
    koscha {Faker::Boolean.boolean}
    vegetarian {Faker::Boolean.boolean}
    vegan {Faker::Boolean.boolean}
    allday { Faker::Boolean.boolean}
    gender { Faker::Number.between(0,1)}
    user
  end
end

当您需要为特定用户创建 child 时的内部规范:

let(:current_user) { create :user }
let(:child) { create :child, user: current_user }

尝试更改您的控制器规格:

 describe UsersController do
   let(:user) { create(:user) }

   describe "GET #show" do

     before { get :show, params: { id: user.id } }
     it "assigns the requested user to @user" do
       assigns(:user).should eq user
     end
     it "renders  the :show template"
     it { expect(response).to have_http_status 200 }
   end

   describe "GET #new" do
     before { get :new }

     it "assigns a new User to @user" do
       assigns(:user).should be_a_new(User)
     end
     it "renders  the :new template"
   end
 end