Skip to content

Commit

Permalink
Fixed an issue using the association_name= method to assign a new obj…
Browse files Browse the repository at this point in the history
…ect updated existing pointers to the proxy, rather than generating a new one
  • Loading branch information
jaronkk committed Jan 4, 2011
1 parent b49beae commit f42d360
Show file tree
Hide file tree
Showing 3 changed files with 66 additions and 9 deletions.
33 changes: 25 additions & 8 deletions lib/mongo_mapper/plugins/associations.rb
Original file line number Diff line number Diff line change
Expand Up @@ -33,17 +33,23 @@ def create_association(type, name, options, &extension)
association = Associations::Base.new(type, name, options, &extension)
associations[association.name] = association

define_method("#{association.name}=") do |value|
get_proxy(association).replace(value)
value
end

if association.one? || association.belongs_to?
define_method(association.name) do
proxy = get_proxy(association)
proxy.nil? ? nil : proxy
end

define_method("#{association.name}=") do |value|
proxy = get_proxy(association)

if (proxy.nil? || proxy.target != value)
proxy = build_proxy(association)
end

proxy.replace(value)
value
end

define_method("#{association.name}?") do
get_proxy(association).present?
end
Expand All @@ -66,6 +72,11 @@ def create_association(type, name, options, &extension)
get_proxy(association)
end

define_method("#{association.name}=") do |value|
get_proxy(association).replace(value)
value
end

end

if association.options[:dependent] && association.many? && !association.embeddable?
Expand Down Expand Up @@ -95,11 +106,17 @@ def embedded_associations
association
end
end


def build_proxy(association)
proxy = association.proxy_class.new(self, association)
self.instance_variable_set(association.ivar, proxy)

proxy
end

def get_proxy(association)
unless proxy = self.instance_variable_get(association.ivar)
proxy = association.proxy_class.new(self, association)
self.instance_variable_set(association.ivar, proxy)
proxy = build_proxy(association)
end
proxy
end
Expand Down
20 changes: 20 additions & 0 deletions test/functional/associations/test_belongs_to_proxy.rb
Original file line number Diff line number Diff line change
Expand Up @@ -36,7 +36,27 @@ def setup
comment.post.should == post
comment.post.nil?.should be_false
end

should "generate a new proxy when replacing the association" do
post1 = @post_class.create(:name => 'post1')
post2 = @post_class.create(:name => 'post2')

comment = @comment_class.new(:name => 'Foo!', :post => post1)
comment.save.should be_true


comment = comment.reload
comment.post.should == post1
comment.post.nil?.should be_false

original_post = comment.post
original_post.name.should == 'post1'

comment.post = post2
comment.post.name.should == 'post2'
original_post.name.should == 'post1'
end

should "unset the association" do
post = @post_class.new(:name => 'mongomapper')
comment = @comment_class.new(:name => 'Foo!', :post => post)
Expand Down
22 changes: 21 additions & 1 deletion test/functional/associations/test_one_proxy.rb
Original file line number Diff line number Diff line change
Expand Up @@ -47,8 +47,28 @@ def setup
post.author = new_author
post.author.should == new_author
end
end

should "generate a new proxy instead of modifying the existing one" do
@post_class.one :author, :class => @author_class

post = @post_class.new
author = @author_class.new(:name => 'Frank')
post.author = author
post.reload

post.author.should == author
post.author.nil?.should be_false

original_author = post.author
original_author.name.should == 'Frank'
new_author = @author_class.new(:name => 'Emily')
post.author = new_author
post.author.should == new_author

original_author.name.should == 'Frank'
end
end

context "with a Hash" do
should "convert to an object of the class and work" do
@post_class.one :author, :class => @author_class
Expand Down

0 comments on commit f42d360

Please sign in to comment.