Uploaded image for project: 'Mongoid'
  1. Mongoid
  2. MONGOID-3629

Adding objects to an embeds_many fails when the parent has just been created in an after callback

    • Type: Icon: Bug Bug
    • Resolution: Won't Do
    • Priority: Icon: Minor - P4 Minor - P4
    • None
    • Affects Version/s: None
    • Component/s: Associations, Callbacks
    • None

      I just burned the better half of a day on this. Perhaps I'm doing something nonstandard with the after_create and the autobuild and the polymorphism, but I don't understand why four of these tests do not pass:

      require 'spec_helper'
      
      class Room
        include Mongoid::Document
        has_one :table, as: :parent, autobuild: true
        
        after_create :ensure_table
      
        def ensure_table
          table.save!
        end
      end
      
      class Table
        include Mongoid::Document
        
        belongs_to :parent, polymorphic: true
        embeds_many :chairs
      end
      
      class Chair
        include Mongoid::Document
        
        embedded_in :table
      end
      
      def do_ALL_the_tests
        it "should be valid" do
          @table.valid?.should be_true
        end
      
        it "should be persisted" do
          @table.persisted?.should be_true
        end
      
        it "should work with push" do
          4.times { @table.chairs << Chair.new }
      
          Table.count.should == 1
          Table.first.chairs.count.should == 4
        end
      
        it "should work with create!" do
          4.times { @table.chairs.create! }
      
          Table.count.should == 1
          Table.first.chairs.count.should == 4
        end
      
      end
      
      describe "A Table" do
        context "created in an after callback" do
          before :each do
            @room= Room.create!
            @table= @room.table
          end
      
          do_ALL_the_tests
        end
      
        context "created in an after callback and reloaded" do
          before :each do
            @room= Room.create!
            @table= @room.table
            @table.reload
          end
      
          do_ALL_the_tests
        end
      
        context "created in an after callback and reinstantiated with first" do
          before :each do
            @room= Room.create!
            @table= Table.first
          end
      
          do_ALL_the_tests
        end
      
        context "created in an after callback and reinstantiated with find" do
          before :each do
            @room= Room.create!
            @table= Table.find(@room.table.id)
          end
      
          do_ALL_the_tests
        end
      
        context "created directly" do
          before :each do
            @table= Table.create!
          end
      
          do_ALL_the_tests
        end
      end
      

      Despite the test block being the same in the case where the object was just created in an after_create, Chairs cannot be added to the embedded collection:

      A Table
        created directly
          should work with push
          should work with create!
          should be persisted
          should be valid
        created in an after callback and reloaded
          should work with push (FAILED - 1)
          should work with create! (FAILED - 2)
          should be persisted
          should be valid
        created in an after callback and reinstantiated with first
          should work with push
          should work with create!
          should be persisted
          should be valid
        created in an after callback and reinstantiated with find
          should work with push
          should work with create!
          should be persisted
          should be valid
        created in an after callback
          should work with push (FAILED - 3)
          should work with create! (FAILED - 4)
          should be persisted
          should be valid
      
      Failures:
      
        1) A Table created in an after callback and reloaded should work with push
           Failure/Error: Table.first.chairs.count.should == 4
             expected: 4
                  got: 0 (using ==)
           # ./spec/models/wat_spec.rb:40:in `block in do_ALL_the_tests'
      
        2) A Table created in an after callback and reloaded should work with create!
           Failure/Error: Table.first.chairs.count.should == 4
             expected: 4
                  got: 0 (using ==)
           # ./spec/models/wat_spec.rb:47:in `block in do_ALL_the_tests'
      
        3) A Table created in an after callback should work with push
           Failure/Error: Table.first.chairs.count.should == 4
             expected: 4
                  got: 0 (using ==)
           # ./spec/models/wat_spec.rb:40:in `block in do_ALL_the_tests'
      
        4) A Table created in an after callback should work with create!
           Failure/Error: Table.first.chairs.count.should == 4
             expected: 4
                  got: 0 (using ==)
           # ./spec/models/wat_spec.rb:47:in `block in do_ALL_the_tests'
      
      Finished in 4.23 seconds
      20 examples, 4 failures
      
      Failed examples:
      
      rspec ./spec/models/wat_spec.rb:36 # A Table created in an after callback and reloaded should work with push
      rspec ./spec/models/wat_spec.rb:43 # A Table created in an after callback and reloaded should work with create!
      rspec ./spec/models/wat_spec.rb:36 # A Table created in an after callback should work with push
      rspec ./spec/models/wat_spec.rb:43 # A Table created in an after callback should work with create!
      

      Here are the Mongoid gems I'm using:

      ra:app(mention) ryan$ bundle exec gem list | grep mong
      carrierwave-mongoid (0.7.0)
      mongo_session_store-rails4 (5.0.1)
      mongoid (4.0.0.beta1)
      mongoid-embedded-errors-messages (2.0.1)
      mongoid-grid_fs (1.9.2)
      

      I'm not sure where to begin to fix this. But if I can provide any more details and/if you can point me in a place to go fix this, I would be willing to submit a PR to get it fixed.

      Thanks!

            Assignee:
            neil.shweky@mongodb.com Neil Shweky (Inactive)
            Reporter:
            ryana ryana
            Votes:
            0 Vote for this issue
            Watchers:
            1 Start watching this issue

              Created:
              Updated:
              Resolved: