正如大家所说,您需要使用连接池。为什么?怎么回事?等。
您的解决方案出了什么问题
我知道这一点,因为我也曾认为这是一个好主意。问题是双重的:
- 所有线程(servlet 请求的每个线程都有一个线程)将共享相同的连接。因此,请求将一次处理一个。这是非常慢的,即使你只是坐在一个浏览器中并依靠F5键。试试吧:这些东西听起来很高级和抽象,但它是经验性的和可测试的。
- 如果连接因任何原因中断,则不会再次调用 init 方法(因为 servlet 不会停止服务)。不要试图通过在doGet或doPost中放置一个尝试来解决这个问题,因为那样你就会陷入地狱(有点像在没有被要求的情况下编写应用程序服务器)。
- 与人们的想法相反,你不会有事务问题,因为事务开始与线程相关联,而不仅仅是连接。我可能是错的,但由于这是一个糟糕的解决方案,所以不要出汗。
为什么选择连接池
连接池为您提供了一大堆优势,但最重要的是它们解决了
- 建立真正的数据库连接成本高昂。连接池周围总是有一些额外的连接,并为您提供其中之一。
- 如果连接失败,连接池知道如何打开一个新连接池
- 非常重要:每个线程都有自己的连接。这意味着线程在它应该在的地方处理:在数据库级别。数据库效率超高,可以轻松处理并发请求。
- 其他东西(如JDBC连接字符串的集中位置等),但是有数百万篇文章,书籍等。
何时获取连接
在服务委托(doPost,doGet,doDisco等)中启动的调用堆栈中的某个位置,您应该获得一个连接,然后您应该做正确的事情并在最终的块中返回它。我应该提到,C#主架构师家伙一次说过,你应该使用块比块多100倍。从未说过的更真实的话...finally
catch
哪个连接池
您位于 servlet 中,因此应使用容器提供的连接池。您的 JNDI 代码将完全正常,除了您如何获取连接。据我所知,所有 servlet 容器都有连接池。
关于上述答案的一些评论建议改用特定的连接池 API。您的 WAR 应该是可移植的,并且“只需部署”。我认为这基本上是错误的。如果您使用容器提供的连接池,那么您的应用程序将可以部署在跨多台计算机的容器上,以及 Java EE 规范提供的所有花哨的东西。是的,必须编写特定于容器的部署描述符,但这是EE方式,mon。
一位评论者提到,某些容器提供的连接池不适用于 JDBC 驱动程序(他/她提到了 Websphere)。这听起来完全是牵强附会和荒谬的,所以这可能是真的。当这样的事情发生时,把你“应该做”的所有事情都扔进垃圾箱,尽你所能。这就是我们得到的报酬,有时:)