-
-
Notifications
You must be signed in to change notification settings - Fork 158
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Stubs on instances of DelegateClass do not behave as expected #621
Comments
@philipchan-shopify Hi. Sorry - I don't have a lot of time to look at this right now, but I suspect it's somewhat related to #30 and/or #589. I don't know if any of the comments on those issues give you any ideas how to work around the problem...? |
I'm adding this because it took me a while to find it! |
I read through the linked issues, and I'm not sure the workaround will work in my situation - I'm trying to mock an object from a 3rd party gem and am unable to change their implementation to a different delegation strategy |
So just to double-check, it's the 3rd party gem that's using |
I had a few minutes to look at this and I've got a bit further. I think that at least part of the problem is that the anonymous class constructed by calling However, things are further complicated because it looks like calling https://github.com/ruby/ruby/blob/909afcb4fca393ce75cc63edc7656fd95a64f0f9/lib/delegate.rb#L417-L419 I think the latter explains why calling Some illustrative output: class A; end
AA = DelegateClass(A)
class B < AA; end
p Object.ancestors # => [Object, Mocha::ObjectMethods, Mocha::Inspect::ObjectMethods, Mocha::ParameterMatchers::InstanceMethods, Minitest::Expectations, Kernel, BasicObject]
p A.ancestors # => [A, Object, Mocha::ObjectMethods, Mocha::Inspect::ObjectMethods, Mocha::ParameterMatchers::InstanceMethods, Minitest::Expectations, Kernel, BasicObject]
p AA.ancestors # => [AA, Delegator, #<Module:0x00000001041df1f0>, BasicObject]
p B.ancestors # => [B, AA, Delegator, #<Module:0x00000001041df1f0>, BasicObject]
b = B.new(A.new)
p b.method(:stubs).owner # => AA |
I have a possible solution, although it reaches into the innards of require "mocha/object_methods"
Delegator.instance_variable_set(:@delegator_api, Delegator.public_api + Mocha::ObjectMethods.instance_methods)
BasicObject.send(:include, Mocha::ObjectMethods) This does two things:
It's worth noting that this permanently includes Can you give that a try and see whether it works in your use case? |
@philipchan-shopify Having spent a bunch of time investigating this, I'd really appreciate some feedback on my suggested solution - thanks in anticipation! |
Since I've heard nothing to the contrary, I'm going to close this. |
See also #622. |
If stubbing a method on a class whose parent class is a DelegateClass, the stub doesn't seem to be called:
Am I setting up the stub on the instance of B incorrectly?
The text was updated successfully, but these errors were encountered: