转录笔记:不过遗憾的是,如下几种方法都没有在我的机器上配置成功(Tomcat5.5.17 + WinXPSP2)。正确配置见我自己的评论,Tomcat 的日志中没发现什么错误,看上去都很正常,但是测试程序却老是提示同样的错误:
Error occurred:org.apache.tomcat.dbcp.dbcp.SQLNestedException: Cannot create JDBC driver of class '' for connect URL 'null'
但Driver名和URL都设置对了,在Admin的DataSource中也看得到。
Tomcat版本之间变化太大了,请大家帮忙看看,到底哪里有问题,谢谢!
1.在$CATALINA_HOME/conf/server.xml中添加配置信息,声明连接池的具体信息,添加内容如下:
<!--声明连接池-->
<Resource name="jdbc/mysql" auth="Container" type="javax.sql.DataSource"/>
<!-- 对连接池的参数进行设置 -->
<ResourceParams name="jdbc/mysql">
<parameter>
<name>factory</name>
<value>org.apache.commons.dbcp.BasicDataSourceFactory</value>
</parameter>
<parameter>
<name>maxWait</name>
<value>5000</value>
</parameter>
<parameter>
<name>maxActive</name>
<value>20</value>
</parameter>
<parameter>
<name>username</name>
<value>shopadm</value>
</parameter>
<parameter>
<name>password</name>
<value>123</value>
</parameter>
<parameter>
<name>url</name>
<value>jdbc:mysql://localhost/shopdb?useUnicode=true&charact-erEncoding=gb2312</value>
</parameter>
<parameter>
<name>driverClassName</name>
<value>com.mysql.jdbc.Driver</value>
</parameter>
<parameter>
<name>maxIdle</name>
<value>10</value>
</parameter>
</ResourceParams>
2. 在$CATALINA_HOME/conf/web.xml的</web-app>前添加如下信息:
<resource-ref>
<description>DB Connection</description>
<res-ref-name>jdbc/mysql</res-ref-name>
<res-type>javax.sql.DataSource</res-type>
<res-auth>Container</res-auth>
</resource-ref>
其中<res-ref-name>中的参数名必须和server.xml中声明的连接名一样。
3. 在$CATALINA_HOME/conf/catalina/localhost目录下找到需要进行数据库连接的当前程序的配置信息,比如这里是shopping.xml,在这个文件中添加如下信息:
<Context …>
…
<ResourceLink name=”jdbc/mysql” global=”jdbc/mysql” type=”javax.sql.DataSource”/>
…
</Context>
大功告成!
在此基础上,参考Tomcat官方网站的用户手册,摸索出另外一种配置连接池的方法,这个方法不需要对server.xml进行修改,只要对需要使用到连接池的程序的配置文档进行修改就可以了。方法如下:
1.$CATALINA_HOME/conf/catalina/localhost目录下找到需要数据库连接池的程序的配置文档,此处是 shopping.xml。在<Context> </Context>之间添加如下信息,声明一个数据库连接池:
<Resource name="jdbc/mysql" auth="Container" type="javax.sql.DataSource"/>
<ResourceParams name="jdbc/mysql">
<parameter>
<name>factory</name>
<value>org.apache.commons.dbcp.BasicDataSourceFactory</value>
</parameter>
<parameter>
<name>maxWait</name>
<value>5000</value>
</parameter>
<parameter>
<name>maxActive</name>
<value>20</value>
</parameter>
<parameter>
<name>password</name>
<value>123</value>
</parameter>
<parameter>
<name>url</name>
<value>jdbc:mysql://localhost/shopdb?useUnicode=true&characterEncoding=gb2312</value>
</parameter>
<parameter>
<name>driverClassName</name>
<value>com.mysql.jdbc.Driver</value>
</parameter>
<parameter>
<name>maxIdle</name>
<value>10</value>
</parameter>
<parameter>
<name>username</name>
<value>shopadm</value>
</parameter>
</ResourceParams>
这里的参数和上一种方法中添加到server.xml里的信息几乎是完全一样的。
2.在对应程序的WEB-INF下建立一个web.xml文档,添加如下信息:
<?xml version="1.0" encoding="ISO-8859-1"?>
<web-app xmlns="http://java.sun.com/xml/ns/j2ee"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://java.sun.com/xml/ns/j2ee
http://java.sun.com/xml/ns/j2ee/web-app_2_4.xsd"
version="2.4">
<resource-ref>
<description>DB Connection</description>
<res-ref-name>jdbc/mysql</res-ref-name>
<res-type>javax.sql.DataSource</res-type>
<res-auth>Container</res-auth>
</resource-ref>
</web-app>
另外一种方法,与Admin 页面配置结果比较接近,同样是放在GlobalNamingResources中
1.将数据库驱动程序的JAR文件放在Tomcat的 common/lib 中;
2.在server.xml中设置数据源,以MySQL数据库为例,如下:
在<GlobalNamingResources> </GlobalNamingResources>节点中加入,
<Resource
name="jdbc/DBPool"
type="javax.sql.DataSource"
password="root"
driverClassName="com.mysql.jdbc.Driver"
maxIdle="2"
maxWait="5000"
username="root"
url="jdbc:mysql://127.0.0.1:3306/test"
maxActive="4"/>
属性说明:name,数据源名称,通常取”jdbc/XXX”的格式;
type,”javax.sql.DataSource”;
password,数据库用户密码;
driveClassName,数据库驱动;
maxIdle,最大空闲数,数据库连接的最大空闲时间。超过空闲时间,数据库连
接将被标记为不可用,然后被释放。设为0表示无限制。
MaxActive,连接池的最大数据库连接数。设为0表示无限制。
maxWait ,最大建立连接等待时间。如果超过此时间将接到异常。设为-1表示
无限制。
3.在你的web应用程序的web.xml中设置数据源参考,如下:
在<web-app></web-app>节点中加入,
<resource-ref>
<description>MySQL DB Connection Pool</description>
<res-ref-name>jdbc/DBPool</res-ref-name>
<res-type>javax.sql.DataSource</res-type>
<res-auth>Container</res-auth>
<res-sharing-scope>Shareable</res-sharing-scope>
</resource-ref>
子节点说明: description,描述信息;
res-ref-name,参考数据源名字,同上一步的属性name;
res-type,资源类型,”javax.sql.DataSource”;
res-auth,”Container”;
res-sharing-scope,”Shareable”;
4.在web应用程序的context.xml中设置数据源链接,如下:
在<Context></Context>节点中加入,
<ResourceLink
name="jdbc/DBPool"
type="javax.sql.DataSource"
global="jdbc/DBPool"/>
属性说明:name,同第2步和第3步的属性name值,和子节点res-ref-name值;
type,同样取”javax.sql.DataSource”;
global,同name值。
至此,设置完成,下面是如何使用数据库连接池。
1.建立一个连接池类,DBPool.java,用来创建连接池,代码如下:
import javax.naming.Context;
import javax.naming.InitialContext;
import javax.naming.NamingException;
import javax.sql.DataSource;
public class DBPool {
private static DataSource pool;
static {
Context env = null;
try {
env = (Context) new InitialContext().lookup("java:comp/env");
pool = (DataSource)env.lookup("jdbc/DBPool");
if(pool==null)
System.err.println("'DBPool' is an unknown DataSource");
} catch(NamingException ne) {
ne.printStackTrace();
}
}
public static DataSource getPool() {
return pool;
}
}
2. 在要用到数据库操作的类或jsp页面中,用DBPool.getPool().getConnection(),获得一个Connection对象,就可 以进行数据库操作,最后别忘了对Connection对象调用close()方法,注意:这里不会关闭这个Connection,而是将这个 Connection放回数据库连接池。
<补充评论>
在网上再三查找,并经过反复试验后,总算是把它配置好了,发现如下几个问题:
1。 Tomcat 5.5.17 的Admin功能很不完善,在JNDI的配置上存在BUG,无法把非全局的DataSource 或ResourceLinks写入%TOMCAT_HOME%/conf/Catalina/localhost /<webname>.xml中;只能手工进行;
2. CLASSPATH配置可能也有问题,Driver包必须放在%TOMCAT_HOME%\common\lib下才能被找 到,%TOMCAT_HOME%/shared/lib下不行,甚至在<webname>/WEB-INF/lib下也不能被找到,应该是这 个版本的问题,记得以前至少在应用下是能找到的;
总结一下,主要是三个地方要配置:
a. %TOMCAT_HOME%/conf/ 下配置DataSource: 配置server.xml 或 localhost/<webname>.xml
其中server.xml下配置DataSource则可供所有WEB应用使用,
需要在<GlobalNamingResources> 下加上<Resource>项,这个通过Admin页面也可以完成;然后给需要用到的应用中加上<ResourceLink>即可,但只能手工进行
<ResourceLink name="jdbc/<jndiname>" global="jdbc/<jndiname>" type="javax.sql.DataSource"/>, 放在<Context>下;
如果只想给某个程序用,不想配置Server.xml的话,可以只在localhost/<webname>.xml中加上<Resource>,把<Resource>加到<Context>下
<Resource
auth="Container"
description="DB Connection"
name="jdbc/<jndiname>"
type="javax.sql.DataSource"
driverClassName="com.mysql.jdbc.Driver"
password="<pass>"
maxIdle="2"
maxWait="5000"
username="<user>"
url="jdbc:mysql://localhost/<dbname>"
maxActive="4"/>
b. 在应用的web.xml中配置<resource-ref>
<resource-ref>
<description>EMCenter Database for WEB Applications</description>
<res-ref-name>jdbc/<jndiname></res-ref-name>
<res-type>javax.sql.DataSource</res-type>
<res-auth>Container</res-auth>
</resource-ref>
c. 把driver包拷贝到%TOMCAT_HOME%/common/lib/下,应该是最简配置了,有兴趣的可以继续试验,留意看logs/目录下的日志记录能加快进程。其实Admin要是能改进一下最好了,这样太麻烦
另: 有些不解的是,我用的sqltags包(jstl.jar,standard.jar)放在WEB-INF/lib下却能被找到,测试代码如下:
<%@ page language="java" contentType="text/html; charset=GB18030"
pageEncoding="GB18030"%>
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
<%@ taglib uri="http://java.sun.com/jsp/jstl/sql" prefix="sql" %>
<%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %>
<sql:query var="rs" dataSource="jdbc/<jndiname>">
select * from <tablename>
</sql:query>
<html>
<head>
<title>DB Test</title>
</head>
<body>
<h2>Results</h2>
<c:forEach var="row" items="${rs.rows}">
ID ${row.id}<br/>
name ${row.name}<br/>
</c:forEach>
</body>
</html>