Read more

ActiveType::Object: Be careful when overriding the initialize method

Jakob Scholz
October 18, 2022Software engineer at makandra GmbH

Background:

ActiveType::Object inherits from ActiveRecod::Base and is designed to behave like an ActiveRecord Object, just without the database persistence.

Don't remove any of the default behavior of the initialize method!

Illustration online protection

Rails Long Term Support

Rails LTS provides security patches for old versions of Ruby on Rails (2.3, 3.2, 4.2 and 5.2)

  • Prevents you from data breaches and liability risks
  • Upgrade at your own pace
  • Works with modern Rubies
Read more Show archive.org snapshot

If you have a class which inherits from ActiveType::Object and you need to override the #initialize method, then you should be really careful:

  • Always pass exactly one attribute. ActiveRecod::Base objects really want to get their arguments processable as keyword arguments. Don't change the syntax, or you'll experience pain.
  • Always call super inside of your overridden #initialize method. A lot of magic things happen in the ActiveRecord world. Just let them happen, otherwise kittens will die somewhere. You don't want that.

Example

class Item < ActiveType::Object

  def initialize(attributes)
    super
  
    # Now, as the ActiveRecod::Base part could do it's duty, I can freely do whatever I want.
  end

end

Example pitfall

  • If you don't run the super method inside #initialize, the object is marked as frozen. Rspec mocks (e.g. using partial doubles Show archive.org snapshot with receive(partial_double).to ...) in tests would raise the following error (just imagine how hard debugging can be):
ArgumentError:
       Cannot proxy frozen objects, rspec-mocks relies on proxies for method stubbing and expectations.
  • If you define initialize with no argument and don't call super, initialize might be hit with this error:
ArgumentError: 
       Wrong number of arguments (given 1, expected 0)

Further readings

Posted by Jakob Scholz to makandra dev (2022-10-18 15:29)