Jersey ThreadPoolExecutorProvider 拒绝请求时如何发送服务器错误响应?

How can the server error response be sent when the Jersey ThreadPoolExecutorProvider rejects the request?

因此,在服务器端,我们扩展了 org.glassfish.jersey.spi.ThreadPoolExecutorProvider 以获得可运行任务的有界 BlockingQueue,覆盖了 corePoolSize 和 MaximumPoolSize。

当BlockingQueue的容量超过时(当有不能再排队的请求时),它开始拒绝任务(这和拒绝请求一样好)。

但我们观察到,当服务器端的任务在上述情况下被拒绝时,没有向客户端发送响应。最初我们甚至不知道请求是否被拒绝,但后来阅读了 java.util.concurrent.RejectedExecutionHandler 并且我们尝试实现一个 customHandler 并在创建一个 Executor 时传递它(请参考下面的代码片段)。

我现在可以看到任务被拒绝了,但不确定如何处理向客户端发送请求被拒绝的响应。如果我不这样做,那么客户端会一直等到超时。

我是否需要在泽西岛进行任何配置才能向客户端发送正确的响应。

    @Override
    protected ThreadPoolExecutor createExecutor(int corePoolSize, int maximumPoolSize, long keepAliveTime, BlockingQueue<Runnable> workQueue, ThreadFactory threadFactory, RejectedExecutionHandler handler){
        System.err.println("MANDAR_CREATED_EXECUTOR");
        return super.createExecutor(corePoolSize, maximumPoolSize, keepAliveTime, workQueue, threadFactory, new CustomHandler());
    }

    
    class CustomHandler implements RejectedExecutionHandler {
        @Override
        public void rejectedExecution(Runnable r, ThreadPoolExecutor executor) {
            System.err.println("MANDAR_REJECTED");
            executor.remove(r);
            executor.purge();
        }
    }

PS:我们用于实现 Jersey 层的样式是 this

解决方案有点像抛出 RejectedExecutionException。这是由 new ThreadPoolExecutor.AbortPolicy() 完成的。奇怪的是 AbortPolicy 是默认策略,在覆盖此 createExecutor 方法之前仍然没有触发。似乎 Jersey 对 Executor 的 RejectionExecutionHandler 的实现有点不同并且没有使用 AbortPolicy。

@Override
protected ThreadPoolExecutor createExecutor(int corePoolSize, int maximumPoolSize, long keepAliveTime, BlockingQueue<Runnable> workQueue, ThreadFactory threadFactory, RejectedExecutionHandler handler){
    return super.createExecutor(corePoolSize, maximumPoolSize, keepAliveTime, workQueue, threadFactory, new ThreadPoolExecutor.AbortPolicy());
}

编辑: 实际上更好的是覆盖 getRejectedExecutionHandler 方法,returns 基于 AbortyPolicy 的处理程序。

/**
* This method returns the handler that handles the rejected runnable tasks.
* We have initialized the handler to {@link AbortPolicy} that helps throwing a {@link RejectedExecutionException} which in turn returns 500 statusCode response
*/
@Override
protected RejectedExecutionHandler getRejectedExecutionHandler() {
    return this.handler;
}