-
-
Notifications
You must be signed in to change notification settings - Fork 1.5k
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
Document concurrency considerations for TestExecutionListener
implementations
#2539
Comments
Good point, we should document that. |
@marcphilipp, thank you. That answer helps me decide how to go about one of the implementations in Apache Ant. |
to avoid races like ``` Aug 06, 2021 1:23:55 PM org.junit.platform.launcher.core.TestExecutionListenerRegistry lambda$notifyEach$1 WARNING: TestExecutionListener [cz.xtf.junit5.listeners.TestExecutionLogger] threw exception for method: executionFinished(TestIdentifier [uniqueId = '[engine:junit-jupiter]/[class:com.redhat.xpaas.eap.microprofile.health.MPHealthUpTest]/[method:healthCheckUpTest()]', parentId = '[engine:junit-jupiter]/[class:com.redhat.xpaas.eap.microprofile.health.MPHealthUpTest]', displayName = 'healthCheckUpTest()', legacyReportingName = 'healthCheckUpTest()', source = MethodSource [className = 'com.redhat.xpaas.eap.microprofile.health.MPHealthUpTest', methodName = 'healthCheckUpTest', methodParameterTypes = ''], tags = [level2, openshift-api], type = TEST], TestExecutionResult [status = SUCCESSFUL, throwable = null]) java.lang.NullPointerException at cz.xtf.junit5.listeners.TestExecutionLogger.executionFinished(TestExecutionLogger.java:39) at org.junit.platform.launcher.core.TestExecutionListenerRegistry$CompositeTestExecutionListener.lambda$executionFinished$10(TestExecutionListenerRegistry.java:109) at org.junit.platform.launcher.core.TestExecutionListenerRegistry.lambda$notifyEach$1(TestExecutionListenerRegistry.java:67) at java.util.ArrayList.forEach(ArrayList.java:1257) at org.junit.platform.launcher.core.TestExecutionListenerRegistry.notifyEach(TestExecutionListenerRegistry.java:65) at org.junit.platform.launcher.core.TestExecutionListenerRegistry.access$200(TestExecutionListenerRegistry.java:32) at org.junit.platform.launcher.core.TestExecutionListenerRegistry$CompositeTestExecutionListener.executionFinished(TestExecutionListenerRegistry.java:108) at org.junit.platform.launcher.core.ExecutionListenerAdapter.executionFinished(ExecutionListenerAdapter.java:56) at org.junit.platform.launcher.core.DelegatingEngineExecutionListener.executionFinished(DelegatingEngineExecutionListener.java:46) at org.junit.platform.launcher.core.OutcomeDelayingEngineExecutionListener.executionFinished(OutcomeDelayingEngineExecutionListener.java:63) at org.junit.platform.engine.support.hierarchical.NodeTestTask.reportCompletion(NodeTestTask.java:183) at org.junit.platform.engine.support.hierarchical.NodeTestTask.execute(NodeTestTask.java:89) at org.junit.platform.engine.support.hierarchical.ForkJoinPoolHierarchicalTestExecutorService$ExclusiveTask.compute(ForkJoinPoolHierarchicalTestExecutorService.java:185) at java.util.concurrent.RecursiveAction.exec(RecursiveAction.java:189) at java.util.concurrent.ForkJoinTask.doExec(ForkJoinTask.java:289) at java.util.concurrent.ForkJoinPool$WorkQueue.runTask(ForkJoinPool.java:1056) at java.util.concurrent.ForkJoinPool.runWorker(ForkJoinPool.java:1692) at java.util.concurrent.ForkJoinWorkerThread.run(ForkJoinWorkerThread.java:157) ``` According to junit-team/junit5#2539 (comment), only `testPlanExecutionStarted` and `testPlanExecutionFinished` are always called from the same thread. All other method could be called from different threads concurrently in case one or multiple test engines execute tests in parallel.
to avoid races like ``` Aug 06, 2021 1:23:55 PM org.junit.platform.launcher.core.TestExecutionListenerRegistry lambda$notifyEach$1 WARNING: TestExecutionListener [cz.xtf.junit5.listeners.TestExecutionLogger] threw exception for method: executionFinished(TestIdentifier [uniqueId = '[engine:junit-jupiter]/[class:com.redhat.xpaas.eap.microprofile.health.MPHealthUpTest]/[method:healthCheckUpTest()]', parentId = '[engine:junit-jupiter]/[class:com.redhat.xpaas.eap.microprofile.health.MPHealthUpTest]', displayName = 'healthCheckUpTest()', legacyReportingName = 'healthCheckUpTest()', source = MethodSource [className = 'com.redhat.xpaas.eap.microprofile.health.MPHealthUpTest', methodName = 'healthCheckUpTest', methodParameterTypes = ''], tags = [level2, openshift-api], type = TEST], TestExecutionResult [status = SUCCESSFUL, throwable = null]) java.lang.NullPointerException at cz.xtf.junit5.listeners.TestExecutionLogger.executionFinished(TestExecutionLogger.java:39) at org.junit.platform.launcher.core.TestExecutionListenerRegistry$CompositeTestExecutionListener.lambda$executionFinished$10(TestExecutionListenerRegistry.java:109) at org.junit.platform.launcher.core.TestExecutionListenerRegistry.lambda$notifyEach$1(TestExecutionListenerRegistry.java:67) at java.util.ArrayList.forEach(ArrayList.java:1257) at org.junit.platform.launcher.core.TestExecutionListenerRegistry.notifyEach(TestExecutionListenerRegistry.java:65) at org.junit.platform.launcher.core.TestExecutionListenerRegistry.access$200(TestExecutionListenerRegistry.java:32) at org.junit.platform.launcher.core.TestExecutionListenerRegistry$CompositeTestExecutionListener.executionFinished(TestExecutionListenerRegistry.java:108) at org.junit.platform.launcher.core.ExecutionListenerAdapter.executionFinished(ExecutionListenerAdapter.java:56) at org.junit.platform.launcher.core.DelegatingEngineExecutionListener.executionFinished(DelegatingEngineExecutionListener.java:46) at org.junit.platform.launcher.core.OutcomeDelayingEngineExecutionListener.executionFinished(OutcomeDelayingEngineExecutionListener.java:63) at org.junit.platform.engine.support.hierarchical.NodeTestTask.reportCompletion(NodeTestTask.java:183) at org.junit.platform.engine.support.hierarchical.NodeTestTask.execute(NodeTestTask.java:89) at org.junit.platform.engine.support.hierarchical.ForkJoinPoolHierarchicalTestExecutorService$ExclusiveTask.compute(ForkJoinPoolHierarchicalTestExecutorService.java:185) at java.util.concurrent.RecursiveAction.exec(RecursiveAction.java:189) at java.util.concurrent.ForkJoinTask.doExec(ForkJoinTask.java:289) at java.util.concurrent.ForkJoinPool$WorkQueue.runTask(ForkJoinPool.java:1056) at java.util.concurrent.ForkJoinPool.runWorker(ForkJoinPool.java:1692) at java.util.concurrent.ForkJoinWorkerThread.run(ForkJoinWorkerThread.java:157) ``` According to junit-team/junit5#2539 (comment), only `testPlanExecutionStarted` and `testPlanExecutionFinished` are always called from the same thread. All other method could be called from different threads concurrently in case one or multiple test engines execute tests in parallel.
This issue has been automatically marked as stale because it has not had recent activity. Given the limited bandwidth of the team, it will be automatically closed if no further activity occurs. Thank you for your contribution. |
This issue has been automatically closed due to inactivity. If you have a good use case for this feature, please feel free to reopen the issue. |
The proposed documentation change sounds useful to me, so I wonder if this issue should be re-opened? |
I'd like to give this one a try. :) |
Add a note about concurrency considerations for `TestExecutionListener` implementations to this interface's Javadoc. Issue: junit-team#2539 Co-authored-by: Marc Philipp <mail@marcphilipp.de>
Add a note about concurrency considerations for `TestExecutionListener` implementations to this interface's Javadoc. Issue: #2539 Co-authored-by: Marc Philipp <mail@marcphilipp.de>
Add a note about concurrency considerations for `TestExecutionListener` implementations to this interface's Javadoc. Issue: #2539 Co-authored-by: Marc Philipp <mail@marcphilipp.de>
TestExecutionListener
implementations
I've been looking at some documentations to see if there is any thread safety semantics to consider when implementing a
org.junit.platform.launcher.TestExecutionListener
. I haven't found any, so asking here.More specifically, is there ever a case where the same instance of
TestExecutionListener
could get invoked by multiple threads (simultaneously), such that these implementations need to handle any thread safety issues? If so, is it only for certain methods or do all methods on that interface's implementation need to take into account this aspect? For example, in theory, I wouldn't expect more than one thread invoking thetestPlanExecutionFinished
method.The text was updated successfully, but these errors were encountered: