mirror of
https://github.com/lucko/LuckPerms.git
synced 2025-08-30 17:49:48 +02:00
Avoid blocking worker pool for command timeout check (#2951)
3rd time lucky...
This commit is contained in:
@@ -182,7 +182,11 @@ public class CommandManager {
|
|||||||
}, this.executor);
|
}, this.executor);
|
||||||
|
|
||||||
// schedule another task to catch if the command doesn't complete after 10 seconds
|
// schedule another task to catch if the command doesn't complete after 10 seconds
|
||||||
timeoutTask.set(scheduler.awaitTimeout(future, 10, TimeUnit.SECONDS, () -> handleCommandTimeout(executorThread, argsCopy)));
|
timeoutTask.set(scheduler.asyncLater(() -> {
|
||||||
|
if (!future.isDone()) {
|
||||||
|
handleCommandTimeout(executorThread, argsCopy);
|
||||||
|
}
|
||||||
|
}, 10, TimeUnit.SECONDS));
|
||||||
|
|
||||||
return future;
|
return future;
|
||||||
}
|
}
|
||||||
|
@@ -25,12 +25,8 @@
|
|||||||
|
|
||||||
package me.lucko.luckperms.common.plugin.scheduler;
|
package me.lucko.luckperms.common.plugin.scheduler;
|
||||||
|
|
||||||
import java.util.concurrent.CompletableFuture;
|
|
||||||
import java.util.concurrent.ExecutionException;
|
|
||||||
import java.util.concurrent.Executor;
|
import java.util.concurrent.Executor;
|
||||||
import java.util.concurrent.TimeUnit;
|
import java.util.concurrent.TimeUnit;
|
||||||
import java.util.concurrent.TimeoutException;
|
|
||||||
import java.util.concurrent.atomic.AtomicReference;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* A scheduler for running tasks using the systems provided by the platform
|
* A scheduler for running tasks using the systems provided by the platform
|
||||||
@@ -89,44 +85,6 @@ public interface SchedulerAdapter {
|
|||||||
*/
|
*/
|
||||||
SchedulerTask asyncRepeating(Runnable task, long interval, TimeUnit unit);
|
SchedulerTask asyncRepeating(Runnable task, long interval, TimeUnit unit);
|
||||||
|
|
||||||
/**
|
|
||||||
* Waits for the given time for {@code future} to complete. If the future isn't completed,
|
|
||||||
* {@code onTimeout} is executed.
|
|
||||||
*
|
|
||||||
* @param future the future to wait for
|
|
||||||
* @param timeout the time to wait
|
|
||||||
* @param unit the unit of timeout
|
|
||||||
* @param onTimeout the function to execute when the timeout expires
|
|
||||||
*/
|
|
||||||
default SchedulerTask awaitTimeout(CompletableFuture<?> future, long timeout, TimeUnit unit, Runnable onTimeout) {
|
|
||||||
// a reference to the thread blocking on the future
|
|
||||||
AtomicReference<Thread> thread = new AtomicReference<>();
|
|
||||||
|
|
||||||
// in a new thread, await the completion of the future up to the given timeout
|
|
||||||
executeAsync(() -> {
|
|
||||||
thread.set(Thread.currentThread());
|
|
||||||
try {
|
|
||||||
future.get(timeout, unit);
|
|
||||||
} catch (InterruptedException | ExecutionException e) {
|
|
||||||
// ignore - this probably means the future completed successfully!
|
|
||||||
} catch (TimeoutException e) {
|
|
||||||
// run the timeout task
|
|
||||||
onTimeout.run();
|
|
||||||
} finally {
|
|
||||||
thread.set(null);
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
// to cancel the timeout task, just interrupt the thread that is blocking on the future
|
|
||||||
// and it will gracefully stop.
|
|
||||||
return () -> {
|
|
||||||
Thread t;
|
|
||||||
if ((t = thread.get()) != null) {
|
|
||||||
t.interrupt();
|
|
||||||
}
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Shuts down the scheduler instance.
|
* Shuts down the scheduler instance.
|
||||||
*
|
*
|
||||||
|
Reference in New Issue
Block a user