I'm creating a new Rails 3.1 application using Cucumber, Devise, and Factory_Girl. I installed successfully Devise and Cucumber. I then created the spec/factories.rb file that contains the following:
require 'factory_girl'
Factory.define :user do |user|
user.name 'Test User'
user.email 'test#email.com'
user.password' testpass'
end
I also added spec/support/devise.rb to add in the test hooks for Devise:
RSpec.configure do |config|
config.include Devise::TestHelpers, :type => :controller
end
In regards to testing, I have not touched anything else and now everytime I run any rake command I get the following (I ran rake spec in this case, just to make sure everything is ready for tests):
rake aborted!
Factory already registered: user
Tasks: TOP => spec => db:test:prepare => db:abort_if_pending_migrations => environment
(See full trace by running task with --trace)
Now if I remove the Factory.define block from the factories file, it runs fine. I've done some Google searching and have come up with absolutely nothing. Since it's saying the Factory is already registered, is Devise for whatever reason, creating a factory already?
Related
Trying to use FactoryGirl to seed my development db with some data. Following this tutorial so my seeds.rb file looks like this:
require 'factory_girl'
Dir[Rails.root.join("spec/factories/*.rb")].each {|f| require f}
100.times do
FactoryGirl.create :idea
end
When running rake db:seed it complains:
rake aborted!
Factory already registered: idea
Why is it a bad thing that the factory is registered? I'm trying to use it, not register it (whatever that means...). Any idea what I'm doing wrong?
Most likely your factories are already being loaded. Try removing the line that does each of the requires and see if that corrects the issue.
I am doing TDD/BDD in Ruby on Rails 3 with Rspec (2.11.0) and FactoryGirl (4.0.0). I have a factory for a Category model:
FactoryGirl.define "Category" do
factory :category do
name "Foo"
end
end
If I drop, create then migrate the database in the test enviroment I get this error:
rake aborted!
Could not find table 'categories'
This problem occurs because FactoryGirl expects the tables to already exist (for some odd reason). If I remove the spec folder from my rails app and do db:migrate, it works. Also if I mark factory-girl-rails from my Gemfile as :require => false it also works (then I have to comment that require in order to run rspec).
I found some information about this problem here: https://github.com/thoughtbot/factory_girl/issues/88
Is there something wrong that I'm doing? How can I "pass by" the FactoryGirl stage in the db:migration task?
I think you need to have factory girl definition like that in Gemfile:
gem 'factory_girl_rails', :require => false
And then you just require it in your spec_helper.rb like that:
require 'factory_girl_rails'
This is the way I'm always using this gem. You don't need to require it in other places than spec_helper.rb. Your current desired approach is just wrong.
A simple fix to this issue is to delay evaluation of any models in your factories by wrapping them in blocks. So, instead of this:
factory :cake do
name "Delicious Cake"
frosting Frosting.new(:flavor => 'chocolate')
filling Filling.new(:flavor => 'red velvet')
end
Do this (notice the curly braces):
factory :cake do
name "Delicious Cake in a box"
frosting { Frosting.new(:flavor => 'chocolate') }
filling { Filling.new(:flavor => 'red velvet') }
end
If you have a lot of factories this may not be feasible, but it is rather straightforward. See also here.
Information from: http://guides.rubyonrails.org/testing.html
When you do end up destroying your testing database (and it will happen, trust me),
you can rebuild it from scratch according to the specs defined in the development
database. You can do this by running rake db:test:prepare.
The rake db:migrate above runs any pending migrations on the development environment
and updates db/schema.rb. The rake db:test:load recreates the test database from the
current db/schema.rb. On subsequent attempts, it is a good idea to first run db:test:prepare, as it first checks for pending migrations and warns you appropriately.
rake db:test:clone Recreate the test database from the current environment’s database schema
rake db:test:clone_structure Recreate the test database from the development structure
rake db:test:load Recreate the test database from the current schema.rb
rake db:test:prepare Check for pending migrations and load the test schema
rake db:test:purge Empty the test database.
You shouldn't need to do any of that.. I think the issue is that your argument to FactoryGirl.define..
try this.
FactoryGirl.define do
factory :category do
name "Foo"
end
end
That should work fine, and does not screw up my migrations or load.. Today, I had to fix an issue where I was referencing a model constant from my factory directly and had to put it in a block to fix things.
FactoryGirl.define do
factory :category do
# this causes unknown table isseus
# state Category::Active
# this does not.
state { Category::Active }
end
end
I'm trying to use Factory Girl in a rake task like this:
require 'factory_girl'
require File.expand_path("spec/factories.rb")
namespace :users do
desc "Create sample users for use in development"
task :create_sample_users => :environment do
Factory(:user, :email => "pending#acme.com")
Factory(:approved_user, :email => "user#acme.com")
end
end
However when I run rake users:create_sample_users I get the error uninitialized constant Entry (Entry is the name of one of my app's classes).
Can anyone tell me how to get Factory girl to see my classes? It's working fine in my tests, just failing in my rake tasks.
I'm guessing that Rails hasn't loaded your models at the point you are requiring the factories. Try this:
require 'factory_girl'
namespace :users do
desc "Create sample users for use in development"
task :create_sample_users => :environment do
require File.expand_path("spec/factories.rb")
Factory(:user, :email => "pending#acme.com")
Factory(:approved_user, :email => "user#acme.com")
end
end
For factory_bot which has replaced factory_girl use:
require 'factory_bot'
namespace :users do
desc "Create sample users for use in development"
task :create_sample_users => :environment do
include FactoryBot::Syntax::Methods
create(:user, :email => "pending#acme.com")
end
end
#dmcnally's answer didn't work for me, as I was getting odd errors of constants not found. Instead, I resolved it by shelling out to rails runner:
sh "rails runner 'FactoryGirl.create :user'"
I'm learning how to do integration testin on my rails app. I started with cucumber but then learned since I'm just testing a models method that I should be using RSPEC. So now I'm trying to get RSPEC installed.
When I run autotest, it is only looking at the /features directory not the /spec directory.
Here's what I've done so far:
.autotest
require 'autotest/growl'
require 'autotest/fsevent'
Autotest.add_hook(:initialize) {|at|
at.add_exception %r{^\.git} # ignore Version Control System
at.add_exception %r{^./tmp} # ignore temp files, lest autotest will run again, and again...
# at.clear_mappings # take out the default (test/test*rb)
at.add_mapping(%r{^lib/.*\.rb$}) {|f, _|
Dir['spec/**/*.rb']
}
nil
}
/spec - created directory
/spec/spec_helper.rb - created
/spec/lib/mailingjob_spec.rb - created, tried to write a case that would fail as follows:
require 'spec_helper'
describe User do
before(:each) do
#valid_attributes = {
:login => "akm",
:email => "akm2000#gmail.com",
:password => "D1ff1cultPa55w0rd",
:password_confirmation => "D1ff1cultPa55w0rd"
}
end
it "should create a new instance given valid attributes" do
User.create!(#valid_attributesXXXX)
end
end
But when I run autotest this rpsec is never run only the features dir with cucumber is running. Ideas? thanks
Try:
rspec --configure autotest
From the autotest README:
[RSpec] if you want to use require
'spec_helper' -> rspec --configure
autotest
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)