Skip to content
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

Enable launch of jmxfetch app's executors as daemon, default to NO-daemon #237

Merged
merged 4 commits into from
Jul 8, 2019

Conversation

labbati
Copy link
Member

@labbati labbati commented Jul 3, 2019

When embedding the jmxfetch app in dd-trce-java we noticed that even if
we run it in a thread marked as daemon, the jmxfetch app was not terminating
when the main method exited.

After some investigation we noticed that threads in tasks executors were
keeping the thread alive.

This PR DOES NOT change the default behavior, were executors are run as
non-daemons. Adds the possibility, though, to be configured to be
executed as daemon.

labbati added 2 commits July 3, 2019 15:11
…emon

When embedding the jmxfetch app in dd-trce-java we noticed that even if
we it in a thread marked as daemon the jmxfetch app was not terminating
when the main method exited.
After some investigation we noticed that threads in tasks executors were
keeping the thread alive.
This PR DOES NOT change the default behavior, were executors are run as
non-daemons. Adds the possibility, though, to be configured to be
executed as daemon.
@labbati labbati added this to the Next milestone Jul 3, 2019
@labbati labbati marked this pull request as ready for review July 3, 2019 15:59
Copy link
Member

@olivielpeau olivielpeau left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks! Made a couple of comments, but overall LGTM 👍

@@ -37,7 +37,7 @@ public void setThreadPoolExecutor(ExecutorService executor) {
* */
public boolean ready() {
ThreadPoolExecutor tpe = (ThreadPoolExecutor) threadPoolExecutor;
return !(tpe.getMaximumPoolSize() == tpe.getActiveCount());
return !tpe.isTerminated() && !(tpe.getMaximumPoolSize() == tpe.getActiveCount());
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

just a question: is this change needed as well for the purposes of the PR, or is it an "unrelated" improvement?

Copy link
Member Author

@labbati labbati Jul 4, 2019

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is required because when running as daemon the underlying thread pull executor can be terminated before the shutdown hook. The problem is that starting from the shutdown hook we check if a thread executor is ready and if not ready we recreate.

I had a false positive (ready) when actually it was terminated.

I did not had a separate method as looking at the code around I thought that adding this check to the ready function made sense.

Totally open to that, though.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

thanks for the explanation!

Hmm, looking at where the ready function is used, and the case you described: does adding the condition here actually solve the issue you mentioned?

i.e.: if the underlying thread pull executor is terminated before the shutdown hook is run, the ready function here would return false, so the logic in the App would recreate a new thread pool executor. Is that the desired behavior?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks for looking into this. This is the expected behavior based on my investigation. The thread pool is recreated (to do some final work) and then once that work is done it will automatically exit.

I tested both in web apps (i.e. long running processes) and short lived CLI apps and this is how I could observe it behaves.

Anyway this ring a bell in you I can look better into this. Do you have a specific concern I can specifically look for?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Hi @olivielpeau, does my answer make sense to you? Please let me know

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ok, thanks for the explanation, makes sense!

src/main/java/org/datadog/jmxfetch/AppConfig.java Outdated Show resolved Hide resolved
Copy link
Member

@olivielpeau olivielpeau left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM, would appreciate a quick review from @truthbk who originally wrote this logic, to double-check I haven't missed anything :)

@olivielpeau olivielpeau requested a review from truthbk July 8, 2019 12:44
Copy link
Member

@truthbk truthbk left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks good to me as well! 👍

@labbati
Copy link
Member Author

labbati commented Jul 8, 2019

Thanks a lot everyone! Should I merge to master myself? Also, can we plan a release to include this fix?

@labbati labbati merged commit 7f36fa0 into master Jul 8, 2019
@tylerbenson tylerbenson deleted the labbati/as-daemon branch July 10, 2019 21:07
return Executors.newFixedThreadPool(size, new ThreadFactory() {
@Override
public Thread newThread(Runnable runnable) {
Thread thread = Executors.defaultThreadFactory().newThread(runnable);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I would suggest assigning a proper name to the thread... this would have greatly helped our troubleshooting. Maybe next time someone does some work here?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

4 participants