Fix #3 - Live Lock. Custom scopes that depend on custom scopes can sometimes create a 'Rescursive Update' problem depending on thread ordering. Fix using a CompletableFuture and atomic map operations.#16
Conversation
…es can sometimes create a 'Rescursive Update' problem depending on thread ordering. Fix using a CompletableFuture and atomic map operations.
microscoped-core/src/main/java/org/tomitribe/microscoped/core/Scope.java
Show resolved
Hide resolved
microscoped-core/src/main/java/org/tomitribe/microscoped/core/Scope.java
Outdated
Show resolved
Hide resolved
…troyed so it can no longer be used
8cfde54 to
fbb3755
Compare
|
@exabrial Hey Agent Fisher, can you create one basic test in a separate PR that replicates the issue? (i.e. it fails and shows the problem) Here are some examples of how I typically write tests for multi-threaded issues. I'd love to see that test to better understand the issue and help ensure the fix is solid. |
|
Hello David! It appears to be related to: having a bean of one custom scope, containing an injection a bean of the same custom scope, and The "Recursive Update" Exception is notated here: So my understanding of the problem is the construction of the scope invokes Given that shaky understanding, I designed this fix around Hoping that explanation makes sense and my understanding of the problem is correct. I'll try to create something that reliably reproduces the problem. |
|
Man, I cannot get this to crash outside of proprietary code. I've tried two custom scopes intermixing calls between in postConstructs. |
|
Ah ok, I figured it out. I can reproduce it reliably now. The good news is, it's not "random"... the "randomness" is likely due to the order in which tests are firing. So you have to have a circular injection (I know, yuck. I didn't realize we had one. But technically it is allowed by the CDI Spec). Our circular dependency is that the EntityManager needs a datasource, but the datasource manager needs the name of the entity manager. The datasource manager starts an in-memory db with the entity manager name as part of the url so it can be found later by the entity manager when it creates its connection pool. Anyway I have a small reproducer with a proprietary custom scope. Trying to see if I can reproduce it using one of the custom scopes in this project. |
|
I stand corrected, while I can now reproduce the issue, I can't reproduce it without the test target eventually calling a stack overflow. Our production code doesn't cause this of course, but here we are :) |
Fix #3 - Live Lock. Custom scopes that depend on custom scopes can sometimes create a 'Rescursive Update' problem depending on thread ordering. Fix using a CompletableFuture and atomic map operations.
This is a bit more of an elegant fix than whats suggested in #3