Open MattNolf opened 5 years ago
According to the Go language spec:
Slice, map, and function values are not comparable. However, as a special case, a slice, map, or function value may be compared to the predeclared identifier nil.
I suspect this is why it doesn't work here. There might be workarounds using the reflect
package but that's not great.
As a workaround you could implement a stub Consume function (using Do function) and then check your function is called that way. Hope this helps!
@tscott0 Perhaps, but it's possible to expect & assert on slices/maps so seems strange that functions would be different.
Will take a look at Do()
as a workaround in the meantime 👍
@MattNolf I didn't know expect and assert worked for slices/maps but that's good to know. I was curious so I did some digging...
Under the hood it's using reflect.DeepEqual.
What I didn't realise is that you can't compare functions with DeepEqual. They are only equal if they are both nil. See docs here. This explains it but there still might be a solution that doesn't use DeepEqual so I think the issue should remain open. Good luck!
Thank you @MattNolf for your detailed report, that is very useful. I will look into this...
Dear all, Unfortunately, I have this issue. Do you have any updates? And is there any way to avoid this issue temporarily?
I don't think this one is fixable as comparison of functions has no guarantee at the language level in Golang.
I propose that passing a function argument to a mocked method should panic.
Instead, the correct usage should be with gomock.AssignableToTypeOf
which currently works.
There is no way to reliably compare functions so this should result in an error IMO.
@nguyenfilip @codyoss WDYT?
See following links for more details:
@cvgw I agree, this would be very hard to support. Panicing sounds like the best short term behavior change.
Hope it's ok to post a workaround; have been dealing with this for a while for variadic option functions and finally found a workable solution.
@MattNolf extending your test:
https://github.com/zachwalton/gomock-test/commit/04033d4265da8cc0d4acfb1c2307963b511916c2
You can build a custom matcher that:
(3) could be reflection, but for my purposes (building and returning a variadic options struct), it was enough to execute both functions and compare the return values.
As a workaround you could implement a stub Consume function (using Do function) and then check your function is called that way.
this worked for me.
we just need to use go.Any()
to match the function argument but do nothing and use Do()
to do what the method should have done.
I am encountering an issue mocking method calls with a functional argument. It appears that gomock is not matching the argument, and so failing with an unexpected call.
Tests are failing with the following:
With argument at index 1 being an aliased function.
I have provided an example scenario below.
And the failing test
mockConsumer.EXPECT().Consume("some-name", mockHandler)
is failing, as gomock does not match mockHandler as the provided argument.Here is the test repository