1.在web项目src路径下新建db.properties文件,并添加以下内容: driver=com.mysql.jdbc.Driver url=jdbc:mysql://localhost:3306/test username=root password=123456 jdbcPoolInitSize=10 说明:url=jdbc:mysql://localhost:3306/数据库名 username=MySQL登录账号 password=MySQL连接密码 jdbcPoolInitSize=连接池大小 2.在src下新建java文件JdbcPool.java,其内容为 import java.io.IOException; import java.io.InputStream; import java.io.PrintWriter; import java.lang.reflect.InvocationHandler; import java.lang.reflect.Method; import java.lang.reflect.Proxy; import java.sql.Connection; import java.sql.DriverManager; import java.sql.SQLException; import java.sql.SQLFeatureNotSupportedException; import java.util.LinkedList; import java.util.Properties; import java.util.logging.Logger; import javax.sql.DataSource; public class JdbcPool implements DataSource { /** * * 使用LinkedList集合来存放数据库链接, * 由于要频繁读写List集合,所以这里使用LinkedList存储数据库连接比较合适 */ private static LinkedList<Connection> listConnections = new LinkedList<Connection>(); static{ InputStream in = JdbcPool.class.getClassLoader().getResourceAsStream("db.properties"); Properties prop = new Properties(); try { prop.load(in); String driver = prop.getProperty("driver"); String url = prop.getProperty("url"); String username = prop.getProperty("username"); String password = prop.getProperty("password"); //数据库连接池的初始化连接数大小 int jdbcPoolInitSize =Integer.parseInt(prop.getProperty("jdbcPoolInitSize")); //加载数据库驱动 Class.forName(driver); for (int i = 0; i < jdbcPoolInitSize; i++){ Connection conn = DriverManager.getConnection(url, username, password); System.out.println("获取到了链接" + conn); //将获取到的数据库连接加入到listConnections集合中,listConnections集合此时就是一个存放了数据库连接的连接池 listConnections.add(conn); } } catch (Exception e) { // TODO Auto-generated catch block throw new ExceptionInInitializerError(e); } } @Override public PrintWriter getLogWriter() throws SQLException { // TODO Auto-generated method stub return null; } @Override public void setLogWriter(PrintWriter out) throws SQLException { // TODO Auto-generated method stub } @Override public void setLoginTimeout(int seconds) throws SQLException { // TODO Auto-generated method stub } @Override public int getLoginTimeout() throws SQLException { // TODO Auto-generated method stub return 0; } @Override public Logger getParentLogger() throws SQLFeatureNotSupportedException { // TODO Auto-generated method stub return null; } @Override public <T> T unwrap(Class<T> iface) throws SQLException { // TODO Auto-generated method stub return null; } @Override public boolean isWrapperFor(Class<?> iface) throws SQLException { // TODO Auto-generated method stub return false; } /* 获取数据库连接 * @see javax.sql.DataSource#getConnection() */ @Override public Connection getConnection() throws SQLException { //如果数据库连接池中的连接对象的个数大于0 if (listConnections.size()>0){ //从listConnections集合中获取一个数据库连接 final Connection conn = listConnections.removeFirst(); System.out.println("listConnections数据库连接池大小是" + listConnections.size()); //返回Connection对象的代理对象 return (Connection) Proxy.newProxyInstance(JdbcPool.class.getClassLoader(), new Class[]{Connection.class}, new InvocationHandler(){ @Override public Object invoke(Object proxy, Method method, Object[] args) throws Throwable { if(!method.getName().equals("close")){ return method.invoke(conn, args); }else{ //如果调用的是Connection对象的close方法,就把conn还给数据库连接池 listConnections.add(conn); System.out.println(conn + "被还给listConnections数据库连接池了!!"); System.out.println("listConnections数据库连接池大小为" + listConnections.size()); } return null; } }); }else{ throw new RuntimeException("对不起,数据库忙"); } } @Override public Connection getConnection(String username, String password) throws SQLException { return null; } } ?3.在src下新建java文件JdbcUtil.java,其内容为 import java.sql.Connection; import java.sql.ResultSet; import java.sql.SQLException; import java.sql.Statement; public class JdbcUtil { /** * 数据库连接池 */ private static JdbcPool pool = new JdbcPool(); /** * @Method: getConnection * @Description: 从数据库连接池中获取数据库连接对象 * @Anthor: * @return Connection数据库连接对象 * @throws SQLException */ public static Connection getConnection() throws SQLException{ return pool.getConnection(); } /** * @Method: release * @Description: 释放资源, * 释放的资源包括Connection数据库连接对象,负责执行SQL命令的Statement对象,存储查询结果的ResultSet对象 * @Anthor: * * @param conn * @param st * @param rs */ public static void release(Connection conn,Statement st,ResultSet rs){ if(rs!=null){ try { //关闭存储查询结果的ResultSet对象 rs.close(); //System.out.println("关闭存储查询结果的ResultSet对象"); } catch (Exception e) { e.printStackTrace(); } rs = null; } if(st!=null){ try { //关闭负责执行SQL命令的Statement对象 st.close(); //System.out.println("关闭负责执行SQL命令的Statement对象"); } catch (Exception e) { e.printStackTrace(); } } if(conn!=null){ try { //关闭Connection数据库连接对象 conn.close(); //System.out.println("关闭Connection数据库连接对象"); } catch (Exception e) { e.printStackTrace(); } } } } 4.在操作数据库时调用Connection conn = JdbcUtil.getConnection();获得数据库的连接,之后按照一般的数据库操作流程即可。 总结:java+mysql+tomcat,当web部署到tomcat后,运行一段时间(应该是8个小时),数据库断开连接,导致网页无法正常打开,出现 SEVERE: The web application [] registered the JDBC driver [com.mysql.jdbc.Driver] but failed to unregister it when the web application was stopped. To prevent a memory leak, the JDBC Driver has been forcibly unregistered. 在网上查了一下,是tomcat新的检测机制导致的问题,换个tomcat6.0之前的版本应该就可以了, |
|