Java ExecutorCompletionService作为API响应程序

Java ExecutorCompletionService作为API响应程序,java,api,executorservice,threadpoolexecutor,Java,Api,Executorservice,Threadpoolexecutor,我有一个服务器应用程序,它在ServerSocket上侦听传入的查询。提交查询的客户机希望打开一个套接字到服务器,向上游传递查询,然后(可能在短时间后)从提交查询的同一套接字读取对查询的响应 为此,我尝试使用ExecutorCompletionService。不同的查询类被传递给不同的可调用的s,但所有查询类都应返回一个字符串 在我真正尝试回复客户之前,所有这些都是可以管理的。Future对象当前都是Future类型,但我无法将该结果(字符串)与相应的套接字相结合 我的解决方案将是使我的所有可调

我有一个服务器应用程序,它在
ServerSocket
上侦听传入的查询。提交查询的客户机希望打开一个套接字到服务器,向上游传递查询,然后(可能在短时间后)从提交查询的同一套接字读取对查询的响应

为此,我尝试使用
ExecutorCompletionService
。不同的查询类被传递给不同的
可调用的
s,但所有查询类都应返回一个
字符串

在我真正尝试回复客户之前,所有这些都是可以管理的。
Future
对象当前都是
Future
类型,但我无法将该结果(
字符串
)与相应的
套接字相结合

我的解决方案将是使我的所有
可调用
都是
可调用
类型,其中
StringSocketPair
看起来像

public class StringSocketPair {
    Socket sock;
    String content;
}
但这一切似乎有点奇怪,因为现在我必须将
Socket
传递给
Callable
构造函数,这样它就可以从
call()
方法返回
String
结果。这样我就可以将
字符串
推到另一个线程中的
套接字
,该线程轮询
ExecutorCompletionService.take()

另一个选项是使用
Runnable
s而不是
Callable
s,并让每个
Runnable
任务自己响应
Socket
,但由于我有十几个查询类型,每个查询类型都有自己的任务对象,我不必添加
respondToClient()
对每个任务对象的每个
run()方法的末尾进行某种调用


对于我认为相当常见的设置,必须有一个更简单的解决方案?

根据使用
可运行的
的思想,您可以使用来定义响应的功能。这将避免您必须为每个任务编写公共代码,因为公共代码将放置在实现Runnable的抽象父类中

模板方法模式:

abstract class TemplateSuperClass implements Runnable {
    public void run() {
        //some setup code here
        String message = taskWork(...);
        socket.write(message);
        //common cleanup code
    }

    abstract String taskWork(...);
}

class HelloWorld extends TemplateSuperClass {
    String taskWork(...) {
        return "Hello World";
    }
}

否则,更改Callable以返回响应消息和套接字的元组可能是正确的。

是的,这正是我的想法,但我仍然必须在每个
Runnable
的最后一行实际调用该方法。除非我能给父类添加某种钩子?不。我已经编辑了我的答案,以包含一个关于使用模板方法模式的示例。