Monkey patch method on one object

I would like to override the behavior of the update_attributes method for an instance of a single model class. Assuming the variable is called @alert , what is the best way to do this? To be clear, I do not want to change the behavior of this method for the entire class.


DENIAL OF RESPONSIBILITY:

I need to do this to make the method return false when I want it so that I can write unit tests for the following error handling code. I understand that this is not the best practice.

+6
source share
2 answers

Just define a method for the object:

 class Thing def greeting 'yo, man' end end Thing.instance_methods(false) #=> [:greeting] object = Thing.new #=> #<Thing:0x007fc4ba276c90> object.greeting #=> "yo, man" 

Define two methods in object (which will be instances of the method in the object singleton class.

 def object.greeting 'hey, dude' end def object.farewell 'see ya' end object.methods(false) #=> [:greeting, :farewell] object.singleton_class.instance_methods(false) #=> [:greeting, :farewell] object.greeting #=> "hey, dude" object.farewell #=> "see ya" new_obj = Thing.new new_obj.greeting #=> "yo, man" new_obj.farewell #NoMethodError: undefined method `farewell' for #<Thing:0x007fe5a406f590> 

Remove the object singleton greeting method.

 object.singleton_class.send(:remove_method, :greeting) object.methods(false) #=> [:farewell] object.greeting #=> "yo, man" 

Another way to remove :greeting from the object singleton class is as follows.

 class << object remove_method(:greeting) end 
+7
source

After creating the object, call "define_method" in it:

 object = Thing.new object.define_method("update_attributes") { return false } 

To do object.update_attributes , now false

+2
source

Source: https://habr.com/ru/post/988533/


All Articles