简体   繁体   中英

Rails testing with rspec

I have a problem with my testing in rails with rspec. All in all I have a structure between 4 models, but for the moment I try to solve my testing for two of them. I'm using faker and FactoryGirl and have the following factories:

 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

and my controller test looks like that

 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

When I try to run the test, I got this error message

  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

My relations and validations in the models are as follow

 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

My problem is, that I'm not sure if there is a fault in my rspec code or if I have made a mistake in my validations and relations in my normal models. Can someone help me?

I think that it would be better to post the whole factory for you. And I think you don't need to require faker if you have it in Gemfile.

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

Inside specs when you need to create a child for the particular user:

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

Try to change your controller spec:

 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

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM