老项目采用tomcat出现异常:Connection reset by peer: socket write error 异常解决方法

jsp+servlet项目一段时间就出现异常,导致无法登陆系统,数据库无法连接上

异常信息如下:

java.sql.SQLException: Io 异常: Connection reset by peer: socket write error
	at oracle.jdbc.dbaccess.DBError.throwSqlException(DBError.java:134)
	at oracle.jdbc.dbaccess.DBError.throwSqlException(DBError.java:179)
	at oracle.jdbc.dbaccess.DBError.throwSqlException(DBError.java:333)
	at oracle.jdbc.driver.OracleConnection.rollback(OracleConnection.java:1380)
	at com.newland.So.Transaction.executeQuery(Transaction.java:107)
	at com.newland.Dao.UserInfoDao.findUser(UserInfoDao.java:184)
	at com.newland.Blo.UserInfoBlo.findUser(UserInfoBlo.java:119)
	at org.apache.jsp.loginAction_jsp._jspService(loginAction_jsp.java:111)
	at org.apache.jasper.runtime.HttpJspBase.service(HttpJspBase.java:70)
	at javax.servlet.http.HttpServlet.service(HttpServlet.java:723)
	at org.apache.jasper.servlet.JspServletWrapper.service(JspServletWrapper.java:388)
	at org.apache.jasper.servlet.JspServlet.serviceJspFile(JspServlet.java:313)
	at org.apache.jasper.servlet.JspServlet.service(JspServlet.java:260)
	at javax.servlet.http.HttpServlet.service(HttpServlet.java:723)
	at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:290)
	at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206)
	at com.newland.So.EncodeFilter.doFilter(EncodeFilter.java:32)
	at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:235)
	at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206)
	at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:233)
	at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:191)
	at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:127)
	at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:103)
	at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:109)
	at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:293)
	at org.apache.coyote.http11.Http11Processor.process(Http11Processor.java:861)
	at org.apache.coyote.http11.Http11Protocol$Http11ConnectionHandler.process(Http11Protocol.java:620)
	at org.apache.tomcat.util.net.JIoEndpoint$Worker.run(JIoEndpoint.java:489)
	at java.lang.Thread.run(Thread.java:744)

解决过程:
出现上面的异常时因为tomcat的conf/context.xml没有加入数据库断开重连配置,配置如下(红字部分):


    
    WEB-INF/web.xml
	
    
    

    
    
    
     validationQuery SELECT COUNT(*) FROM DUAL  
     testOnBorrow true  
     testOnReturn true  
     testWhileIdle true 


配置完成重启还是会出现错误,怎么办呢,考虑用连接池获取连接的方式替代原来的jdbc连接,我选用了C3P0
下面是部分关键代码:
dataSource = new ComboPooledDataSource();
dataSource.setUser(ConnUserName);
dataSource.setPassword(ConnPassWord);
dataSource.setJdbcUrl(ConnUrl);
		
dataSource.setDriverClass("oracle.jdbc.driver.OracleDriver");
dataSource.setInitialPoolSize(initialPoolSize);
dataSource.setMinPoolSize(minPoolSize);
dataSource.setMaxPoolSize(maxPoolSize);
dataSource.setMaxStatements(maxStatements);
dataSource.setMaxIdleTime(maxIdleTime);

//连接池
	        if(dataSource!=null){
	        	conn = dataSource.getConnection();
	        }

用这种方式暂时解决了问题,至少不会出现登录不了系统的情况了

然后接着几天又出现问题了,登录不了了,重新想办法,设置连接池配置,不靠谱,因为IO断了,重连有问题,还是自己改程序吧

添加异常自动重连,以下是initDataSource关键代码,其他数据库连接的简单写法就不写了:
//如果是重连的,获取连接池的连接
			try {
				conn = dataSource.getConnection();
				conn.setAutoCommit(false);
			} catch (SQLException e) {
				e.printStackTrace();
				reConnect();//自动重连
			}
/** 如果初始化数据库失败无限次重连,直到连接成功为止
     * 为了解决异常:java.sql.SQLException: Io 异常: Connection reset by peer: socket write error
     */
public static void reConnect() {
		while (true) {
			if (conn == null) {
				logger.info("-----------------start reinit dataSource-----------------");
				Transaction.initDataSource();
			} else {
				break;
			}
		}
	}

/**
     * 查询数据,conn为空就自动重连
     * @param qstr
     * @return
     * @throws SQLException
     */
public ResultSet executeQuery(String qstr) throws SQLException{
    	ResultSet cResultSet = null;
		try{
			if(conn==null ){
				reConnect();
			}
		    stmt = conn.createStatement();
		    cResultSet = stmt.executeQuery(qstr);
		   // stmt.close();   //zqh 2008-07-28
		}
		catch(SQLException e) {
			stmt.close();
			conn.rollback();
			throw e;
		}
		return cResultSet;
    }
/**
   	 * 数据更新,conn为空就自动重连
   	 * @param qstr
   	 * @throws SQLException
   	 */
    public void executeUpdate(String qstr) throws SQLException{
		try{
			if(conn==null ){
				reConnect();
			}
			stmt = conn.createStatement();
			stmt.executeUpdate(qstr);
			stmt.close();
	    }
	    catch(SQLException e) {
	    	stmt.close();
		    conn.rollback();
		    throw e;
	    }
     }

在系统登录模块异常注入重连机制:
catch(SQLException e){
			e.printStackTrace();
			Transaction.initDataSource();
		}


不知其他人是否有更好的方法来解决此类问题

你可能感兴趣的:(tomcat,tomcat,异常)