Search code examples
rspecassignment-operatorstubexpectations

Rspec expect assignment (=) method to be called


I am writing some test where I would like to assert that some method actually calls the assignment method on an object which I have stubbed.

I have tried doing this:

expect(test_object.some_object[:whatever]).to receive(:=).with(some_data) #Does NOT work

test_object.method()

This does not appear to work. Is there a way for me to do this?


The reason for doing this is that the "some_object" is an open struct object which is a stand-in for an external library which I don't want to invoke when testing.


Solution

  • There is no such thing as an "assignment method" in Ruby. When you assign a value to variable in Ruby (e.g. local variable, instance variable, class variable), you aren't calling a method. The variable is a "container" of sorts for an object and there is no way for RSpec to track whether or not an assignment to a variable takes place.

    The one exception of sorts to this rule is the case of so-called "setter" methods, as used with attr_writer and attr_accessor. In this case, you still don't have an assignment method per se, but if you define a method such as:

    class MyObject
      def my_attribute=(value)
        ...
      end
    end
    

    or use the equivalent attr_... calls, then the following code:

    MyObject.new.my_attribute = 'foo'
    

    will be treated as

    MyObject.new.my_attribute=('foo')
    

    and you can stub or set expectations on the my_attribute= method like any other method.