Java 管理图书馆服务的最佳实践是什么?

Java 管理图书馆服务的最佳实践是什么?,java,threadpool,shutdown-hook,Java,Threadpool,Shutdown Hook,在我的一个库中,我使用具有5个线程的固定线程池执行器;我的线程不是重量级的,我.get()带有超时,但对于执行器服务,我创建了它,之后,这就是“活到老,任其发展” 你应该.shutdown{,Now}()当你完成它的时候;但这是一个库,我无法预先知道它将如何使用:在一个由servlet容器管理的webapp中,使用一个简单的main() 这感觉不对。我怎样才能做得更好?我是否应该使用除执行器服务以外的其他服务 编辑链接到唯一用户:;守护进程线程可能是一个解决方案,现在我不知道它们是否有我应该注意

在我的一个库中,我使用具有5个线程的固定线程池执行器;我的线程不是重量级的,我
.get()
带有超时,但对于
执行器服务
,我创建了它,之后,这就是“活到老,任其发展”

你应该
.shutdown{,Now}()
当你完成它的时候;但这是一个库,我无法预先知道它将如何使用:在一个由servlet容器管理的webapp中,使用一个简单的
main()

这感觉不对。我怎样才能做得更好?我是否应该使用除执行器服务以外的其他服务


编辑链接到唯一用户:;守护进程线程可能是一个解决方案,现在我不知道它们是否有我应该注意的缺点…

好的,这不是一个真正的答案,更像是一个想法

正如我在前面的评论中提到的,您的
LoadingMessageSourceProvider
组件维护状态,因此必须有人负责正确关闭该组件。您可以尝试通过注册A来实现这一部分(我不会考虑<代码>最终完成< /代码>这里:-)。 我宁愿将它留给组件的用户(应用程序),因为它更清楚何时关闭。事实上,您正在实现一个具有生命周期的轻量级容器——在某种程度上类似于Java EE 7容器提供程序实现的轻量级容器

鉴于您没有可用的JSR-236容器,您必须使调用方能够管理生命周期。我可以想到一个工厂方法,简化的例子:

// maintains the executor service (one service per factory)
private MessageSourceProviderFactory f = MessageSourceProviderFactory.instance();

private void stuff() {
    MessageSourceProvider msp = f.newBuilder()/*. [...] */.build();
    // work with the provider
}

// at some point in time the caller decides to finish
private void end() {
    f.shutdown(); // shutdown the factory and the ExecutorService
}
JSR-236第3.1.6.1节在生命周期方面相当有趣:

3.1.6.1 Java EE产品提供商要求本小节描述了ManagedExecutorService的其他要求 提供者

  • 从ManagedExecutorService执行时,所有任务都将使用提交的组件的Java EE组件标识运行 这项任务
  • ManagedExecutorService的生命周期由应用程序服务器管理。服务器上的所有生命周期操作 ManagedExecutorService接口将抛出 java.lang.IllegalStateException异常。这包括 中定义的以下方法: java.util.concurrent.ExecutorService接口:waitTermination(), isShutdown()、isTerminated()、shutdown()和SHUTDOWNOW()。最终 第3-11版
  • 如果任务的组件未启动,则提交给执行者的任务不能运行
  • 当ManagedExecutorService实例被关闭时 Java EE产品提供程序:

  • 所有提交新任务的尝试都将被拒绝
  • 如果未运行,将取消所有提交的任务
  • 所有正在运行的任务线程都被中断
  • 将调用所有已注册的ManagedTaskListener

  • IMO可能是重复的,它在客户端(API调用方)上关闭服务,因为您的lib是有状态的。当然,守护进程线程可以解决一些问题,但这可能不是您想要的,因为它们会在所有非守护进程线程停止后自动消亡。是否可以将接口共享到您的库?@home链接到唯一使用它的类:。“用户端”类,
    MessageBundle
    ,可以是
    private static final
    ——事实上我总是这样使用它