-
Notifications
You must be signed in to change notification settings - Fork 59
withObjectMocked is not threadsafe #311
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
Comments
Interesting, according to the java docs of the feature it relies on it should be thread safe if used properly
I wonder if there is anything wrong in my impl... |
@bbonanno thank you for your response. I think there is an issue with the following piece of code in the current implementation:
The piece of doc you referenced describes a usage of a special case of mocking
|
Ohh yes, you're right. So yes, is non thread-safe as it stands now, I'll try to see if I can make it so, but will probably have to involve a lock on that class or something (which will prevent tests that use that object to run in parallel, but unless your whole system is calling the same object it should be fine I think). Gonna sketch something out and see if I can push it today |
@aleksey-suprun please check the PR associated to this issue, the solution is a bit nuclear, but I don't think there's a way around it as we can't control how the compiler links the access to the singleton instance |
Hi @bbonanno. I checked your solution. Actually, my first attempt to work the problem around was exactly the same. But it does not solve the main issue. The problem is not connected with a parallel mocking. The problem pops up when a number of tests interact with the same scala object (singleton) in parallel. Due to the fact that scala object is a singleton, we are getting mocked instance even in tests which are not going to mock the object but run in parallel in a separate thread. That causes some unverified calls in mocked tests and smart nulls exceptions in non-mocked tests during the execution. For example, we have a couple of test classes: class FooSpec extends AnyFunSpec with MockitoSugar {
it ("should use mock") {
withObjectMocked[FooObject.type] {
when(FooObject.simpleMethod).thenReturn(1)
FooObject.simpleMethod
verify(FooObject).simpleMethod
}
}
}
class BarSpec extends AnyFunSpec with MockitoSugar {
it ("should not use mock") {
FooObject.simpleMethod should not be (null)
}
} There is a high probability to get both of them failed when they run simultaneously in separate threads. |
ohh I see, mixed concurrency would definitively be a problem... |
Thank you. Today I tried to find something which can help but still don't have any solution. |
@aleksey-suprun please have a look again, I think I got it right this time :) |
booo, it worked in my machine 😅 |
OK, this time I got a green build :P Please let me know your thoughts @aleksey-suprun |
@bbonanno that looks great! 👍 Looking forward to the release 😉 |
Protect against concurrent non-mocked access to the a mocked object (Fix #311)
Hi! It seems
withObjectMocked
may cause unexpected failures when tests are executing in parallel. According to implementation, it uses reflection to set an internal state of a singleton which may lead to unexpected behavior when another test runs in a different thread and tries to interact with that scala object.This can lead to the following exceptions:
or
or
Any help or workaround will be appreciated! Thanks in advance.
The text was updated successfully, but these errors were encountered: