我讨厌陈述似乎在网上有很多解决方案的问题,但我们似乎无法为我们的案例找到任何有效的最佳实践解决方案,因此觉得我们别无选择。
我们正在构建一个RESTful服务器应用程序,其中使用期间可能会从几个小时到几个月不等。
服务器由Jetty托管。我们没有使用任何ORM,但应用程序分为三层(WebService,Business和Data Layer)。数据层存在通过Guice框架注入的一个类。 JDBC(MySQL连接)在此类的构造函数中实例化。在我们理解Guice默认情况下在每个请求(ref)上创建一个新实例之前,我们首先遇到了很多连接问题。为了摆脱这个问题,并且因为我们的数据层类是有状态的,我们将类注入为Singleton。
现在我们已经预见到,当我们的REST应用程序暂时不使用时,我们可能会遇到麻烦,因为连接会超时,并且不会实例化新的连接,因为构造函数只会被调用一次。 / p>
我们现在有多种解决方案,但我们似乎无法找到解决这个问题的最佳方法,因为它们似乎都不是那么好。任何对其他解决方案的意见或建议都将受到赞赏。
1。扩展配置的mysql超时间隔 我们真的不想要这个,因为我们认为这不是最好的做法。我们当然不应该有任何泄漏的连接对象,但如果有的话,它们会填满可用连接的空闲空间。
2。在每个方法的开头实例化一个新连接,并在最后关闭它 据我们所知,这根本不是最佳做法,因为它会造成很大的开销,应该尽可能避免?
第3。将注入更改回“按请求”,并在每个方法结束时关闭池 这会比#2更糟糕,因为我们不仅要实例化一个新连接,还要在每个请求上实例化一个新对象?
4。检查每个方法开头的连接状态,并在关闭时实例化新连接 一个例子是ping(example)mysql,并在它抛出异常时实例化一个新连接。这会起作用,但会产生一些开销。关于这个输入是否真的会对性能产生任何影响的任何想法?
5。显式捕获方法中抛出的任何异常,指示连接已关闭,如果是,则实例化新连接 这样,我们就可以摆脱ping开销,但它会使我们的代码变得非常复杂,因为我们必须找到一种方法来确保方法将返回如果已经存在的连接它们将返回的内容。 / p>
6。使用连接池 除了使用应用程序服务器(即Glassfish)之外,我们不熟悉连接池。我们也想知道这是否真的可以解决我们的问题?如果是这样;对我们提供连接池的任何框架的任何建议? Here他们建议在Jetty中使用PLUS。
请询问是否有任何不清楚的地方。我可能忘记添加一些重要信息。这对我来说更像是一个设计问题,但如果有人认为这会有所帮助,我很乐意提供任何代码。
提前致谢!
答案 0 :(得分:2)
连接池是要走的路 它们有许多优点:
你当然应该在某种类型的游泳池中保持联系,事实上,如果你不咬人,你几乎肯定会最终自己写一个。
当你实现连接检查以便它们不会过时时,某种类型的连接保持器,这样你就不需要每次都重新打开它们,某种异常处理代码...你得到我的漂移。
我使用了dbcp和boneCP,两者都非常易于使用和配置,并且可以节省您处理JDBC连接问题的挫折时间。
我并不过分熟悉Guice,但我认为它有一些方法可以为Object提供自己的工厂方法,因此您可以使用它来从池中获取连接,然后在完成返回后简单地调用close()
他们到游泳池
如果您正在使用网络服务器,您始终可以使用interceptor
或filter
绑定到工作线程的连接并在处理后丢弃它们,在这种情况下,您的连接提供商只需要将连接提供者绑定到当前的主题。
答案 1 :(得分:1)
改为注入Provider<Connection>
并让提供者从可以检测陈旧条目的连接池中发出连接(编辑:在您需要时编辑)。
应该从池中丢弃未返回的连接。