Skip to content

Commit

Permalink
Factory overrides are applied before other attributes. Fixes #140.
Browse files Browse the repository at this point in the history
  • Loading branch information
metaskills authored and joshuaclayton committed Aug 8, 2011
1 parent ec88698 commit 4b83b1e
Show file tree
Hide file tree
Showing 5 changed files with 76 additions and 3 deletions.
1 change: 1 addition & 0 deletions Gemfile
Expand Up @@ -4,6 +4,7 @@ gem "rake"
gem "rspec", "~> 2.0"
gem "rcov"
gem "activerecord", :require => false
gem "activesupport", :require => false
gem "rr"
gem "sqlite3-ruby", :require => false
gem "appraisal", "~> 0.3.5"
Expand Down
1 change: 1 addition & 0 deletions Gemfile.lock
Expand Up @@ -58,6 +58,7 @@ PLATFORMS

DEPENDENCIES
activerecord
activesupport
appraisal (~> 0.3.5)
bluecloth
cucumber (~> 1.0.0)
Expand Down
4 changes: 4 additions & 0 deletions lib/factory_girl/attribute.rb
Expand Up @@ -34,6 +34,10 @@ def priority
1
end

def aliases_for?(attr)
FactoryGirl.aliases_for(attr).include?(name)
end

def <=>(another)
return nil unless another.is_a? Attribute
self.priority <=> another.priority
Expand Down
8 changes: 5 additions & 3 deletions lib/factory_girl/factory.rb
Expand Up @@ -76,13 +76,15 @@ def add_callback(name, &block)
def run(proxy_class, overrides) #:nodoc:
proxy = proxy_class.new(build_class)
overrides = symbolize_keys(overrides)
overrides.each {|attr, val| proxy.set(attr, val) }
passed_keys = overrides.keys.collect {|k| FactoryGirl.aliases_for(k) }.flatten
@attributes.each do |attribute|
unless passed_keys.include?(attribute.name)
factory_overrides = overrides.select { |attr, val| attribute.aliases_for?(attr) }
if factory_overrides.empty?
attribute.add_to(proxy)
else
factory_overrides.each { |attr, val| proxy.set(attr, val) }
end
end
overrides.each { |attr, val| proxy.set(attr, val) }
proxy.result(@to_create_block)
end

Expand Down
65 changes: 65 additions & 0 deletions spec/acceptance/overrides_spec.rb
@@ -0,0 +1,65 @@
require 'spec_helper'
require 'acceptance/acceptance_helper'
require 'active_support/ordered_hash'

describe "attribute overrides" do
before do
define_model('User', :admin => :boolean)
define_model('Post', :title => :string,
:secure => :boolean,
:user_id => :integer) do
belongs_to :user

def secure=(value)
return unless user && user.admin?
write_attribute(:secure, value)
end
end

FactoryGirl.define do
factory :user do
factory :admin do
admin true
end
end

factory :post do
user
title "default title"
end
end
end

let(:admin) { FactoryGirl.create(:admin) }

let(:post_attributes) do
attributes = ActiveSupport::OrderedHash.new
attributes[:secure] = false
attributes
end

let(:non_admin_post_attributes) do
post_attributes[:user] = FactoryGirl.create(:user)
post_attributes
end

let(:admin_post_attributes) do
post_attributes[:user] = admin
post_attributes
end

context "with an admin posting" do
subject { FactoryGirl.create(:post, admin_post_attributes) }
its(:secure) { should == false }
end

context "with a non-admin posting" do
subject { FactoryGirl.create(:post, non_admin_post_attributes) }
its(:secure) { should be_nil }
end

context "with no user posting" do
subject { FactoryGirl.create(:post, post_attributes) }
its(:secure) { should be_nil }
end
end

0 comments on commit 4b83b1e

Please sign in to comment.