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

Mongoid::Timestamps shouldn't update deleted documents (FrozenError)

    • Type: Icon: Bug Bug
    • Resolution: Fixed
    • Priority: Icon: Unknown Unknown
    • 9.1.0, 8.0.9, 8.1.9, 9.0.5
    • Affects Version/s: 7.5.4, 8.1.6, 9.0.2
    • Component/s: None
    • None
    • None
    • Ruby Drivers
    • Not Needed
    • Hide

      1. What would you like to communicate to the user about this feature?
      2. Would you like the user to see examples of the syntax and/or executable code and its output?
      3. Which versions of the driver/connector does this apply to?

      Show
      1. What would you like to communicate to the user about this feature? 2. Would you like the user to see examples of the syntax and/or executable code and its output? 3. Which versions of the driver/connector does this apply to?
    • None
    • None
    • None
    • None
    • None
    • None

      Here's a script demonstrating the bug:

      require 'bundler/inline'
      
      gemfile do
        source "https://rubygems.org"
        gem "mongoid"
        gem "ostruct" # get rid of warnings in newer Rubies
      end
      
      Mongoid.configure do |config|
        config.clients.default = {
          hosts: ['localhost:27017'],
          database: 'mongoid_test',
        }
      end
      
      class Article
        include Mongoid::Document
      
        embeds_many :authors
      end
      
      class Author
        include Mongoid::Document
        include Mongoid::Timestamps unless ENV["SKIP_TIMESTAMP"]
      
        field :name, type: String
        embedded_in :article
      
        before_save :destroy_if_rodrigo
      
        def destroy_if_rodrigo
          destroy if name == "Rodrigo"
        end
      end
      
      article = Article.create
      article.authors << Author.new(name: "Rodrigo")
      article.save
      

      Run it without including Mongoid::Timestamps:

      > SKIP_TIMESTAMP=1 ruby mongoid-frozen-attributes-bug.rb

      Now try with Mongoid::Timestamps:

      > ruby mongoid-frozen-attributes-bug.rb

      ruby mongoid-frozen-attributes-bug.rb 
      /Users/rodrigo.rosas/.rbenv/versions/3.3.5/lib/ruby/gems/3.3.0/gems/mongoid-9.0.2/lib/mongoid/attributes.rb:191:in `block in write_attribute': can't modify frozen Hash: {"_id"=>BSON::ObjectId('6727ceff9b99b276f43be4ec'), "name"=>"Rodrigo"} (FrozenError)
      	from /Users/rodrigo.rosas/.rbenv/versions/3.3.5/lib/ruby/gems/3.3.0/gems/mongoid-9.0.2/lib/mongoid/threaded/lifecycle.rb:31:in `_assigning'
      	from /Users/rodrigo.rosas/.rbenv/versions/3.3.5/lib/ruby/gems/3.3.0/gems/mongoid-9.0.2/lib/mongoid/attributes.rb:174:in `write_attribute'
      	from /Users/rodrigo.rosas/.rbenv/versions/3.3.5/lib/ruby/gems/3.3.0/gems/mongoid-9.0.2/lib/mongoid/fields.rb:696:in `block (2 levels) in create_field_setter'
      	from /Users/rodrigo.rosas/.rbenv/versions/3.3.5/lib/ruby/gems/3.3.0/gems/mongoid-9.0.2/lib/mongoid/timestamps/created.rb:28:in `set_created_at'
      	from /Users/rodrigo.rosas/.rbenv/versions/3.3.5/lib/ruby/gems/3.3.0/gems/activesupport-7.2.2/lib/active_support/callbacks.rb:362:in `block in make_lambda'
      	from /Users/rodrigo.rosas/.rbenv/versions/3.3.5/lib/ruby/gems/3.3.0/gems/activesupport-7.2.2/lib/active_support/callbacks.rb:179:in `block in call'
      	from /Users/rodrigo.rosas/.rbenv/versions/3.3.5/lib/ruby/gems/3.3.0/gems/activesupport-7.2.2/lib/active_support/callbacks.rb:668:in `block (2 levels) in default_terminator'
      	from /Users/rodrigo.rosas/.rbenv/versions/3.3.5/lib/ruby/gems/3.3.0/gems/activesupport-7.2.2/lib/active_support/callbacks.rb:667:in `catch'
      	from /Users/rodrigo.rosas/.rbenv/versions/3.3.5/lib/ruby/gems/3.3.0/gems/activesupport-7.2.2/lib/active_support/callbacks.rb:667:in `block in default_terminator'
      	from /Users/rodrigo.rosas/.rbenv/versions/3.3.5/lib/ruby/gems/3.3.0/gems/activesupport-7.2.2/lib/active_support/callbacks.rb:180:in `call'
      	from /Users/rodrigo.rosas/.rbenv/versions/3.3.5/lib/ruby/gems/3.3.0/gems/activesupport-7.2.2/lib/active_support/callbacks.rb:559:in `block in invoke_before'
      	from /Users/rodrigo.rosas/.rbenv/versions/3.3.5/lib/ruby/gems/3.3.0/gems/activesupport-7.2.2/lib/active_support/callbacks.rb:559:in `each'
      	from /Users/rodrigo.rosas/.rbenv/versions/3.3.5/lib/ruby/gems/3.3.0/gems/activesupport-7.2.2/lib/active_support/callbacks.rb:559:in `invoke_before'
      	from /Users/rodrigo.rosas/.rbenv/versions/3.3.5/lib/ruby/gems/3.3.0/gems/activesupport-7.2.2/lib/active_support/callbacks.rb:109:in `run_callbacks'
      	from /Users/rodrigo.rosas/.rbenv/versions/3.3.5/lib/ruby/gems/3.3.0/gems/mongoid-9.0.2/lib/mongoid/interceptable.rb:139:in `run_callbacks'
      	from /Users/rodrigo.rosas/.rbenv/versions/3.3.5/lib/ruby/gems/3.3.0/gems/mongoid-9.0.2/lib/mongoid/persistable/creatable.rb:111:in `block (2 levels) in prepare_insert'
      	from /Users/rodrigo.rosas/.rbenv/versions/3.3.5/lib/ruby/gems/3.3.0/gems/activesupport-7.2.2/lib/active_support/callbacks.rb:110:in `run_callbacks'
      	from /Users/rodrigo.rosas/.rbenv/versions/3.3.5/lib/ruby/gems/3.3.0/gems/mongoid-9.0.2/lib/mongoid/interceptable.rb:139:in `run_callbacks'
      	from /Users/rodrigo.rosas/.rbenv/versions/3.3.5/lib/ruby/gems/3.3.0/gems/mongoid-9.0.2/lib/mongoid/persistable/creatable.rb:110:in `block in prepare_insert'
      	from /Users/rodrigo.rosas/.rbenv/versions/3.3.5/lib/ruby/gems/3.3.0/gems/activesupport-7.2.2/lib/active_support/callbacks.rb:101:in `run_callbacks'
      	from /Users/rodrigo.rosas/.rbenv/versions/3.3.5/lib/ruby/gems/3.3.0/gems/mongoid-9.0.2/lib/mongoid/interceptable.rb:139:in `run_callbacks'
      	from /Users/rodrigo.rosas/.rbenv/versions/3.3.5/lib/ruby/gems/3.3.0/gems/mongoid-9.0.2/lib/mongoid/persistable/creatable.rb:109:in `prepare_insert'
      	from /Users/rodrigo.rosas/.rbenv/versions/3.3.5/lib/ruby/gems/3.3.0/gems/mongoid-9.0.2/lib/mongoid/persistable/creatable.rb:21:in `insert'
      	from /Users/rodrigo.rosas/.rbenv/versions/3.3.5/lib/ruby/gems/3.3.0/gems/mongoid-9.0.2/lib/mongoid/persistable/savable.rb:27:in `save'
      	from /Users/rodrigo.rosas/.rbenv/versions/3.3.5/lib/ruby/gems/3.3.0/gems/mongoid-9.0.2/lib/mongoid/association/embedded/embeds_many/proxy.rb:96:in `block in <<'
      	from <internal:kernel>:90:in `tap'
      	from /Users/rodrigo.rosas/.rbenv/versions/3.3.5/lib/ruby/gems/3.3.0/gems/mongoid-9.0.2/lib/mongoid/association/embedded/embeds_many/proxy.rb:94:in `<<'
      	from mongoid-frozen-attributes-bug.rb:37:in `<main>'
      

      By the way, `ostruct` should be added as a dependency.

            Assignee:
            dmitry.rybakov@mongodb.com Dmitry Rybakov
            Reporter:
            rosenfeld Rodrigo Rosenfeld Rosas
            Votes:
            0 Vote for this issue
            Watchers:
            3 Start watching this issue

              Created:
              Updated:
              Resolved:
              None
              None
              None
              None