结合最近两天在网上看的各种帖子,昨天自己实际试了下,下面以问题的方式,对自己之前的困惑做个回答。
首先说一下,要用到的几个文件。
1)Jboss数据源配置文件,这儿是oracle数据源,数据源后缀名必须以-ds.xml结束,放到部署目录下。
<?xml version="1.0" encoding="UTF-8"?> <datasources> <local-tx-datasource> <jndi-name>jdbc/asap002</jndi-name>
<connection-url>jdbc:oracle:thin:@(DESCRIPTION=(ADDRESS_LIST=(LOAD_BALANCE=off)(ADDRESS=(PROTOCOL=TCP)(HOST=xx.xx.xx.xx)(PORT=1523))(ADDRESS=(PROTOCOL=TCP)(HOST=xx.xx.xx.xx)(PORT=1523))) (CONNECT_DATA=(SERVICE_NAME=asap002)))</connection-url> <use-java-context>true</use-java-context> <driver-class>oracle.jdbc.driver.OracleDriver</driver-class> <min-pool-size>5</min-pool-size> <max-pool-size>20</max-pool-size> <user-name>asap002</user-name> <password>xxx</password>
<exception-sorter-class-name>org.jboss.resource.adapter.jdbc.vendor.OracleExceptionSorter</exception-sorter-class-name> <metadata> <type-mapping>Oracle9i</type-mapping> </metadata> </local-tx-datasource> </datasources>
本文关注重点<jndi-name>jdbc/asap002</jndi-name>和<use-java-context>true</use-java-context>两个节点。为后续叙述方便,jndi-name的值(这里是jdbc/asap002),我们称为ds-jndi-name。use-java-context的值(这里是true),我们称为use-java-context。
2)第二文件是jboss-web.xml文件,同web.xml一同放在web工程的WEB-INF目录下。
<!DOCTYPE jboss-web PUBLIC "-//JBoss//DTD Web Application 5.0//EN" "http://www.jboss.org/j2ee/dtd/jboss-web_5_0.dtd"> <jboss-web> <class-loading java2ClassLoadingCompliance='false'> <loader-repository> com.example:loader=react <loader-repository-config> java2ParentDelegaton=false </loader-repository-config> </loader-repository> </class-loading> <resource-ref> <res-ref-name>jdbc/asap002</res-ref-name> <jndi-name>java:jdbc/asap002</jndi-name> </resource-ref> </jboss-web>
这儿重点关注 <resource-ref> <res-ref-name>jdbc/asap002</res-ref-name> <jndi-name>java:jdbc/asap002</jndi-name> </resource-ref>节点。<resource-ref>节点我们称为jboss-resource-ref;res-ref-name的值(jdbc/asap002)我们称为jboss-res-ref-name;jndi-name的值(java:jdbc/asap002)我们称为jboss-jndi-name。
3)第三文件是web.xml文件。
<?xml version="1.0"?> <!DOCTYPE web-app PUBLIC "-//Sun Microsystems, Inc.//DTD Web Application 2.3//EN" "http://java.sun.com/dtd/web-app_2_3.dtd"> <web-app> <display-name>TumsQRevceive</display-name> <servlet> <servlet-name>TumsQRevceive</servlet-name> <servlet-class>com.travelsky.react.servlet.TumsReceiveServlet</servlet-class> <load-on-startup>99</load-on-startup> </servlet> <servlet> <servlet-name>ForRequestReceive</servlet-name> <servlet-class>com.travelsky.react.servlet.ForRequestReceive</servlet-class> </servlet> <servlet> <servlet-name>First</servlet-name> <servlet-class>test.servlet.First</servlet-class> </servlet> <servlet-mapping> <servlet-name>ForRequestReceive</servlet-name> <url-pattern>/ForRequestReceive</url-pattern> </servlet-mapping> <servlet-mapping> <servlet-name>First</servlet-name> <url-pattern>/First</url-pattern> </servlet-mapping> <welcome-file-list> <welcome-file>index.jsp</welcome-file> </welcome-file-list> <resource-ref> <description>DB Connection</description> <res-ref-name>jdbc/asap002</res-ref-name> <res-type>javax.sql.DataSource</res-type> <res-auth>Container</res-auth> </resource-ref> </web-app>
这个文件重点关注<resource-ref>节点及其子节点<res-ref-name>jdbc/asap002</res-ref-name>。<resource-ref>节点我们称为web-resource-ref;res-ref-name的值(jdbc/asap002)我们称为web-res-ref-name。
4)因为使用Hibernate连接数据库,第四个文件是Hibernate主配置文件Hibernate.cfg.xml。
<?xml version='1.0' encoding='UTF-8'?> <!DOCTYPE hibernate-configuration PUBLIC "-//Hibernate/Hibernate Configuration DTD 3.0//EN" "http://hibernate.sourceforge.net/hibernate-configuration-3.0.dtd"> <hibernate-configuration> <session-factory> <property name="hibernate.connection.datasource"> java:comp/env/jdbc/asap002 </property> <property name="dialect"> org.hibernate.dialect.Oracle9Dialect </property> <property name="hibernate.show_sql">true</property> <mapping resource="tables/EspBaseServiceauth.hbm.xml" /> <mapping resource="tables/EspBaseUser.hbm.xml" /> <mapping resource="tables/EspBaseConfig.hbm.xml" /> <mapping resource="tables/EspSeatFare.hbm.xml" /> <mapping resource="tables/EspBaseAirportcity.hbm.xml" /> <mapping resource="tables/EspBaseOptionalsubcodes.hbm.xml" /> <mapping resource="tables/EspBaseIbeconfig.hbm.xml" /> <mapping resource="tables/EspGdsbsprevaOffice.hbm.xml" /> <mapping resource="tables/EspBaseAirline.hbm.xml" /> </session-factory> </hibernate-configuration>
这个文件重点关注<property name="hibernate.connection.datasource">java:comp/env/jdbc/asap002</property>这个节点。我们称属性值java:comp/env/jdbc/asap002为hibernate.connection.datasource。
下面列出我之前的疑问并解答,相信有些也是其他人的困惑。
1)ds-jndi-name和jboss-jndi-name有什么关系?
这取决于use-java-context,如果use-java-context=false,也就是不使用java上下文,两者应该配成相同值;如果use-java-context=true,jboss-jndi-name应该在ds-jndi-name前面加‘java:’,即jboss-jndi-name=java:ds-jndi-name.对于数据源,建议将use-java-context配成true。
2)jboss-resource-ref和web-resource-ref有什么关系?
必须一样。而且当web-resource-ref存在时,jboss-resource-ref必须存在;
当jboss-resource-ref存在时,web-resource-ref可以省略。
3)web-resource-ref和hibernate.connection.datasource有什么关系?
这取决于hibernate采用JNDI(Java Naming and Directory Interface)还是ENC(Enterprise Naming Context)查找数据源。
如果直接采用JNDI,hibernate.connection.datasource应该等于数据源JNDI名称,即jboss-jndi-name,此时jboss-web.xml中的jboss-resource-ref节点和web.xml中的web-resource-ref节点可以同时省略;
如果采用ENC,hibernate.connection.datasource应该等于java:comp/env/web-resource-ref.此时,jboss-web.xml中的jboss-resource-ref节点必须存在,而web-resource-ref节点可以省略。
上面两种方式都可以成功使用数据源,建议采用ENC,因为这样应用不会直接依赖JNDI名字,移植性更好,比如将应用移植到其他服务器时,如果数据源JNDI名字有改变,仅需要在jboss-web.xml中更改,而不需要修改hibernate配置文件或代码。另外,像Tomcat不支持JNDI的中间件,只能采用ENC方式查找。