-
Notifications
You must be signed in to change notification settings - Fork 80
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
Issue 355: ProcessHandler configurable executor timeout #356
Issue 355: ProcessHandler configurable executor timeout #356
Conversation
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
- Public static variables should be considered as bad practice.
- A user should not know intrinsic details of
ProcessHandler
to change timeout
src/main/java/com/github/kokorin/jaffree/process/ProcessHandler.java
Outdated
Show resolved
Hide resolved
src/main/java/com/github/kokorin/jaffree/process/ProcessHandler.java
Outdated
Show resolved
Hide resolved
The variable is
The user has the intrinsic details of ProcessHandler thrust upon them the first time they see this in their logs:
It is only at this point that anyone will go looking for a way to change the timeout, so naturally they will look in ProcessHandler first - unless we change the log message or leave other clues in the code. If you don't like the user working with Perhaps then somewhere within the fluent API when we start the eg we could override the
Or we could create some sort of Config object if we want to leave room to add more configuration items in the future. eg
Or if you were thinking something else let me know - I am happy to open a new PR that follows your preferred design approach. |
@@ -50,7 +50,8 @@ public class ProcessHandler<T> { | |||
private Stopper stopper = null; | |||
private List<String> arguments = Collections.emptyList(); | |||
|
|||
private static final int EXECUTOR_TIMEOUT_MILLIS = 10_000; | |||
@SuppressWarnings("checkstyle:MagicNumber") // 10,000ms is the default timeout |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It's better to declare static final variable named DEFAULT_EXECUTOR_TIMEOUT_MILLIS
and assign it to executorTimeoutMillis
I prefer not to change |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Please, rebase on latest in develop branch (as it contains MacOS test fixes)
src/main/java/com/github/kokorin/jaffree/process/ProcessHandler.java
Outdated
Show resolved
Hide resolved
src/main/java/com/github/kokorin/jaffree/process/ProcessHandler.java
Outdated
Show resolved
Hide resolved
…cutor Timeout value
30229b2
to
0d4817e
Compare
src/main/java/com/github/kokorin/jaffree/process/ProcessHandler.java
Outdated
Show resolved
Hide resolved
@@ -180,7 +199,9 @@ protected T interactWithProcess(final Process process) { | |||
status = process.waitFor(); | |||
LOGGER.info("Process has finished with status: {}", status); | |||
|
|||
waitForExecutorToStop(executor, EXECUTOR_TIMEOUT_MILLIS); | |||
if (executorTimeoutMillis > 0) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
waitForExecutorToStop
must be invoked, otherwise ProcessHandler exists immediately.
Check for zero timeout should be done in that method.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
EDIT: This reply was written when I had misunderstood your intention for executorTimeoutMillis == 0
I thought 0 would mean "do not wait at all", but now I think you intended 0 to mean "wait forever".
I still think that this comment is technically correct - there is a small (mostly harmless) edge-case bug.
But to understand the reasoning you will have to imagine that 0ms timeout means 0ms timeout ie "don't wait at all".
Let's discuss the implementation of waitForExecutorToStop()
.
First of all I think that this line
if (System.currentTimeMillis() - waitStarted > timeoutMillis) {
has an edge-case bug.
It should actually use >=
.
Think about the case where timeoutMillis
== 0:
System.currentTimeMillis() - waitStarted
will almost certainly be 0- The if clause will fail and you will end up invoking
Thread.sleep(100)
- That would be unintended / unexpected
In a practical sense, this was not important when we had a constant EXECUTOR_TIMEOUT_MILLIS, and it is not important if we short-circuit for the timeoutMillis==0
case.
But given that we are discussing calling waitForExecutorToStop()
for the zero case, I thought I should mention it.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Second of all I wonder why you have a do ... while
loop instead of a while
loop.
The do ... while
deals with the case where the executor has already stopped by the time we run waitForExecutorToStop()
.
In this case, why do we want to force a Thread.sleep(100)
?
Why would we want to log "Executor hasn't yet stopped..." when that is not true?
The log is only at TRACE level, so the practical outcome is pretty harmless.
Further it is perhaps very unlikely to hit this case ... but it seems to me that a while
loop would be the correct implementation - am I misunderstanding something?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
waitForExecutorToStop must be invoked, otherwise ProcessHandler exists immediately.
This was confusing me for a long time ... until I realised ... I think I misunderstood your previous request:
I think it makes sense to allow a user to disable timeout by setting 0 (zero) value.
What you meant was "a zero value means wait indefinitely".
I thought you meant "a zero value means don't wait at all".
As a general rule in configuration values, I prefer to let zero mean zero - and then use -1, or "any negative value" to mean a special case like "disable the timeout".
The bonus with "any negative value" is that you don't need to check for valid values - all values have some meaning.
However, in this particular case, would an actual 0ms
timeout ever be a useful setting?
Perhaps here the "0" as a special value makes sense ...
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
However, in this particular case, would an actual
0ms
timeout ever be a useful setting? Perhaps here the "0" as a special value makes sense ...
Even ffmpeg itself uses -threads 0
as an option to use all threads available.
Second of all I wonder why you have a do ... while loop instead of a while loop.
The do ... while deals with the case where the executor has already stopped by the time we run waitForExecutorToStop().
To be honest, I don't care. It's highly unlikely that ffmpeg will complete in 100ms or less.
if (System.currentTimeMillis() - waitStarted > timeoutMillis) {
I think it can be like if (timeoutMillis> 0 && System.currentTimeMillis() - waitStarted > timeoutMillis) {
…imeout means indefinite wait
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thank you
Allow an application developer to override the default Executor Timeout value