Java Tomcat和其他容器中的数据源和连接池与JNDI有什么关系?

Java Tomcat和其他容器中的数据源和连接池与JNDI有什么关系?,java,jdbc,jndi,connection-pooling,Java,Jdbc,Jndi,Connection Pooling,我试图理解连接池(JDBC连接池)。根据答案,每个容器都有自己的机制。我还试图了解JNDI及其实现,以及与在网络中定位对象(如目录和用户)相关的任何帖子或文章,以下是一些文章: 阅读这篇描述如何在Tomcat容器中管理连接池的文章,第二段 已向命名服务注册javax.sql.DataSource接口 基于jndiapi。数据源驱动程序允许访问 数据库通过数据源接口。在中查找数据源对象 基于通过JNDI资源注册的上下文 问题是JNDI和networking目录与实例化提供连接池(可能通过fly

我试图理解连接池(JDBC连接池)。根据答案,每个容器都有自己的机制。我还试图了解JNDI及其实现,以及与在网络中定位对象(如目录和用户)相关的任何帖子或文章,以下是一些文章:

阅读这篇描述如何在Tomcat容器中管理连接池的文章,第二段

已向命名服务注册javax.sql.DataSource接口 基于jndiapi。数据源驱动程序允许访问 数据库通过数据源接口。在中查找数据源对象 基于通过JNDI资源注册的上下文

问题是JNDI和networking目录与实例化提供连接池(可能通过flyweight设计模式实现)的数据源实现有什么关系


我错过什么了吗

它们没有直接关系。DataSource只是一个用于管理数据库连接池中的连接的接口。任何Javaservlet容器或JavaEE容器都可以为此接口提供自己的实现

作为一名应用程序开发人员,您不需要担心容器如何实例化此实现或实际的实现类是什么

为了在实际的容器实现和应用程序之间提供松散耦合,您只需要获得此实现的一个实例,该实例通常通过JNDI完成


容器实例化数据源实现,并将其绑定到JNDI注册表中的特定地址,您可以作为应用程序开发人员在该地址中检索它。在应用程序中,您只需使用数据源接口访问此实现,从而使您的应用程序可以在不同的服务器及其各自的数据源实现上进行移植。

要想象这些完全无关的技术是如何工作的,最好说明为什么会存在JNDI、池之类的东西

  • 您有一个Java应用程序,希望连接到数据库并持久化数据。好了,JDBC来了
  • 在持久化数据时,您会注意到打开和关闭到数据库的连接非常耗时,并且会降低程序的速度。所以您引入了池-JDBC连接不是每次使用时都打开和关闭,而是从池中获取并返回到池中

  • JPA—您已经厌倦了编写特定于数据库的代码,所以您编写了一个库来处理许多与持久性相关的事情,这样您的生活就更轻松了

  • JNDI—您正在以企业应用程序的形式编写Java应用程序,可以是JavaEE,也可以是某种不推荐的替代Spring。你必须以某种方式创造。朴素的方法是让应用程序创建自己的数据源(在Spring中仍然是可行的选项)。更好的方法是在服务器上配置数据源。数据源由一个名称标识,应用程序只指定名称,而不指定其他名称。然后,将数据源部署到应用服务器时,将其注入应用程序。数据源配置和创建在服务器上完成,并通过JNDI注入到应用程序中。例如,通过这种方式,您可以让更多的应用程序使用相同的连接池共享相同的数据源


  • 但JNDI不仅仅用于数据源“注入”。使用JNDI,您可以识别和本地化任何资源

    有时JNDI用作对象存储(Java对象),不是通过网络或文件系统访问对象,如打印机和目录,而是访问已在内存中实例化的Java对象。 我之所以感到困惑,是因为每当您阅读JNDI时,它都会解释它的主要用途,而不是用来实例化数据源对象的方式:

    以下是oracle教程中的一段话:

    除了在中使用目录外,还将目录作为对象存储 传统的方式是,Java应用程序也可以将其用作存储库 对于Java对象,即存储和检索Java对象。对于 例如,Java打印客户端程序应该能够查找 打印机对象,并将数据流发送到 用于打印的打印机对象


    但是JNDI不是用来定位目录和对象的吗?容器如何使用JNDI为应用程序提供数据源实现?JNDI用于使对象引用可用。这可以是本地的,也可以是通过网络的,具体取决于JNDI实现。在容器数据源的上下文中,容器只需执行对象实例化(即newdatasourceimpl()),然后在JNDI注册表中“注册”它。然后应用程序可以使用JNDI查找此数据源。据我所知,这一点是通过JNDI公开数据源,以便多个应用程序可以使用同一个池?@Adelin-
    多个应用程序可以使用同一个池
    -不,这不是主要原因。主要原因是有一个可以定义数据源的单一位置,因此代码的其余部分不知道该定义。其余的代码可以是单个应用程序(首选)或多个应用程序(不首选)。@Paulie“幼稚的方法是让应用程序创建自己的数据源”-这不一定幼稚。这取决于应用程序。看见Java EE的美妙之处在于,您可以透明地从应用程序内定义的数据源来回移动到“服务器上”定义的数据源,而使用该数据源的应用程序代码不必知道或关心。@ArjanTijms但为什么是JNDI?为什么不使用一些公开数据源的jar,比如一个数据源工厂或者它管理的每个应用程序都可以获取的jar呢