I have a controller spec something like this
describe :bizzaro_controller do
let(:credit_card_account) { FactoryGirl.build :credit_card_account }
it "doesn't blow up with just the stub" do
CreditCardAccount.stub(:new).and_return(credit_card_account)
end
it "doesn't blow up" do
credit_card_account
CreditCardAccount.stub(:new).and_return(credit_card_account)
end
end
Which results in this:
bizzaro_controller
doesn't blow up with just the stub (FAILED - 1)
doesn't blow up
Failures:
1) bizzaro_controller doesn't blow up
Failure/Error: let(:credit_card_account) { FactoryGirl.build :credit_card_account }
NoMethodError:
undefined method `exp_month=' for nil:NilClass
# ./spec/controllers/user/bizzareo_controller_spec.rb:5:in `block (2 levels) in <top (required)>'
# ./spec/controllers/user/bizzareo_controller_spec.rb:9:in `block (3 levels) in <top (required)>'
Finished in 0.23631 seconds
2 examples, 1 failure
My credit card factory looks like this:
FactoryGirl.define do
factory :credit_card_account do
exp_month 10
exp_year 2075
number '3'
end
end
My CreditCardAccount is an empty ActiveRecord::Base model
=> CreditCardAccount(id: integer, exp_month: integer, exp_year: integer, number: string)
Versions
0 HAL:0 work/complex_finance % bundle show rails rspec-rails factory_girl
/home/brundage/.rvm/gems/ruby-2.0.0-p247#complex_finance/gems/rails-4.0.0
/home/brundage/.rvm/gems/ruby-2.0.0-p247#complex_finance/gems/rspec-rails-2.14.0
/home/brundage/.rvm/gems/ruby-2.0.0-p247#complex_finance/gems/factory_girl-4.2.0
This should be working. all points that your test database is not correct.
RAILS_ENV=test rake db:drop db:create will drop and recreate your test database. Then try to run your rspec using the rake command, in order to migrate the database: rake rspec
I was having the same problem, but I think the cause of my problem was different. My solution, however, may perhaps be useful: I used the Fabrication gem (http://www.fabricationgem.org/) instead of FG.
The reason why I was having this problem was because I was trying to have FG create/build an object that was not ActiveRecord, it was only an ActiveModel, and it had to be initialized with arguments.
I didn't see in the Fabricator documentation an example totally like what I needed, but I got it with this syntax:
Fabricator(:my_class) do
on_init do
init_with("Company Name", "Fake second arg")
end
end
My problem was that in model I made a private method called :send (forgot that it is already used in Ruby).
Related
I've been building my application and I'm now ready to start testing. I have Factory girl defined in seeds.rb but as I'm running tests I've also defined the tests in the usual place /spec/factories.rb for Rspec.
However my first tests fails with the following error.
user_spec.rb
require 'spec_helper'
describe User do
it "should have valid factory" do
FactoryGirl.build(:user1).should be_valid
end
end
Error returned:
Failures:
1) User should have valid factory
Failure/Error: FactoryGirl.build(:user1).should be_valid
NoMethodError:
undefined method `first_name=' for #<User:0x000000061410f8>
# ./spec/models/user_spec.rb:5:in `block (2 levels) in <top (required)>'
Finished in 0.05459 seconds
1 example, 1 failure
Failed examples:
rspec ./spec/models/user_spec.rb:4 # User should have valid factory
Randomized with seed 29084
spec/factories.rb
FactoryGirl.define do
factory :admin1, class: User do
first_name "admin"
last_name "minstrator"
password "admin1234"
profile_name "profilename"
email "admin#admin.com"
password_confirmation "admin1234"
admin true
end
factory :user1, class: User do
first_name "user2"
last_name "man2"
password "user1234"
profile_name "profilename"
email "user2#user.com"
password_confirmation "user1234"
admin false
end
end
It works fine when using the data on development in my seed.rb but now I've started testing using Rspec it has all gone wrong.
What am I doing incorrectly here. I'm not a huge fan of testing at the moment but I need to improve my skill set here as I know it can be extremely useful for web applications.
You help is greatly appreciated, please let me know if you need anymore info.
If your code works in development, but not in test, my guess is that your test copy of the database is not in sync. Try running rake db:test:prepare or rake db:test:clone and run your specs again.
Note:
db:test:clone isn't required in Rails 4.2.0 'WARNING: db:test:clone is deprecated. The Rails test helper now maintains your test schema automatically, see the release notes for details.')
I believe the issue here was that one of my migrations was missing and because it didn't have users first_name in the model there was nothing defined.
A big tip to all newbies, never ever ever delete any of your migrations.
As Homer Simpson quite rightly said "D'oh"
I followed a few tutorials and docs of FactoryGirl to use with RSpec. Currently I get one error when trying to use FactoryGirl.create:
describe "GenericRecipesController" do
describe "GET 'index'" do
it "displays list of generic recipes" do
generic_recipe = FactoryGirl.create(:generic_recipe)
visit '/recipe'
response.should be_success
end
end
end
And the error:
GenericRecipesController GET 'index' displays list of generic recipes
Failure/Error: generic_recipe = FactoryGirl.create(:generic_recipe)
NameError:
uninitialized constant GenericRecipe
# ./spec/integration/generic_recipes_spec.rb:8:in `block (3 levels) in <top (required)>'
The rest of code is there.
You can try this:
factory :generic_recipe, class: EdibleRecipe::GenericRecipe do
# ...
end
I think problem in a nesting model in module
Upd: delete file /spec/factories.rb, in file /spec/support/factories.rb make
factory :generic_recipe, class: EdibleRecipe::GenericRecipe do
When you will run tests, probably will see 'can not load table'. Make
rake db:migrate RAILS_ENV=test
and try again.
You don't seem to have a GenericRecipe model in your app. Factory Girl is looking for a Model called GenericReciper and can't find it.
My spec/models code as require 'spec_helper'
describe Student do
it "should be work" do
student = Student.find 1
puts student.version
end
end
When running the code it shows the following error..,
Failures:
1) Student should be work
Failure/Error: student = Student.find 2
ActiveRecord::StatementInvalid:
Could not find table 'students'
# ./spec/models/student_spec.rb:6:in `block (2 levels) in <top (require
Finished in 0.00109 seconds
1 example, 1 failure
Failed examples:
rspec ./spec/models/student_spec.rb:4 # Student should be work
I'm having students table.Also, I'm using paper_trail gem.
After running rake db:test:prepare then it shows an error as.,
Failures:
1) Student should be work
Failure/Error: s = Student.find 1
ActiveRecord::RecordNotFound:
Couldn't find Student with id=1
# ./models/student_spec.rb:5:in `block (2 levels) in <top (required)>'
Finished in 0.02182 seconds
1 example, 1 failure
Failed examples:
rspec ./models/student_spec.rb:4 # Student should be work
It seems there is no table students in test environment, try to run
$ bundle exec rake db:test:prepare
Do you have propagated some data in your test database (using fixtures or something like FactoryGirl gem)?
Otherwise you wouldn't find any "students" in your DB.
Test-DB and Development DB have nothing in common. In fact the Test-DB will be cleared for each test.
The problem is there is no studend with id=1 in the students table of the test DB (the test DB is cleared before start new tests).
What do you want to test?
Maybe you want to use the before to insert a student at the start of the spec:
describe Student do
before do
#student = Student.new(:version => 15)
#student.save
end
it "should be work" do
student = Student.first
# Test something ...
end
end
The before block is run before every test, in this case you can get the first student in the (test) DB because you inserted it in the before block (but I don't know what you're trying to test and if save a student is really needed).
I have a naked rails 3 app with one model, generated using rails g model User.
I've added a factory (using factory_girl_rails):
Factory.define :user do |f|
f.email "test#test.com"
f.password "blah"
f.password_confirmation "blah"
f.display_name "neezer"
end
Then I've added one test:
require 'spec_helper'
describe User do
subject { Factory :user }
it "can be created from a factory" do
subject.should_not be_nil
subject.should be_kind_of User
end
end
Then I migrate my database using rake db:migrate.
Then I run the test using rspec spec, and the test fails with the following:
Failures:
1) User can be created from a factory
Failure/Error: subject { Factory :user }
ActiveRecord::StatementInvalid:
Could not find table 'users'
# ./spec/models/user_spec.rb:5:in `block (2 levels) in <top (required)>'
# ./spec/models/user_spec.rb:8:in `block (2 levels) in <top (required)>'
I'm confused, because I did just migrate my database, and my schema.db file reflects that there is a users table present, so what gives?
I know this is a beginner question, but banging my head against a wall isn't working...
factory_girl (1.3.3)
factory_girl_rails (1.0.1)
rails (3.0.5)
rspec-rails (2.5.0)
sqlite3 (1.3.3)
Try to execute
rake db:test:prepare
This should fix your tests db.
The point here is that rspec command doesn't execute migrations on your test database. and rake db:migrate only runs migrations in your current environment, probably development. Others environment like production and test ends without having those changes.
You can run
rake spec
That will prepare your testing db (drop and create using schema.rb) and run all tests.
As the other answer suggested, this:
rake db:test:prepare
Will also setup your testing db, but you have to run the rspec command after that, so, personally I prefer the first option.
try this out:
For rails version > 4.1+ this solution will work as the current scenario.
but in Rails 4.1+, rake db:test:prepare is deprecated.
try using
rake db:migrate RAILS_ENV=test (it will work for all version of rails)
I'm getting these failures when running rspec spec/. The spec that is failing is was auto-generated with the scaffolding. I'm trying to understand RSpec but I don't know where to begin looking for the cause other than it feels like some method is missing?!? Yet, app appears to be working fine. Nothing about these failures appears in test.log. Is there another place I should be looking for hints to track this down?
$ rspec spec/
.....................F.F.
Failures:
1) clowns/edit.html.haml renders the edit clown form
Failure/Error: render
undefined method `to_sym' for nil:NilClass
# ./app/views/clowns/_form.html.haml:4:in `block in _app_views_clowns__form_html_haml__3590088286240866241_2176114460_3896491916910336970'
# ./app/views/clowns/_form.html.haml:1:in `_app_views_clowns__form_html_haml__3590088286240866241_2176114460_3896491916910336970'
# ./app/views/clowns/edit.html.haml:3:in `_app_views_clowns_edit_html_haml___574620942879655923_2176081980_599706797287605391'
# ./spec/views/clowns/edit.html.haml_spec.rb:13:in `block (2 levels) in <top (required)>'
2) clowns/new.html.haml renders new clown form
Failure/Error: render
undefined method `to_sym' for nil:NilClass
# ./app/views/clowns/_form.html.haml:4:in `block in _app_views_clowns__form_html_haml__3590088286240866241_2176114460_3896491916910336970'
# ./app/views/clowns/_form.html.haml:1:in `_app_views_clowns__form_html_haml__3590088286240866241_2176114460_3896491916910336970'
# ./app/views/clowns/new.html.haml:3:in `_app_views_clowns_new_html_haml__1085372210838170129_2159651900_599706797287605391'
# ./spec/views/clowns/new.html.haml_spec.rb:12:in `block (2 levels) in <top (required)>'
Finished in 1.03 seconds
27 examples, 2 failures, 2 pending
And here is the spec that apparently fails (edit.html.haml_spec.rb). It was auto-generated by rails g scaffold Clown name:string balloons:integer:
#spec/views/clowns/edit.html.haml_spec.rb
require 'spec_helper'
describe "clowns/edit.html.haml" do
before(:each) do
#clown = assign(:clown, stub_model(Clown,
:name => "MyString",
:balloons => 1
))
end
it "renders the edit clown form" do
render
# Run the generator again with the --webrat-matchers flag if you want to use webrat matchers
assert_select "form", :action => clown_path(#clown), :method => "post" do
assert_select "input#clown_name", :name => "clown[name]"
assert_select "input#clown_balloons", :name => "clown[balloons]"
end
end
end
Are you also using simple_form (or perhaps even formtastic)? I get the same error when I convert the scaffold forms from standards forms to simple_form forms (form_for(#user) => simple_form_for(#user)).
It still works, as you say, so I'm not sure it's worth worrying about. I think you'd be better off just letting Cucumber worry about it. Sarah Mei says view specs are a waste of time. :-)