2016-09-19 144 views
0

我想检查一些数据库主机是否还活着。 ConfigReader类分析一个xml文件并获取一些数据库主机的列表。 我希望看到这样的日志,如果某些主机不可用:春天AOP异常处理

running check for host:dbhost1 
Some Exception is ... 
running check for host:dbhost2 
host is alive 

等。

但是我看到这个例外,如果主机不活着。应用程序退出而不是记录并抛出异常。

#### running check for host:dbhost1 
Exception in thread "main" java.sql.SQLException: Cannot create PoolableConnectionFactory (I/O-Fehler: The Network Adapter could not establish the connection) 
    at org.apache.commons.dbcp2.BasicDataSource.createPoolableConnectionFactory(BasicDataSource.java:2291) 
    at org.apache.commons.dbcp2.BasicDataSource.createDataSource(BasicDataSource.java:2038) 
    at org.apache.commons.dbcp2.BasicDataSource.getConnection(BasicDataSource.java:1533) 
    at com.csinfra.jdbmon.app.CheckDatabase.runCheckGroup(CheckDatabase.java:108) 

这里是类:

@Component 
public class ScheduleCheck { 
    public ConfigReader configReader; 
    public CheckDatabase checkDatabase; 

    public void runHostCheck() throws Exception { 
     configReader.readConfig(); 
     checkDatabase.setConfigReader(configReader);   
     for(Host host:configReader.getHostMap().values()){    
       System.out.println("#### running check for host:"+host.getId()); 
       checkDatabase.runCheckGroup(host, getCheckFromCheckGroup(host));       
     } 
    } 
} 



@Component 
public class CheckDatabase { 
    public void runCheckGroup(Host host) throws Exception{    
      createConnections(host.getJdbcurl(), host.getJdbcuser(), host.getJdbcpassword(), host.getDriverclassname()); 
      Connection connection_single = jdbcPool.getConnection(); 
      if(connection_single!=null){      
       System.out.println("host is alive"); 
      }       
    } 

    public void createConnections(String url, String username, String password, String driverClassname) throws Exception{ 
      jdbcPool = new BasicDataSource();      
      jdbcPool.setDriverClassName(driverClassname); 
      jdbcPool.setUsername(username); 
      jdbcPool.setUrl(url); 
      jdbcPool.setPassword(password); 
      jdbcPool.setInitialSize(2); 
      jdbcPool.setCacheState(false); 
      jdbcPool.setMaxTotal(2); 
      jdbcPool.setMaxWaitMillis(6000); 
      jdbcPool.setMaxIdle(2); 
      jdbcPool.setDefaultReadOnly(true); 
    } 
} 


@Configurable 
@Aspect 
@Component 
public class AopMethodLogger { 

    private static final Logger LOGGER = RootLogger.getLogger(AopMethodLogger.class); 

    @AfterThrowing(pointcut = "execution(* com.csinfra.app..*.*(..))", throwing = "exception") 
    public void logAfterThrowing(JoinPoint joinPoint, Throwable exception) throws Throwable { 
     LOGGER.debug("Some Exception is "+exception.getLocalizedMessage()); 
     throw exception; 
    } 
} 


<?xml version="1.0" encoding="UTF-8"?> 
<beans xmlns="http://www.springframework.org/schema/beans" 
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
    xmlns:context="http://www.springframework.org/schema/context" 
    xmlns:tx="http://www.springframework.org/schema/tx" 
    xmlns:aop="http://www.springframework.org/schema/aop" 
    xsi:schemaLocation="http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop-3.2.xsd 
     http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd 
     http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx-3.2.xsd 
     http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-3.2.xsd"> 

    <aop:aspectj-autoproxy proxy-target-class="true" /> 
    <context:component-scan base-package="com.csinfra.app /> 

    <bean id="aopMethod" class="com.csinfra.app.log.AopMethodLogger" /> 

    <bean id="scheduleCheck" class="com.csinfra.app.ScheduleCheck"> 
     <property name="configReader" ref="configReader" /> 
     <property name="checkDatabase" ref="checkDatabase" /> 
    </bean> 

    <bean id="checkDatabase" class="com.csinfra.app.CheckDatabase"> 
    </bean> 

</beans> 

回答

0

CheckDatabase.runCheckGroup抛出一个异常,它没有被处理,这就是为什么在应用程序退出。 环绕您的​​通话使用try/catch来runCheckGroup和记录异常:

try{ 
    checkDatabase.runCheckGroup(host, getCheckFromCheckGroup(host));    
} catch(Exception e){ 
    System.out.println("Exception occured :"+e); 
} 

到数据库连接的数量是有限的,因此,创建一个新的连接,只是为了检查数据库是活似乎相当昂贵。 这可能是更好地让春天注入所有可用的数据源:

@Autowire 
List<DataSource>dataSources; 

这还具有以下优点自动检查所有配置的数据源,无需额外配置。

而不是叠代的,每个做类似

new JdbcTemplate(dataSource).queryForInt("SELECT 1") 

,以检查它的活着。

+0

嗨Stefan,我想抛出异常,并在AopMethodLogger类中开始一些纠正措施。是否有可能在CheckDatabase和AopMethodLogger类中捕获异常? – user2683906