ibatis sqlmapclient加载问题

时间:2014-05-13 06:44:30

标签: xml spring mybatis ibatis sqlmap

我在spring_config.xml中加载sqlmapclient,如下所示

<bean id="sqlMapClient"
        class="org.springframework.orm.ibatis.SqlMapClientFactoryBean">
        <property name="configLocations" value="com/de/test/SqlMapConfig.xml"/>
        <property name="dataSource" ref="dataSource" />
    </bean>

但该属性未加载sqlMapConfig.xml。我的sqlMapConfig.xml是

<sqlMapConfig>

<settings
cacheModelsEnabled="true"
enhancementEnabled="true"
lazyLoadingEnabled="true"
maxRequests="32"
maxSessions="10"
maxTransactions="5"
useStatementNamespaces="true"
/>

    <!--Addind Resource files -->
    <sqlMap resource="emerg_ibatis_services.xml"/>
    <sqlMap resource="external_ibatis_services.xml"/>

</sqlMapConfig>

抛出异常,如下所示,

Exception in thread "main" org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'sqlMapClient' defined in class path resource [irams_de_spring_config.xml]: Invocation of init method failed; nested exception is java.lang.ExceptionInInitializerError
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.initializeBean(AbstractAutowireCapableBeanFactory.java:1337)
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:476)
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory$1.run(AbstractAutowireCapableBeanFactory.java:412)
    at java.security.AccessController.doPrivileged(Native Method)
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:383)
    at org.springframework.beans.factory.support.AbstractBeanFactory$1.getObject(AbstractBeanFactory.java:276)
    at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:222)
    at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:273)
    at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:175)
    at org.springframework.beans.factory.support.DefaultListableBeanFactory.preInstantiateSingletons(DefaultListableBeanFactory.java:479)
    at org.springframework.context.support.AbstractApplicationContext.finishBeanFactoryInitialization(AbstractApplicationContext.java:716)
    at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:377)
    at org.springframework.context.support.ClassPathXmlApplicationContext.<init>(ClassPathXmlApplicationContext.java:139)
    at org.springframework.context.support.ClassPathXmlApplicationContext.<init>(ClassPathXmlApplicationContext.java:83)
    at com.bt.irams.de.test.Test.main(Test.java:32)
Caused by: java.lang.ExceptionInInitializerError
    at com.ibatis.sqlmap.engine.builder.xml.SqlMapConfigParser.<init>(SqlMapConfigParser.java:58)
    at com.ibatis.sqlmap.engine.builder.xml.SqlMapConfigParser.<init>(SqlMapConfigParser.java:45)
    at org.springframework.orm.ibatis.SqlMapClientFactoryBean.buildSqlMapClient(SqlMapClientFactoryBean.java:334)
    at org.springframework.orm.ibatis.SqlMapClientFactoryBean.afterPropertiesSet(SqlMapClientFactoryBean.java:291)
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.invokeInitMethods(AbstractAutowireCapableBeanFactory.java:1368)
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.initializeBean(AbstractAutowireCapableBeanFactory.java:1334)
    ... 14 more
Caused by: java.lang.RuntimeException: Error creating logger for class class com.ibatis.sqlmap.engine.impl.SqlMapClientImpl.  Cause: java.lang.NullPointerException
    at com.ibatis.common.logging.LogFactory.getLog(LogFactory.java:33)
    at com.ibatis.sqlmap.engine.impl.SqlMapClientImpl.<clinit>(SqlMapClientImpl.java:40)
    ... 20 more
Caused by: java.lang.NullPointerException
    at com.ibatis.common.logging.LogFactory.getLog(LogFactory.java:31)
    ... 21 more

此代码导致什么问题?我正在使用ibatis 2.3.0

1 个答案:

答案 0 :(得分:0)

这是SqlMapClientFactoryBean的source code。如果注意堆栈跟踪,可以看到以下几行:

at com.ibatis.sqlmap.engine.builder.xml.SqlMapConfigParser.<init>(SqlMapConfigParser.java:58)
at com.ibatis.sqlmap.engine.builder.xml.SqlMapConfigParser.<init>(SqlMapConfigParser.java:45)
at org.springframework.orm.ibatis.SqlMapClientFactoryBean.buildSqlMapClient(SqlMapClientFactoryBean.java:334)
at org.springframework.orm.ibatis.SqlMapClientFactoryBean.afterPropertiesSet(SqlMapClientFactoryBean.java:291)

SqlMapClientFactoryBean中第334行(以及之前的几行)的源代码是:

if (ObjectUtils.isEmpty(configLocations)) {
        throw new IllegalArgumentException("At least 1 'configLocation' entry is required");
    }

    SqlMapClient client = null;
    SqlMapConfigParser configParser = new SqlMapConfigParser();

在创建SqlMapConfigParser的源代码行之前(堆栈跟踪中的第334行),有一个if语句不会失败(否则你会看到IllegalArgumentException而不是NullPointerException {1}})。所以,configLocations没有任何问题。问题出在iBatis自己的代码中,由于iBatis中的日志记录设置,甚至无法加载文件。

首先调试初始化代码:在LogFactory class的第12行插入一个断点,看看com.ibatis.common.resources.Resources使用的类加载器是否有任何问题,为什么找不到这些LogFactory中的类:

   tryImplementation("org.apache.commons.logging.LogFactory", "com.ibatis.common.logging.jakarta.JakartaCommonsLoggingImpl");
   tryImplementation("org.apache.log4j.Logger", "com.ibatis.common.logging.log4j.Log4jImpl");
   tryImplementation("java.util.logging.Logger", "com.ibatis.common.logging.jdk14.Jdk14LoggingImpl");
   tryImplementation("java.lang.Object", "com.ibatis.common.logging.nologging.NoLoggingImpl");

也许你的类路径中有多个iBatis jar,或者你的类路径中没有iBatis,我不知道。并且很难从堆栈跟踪中分辨出来,因为iBatis代码会隐藏在发生类加载问题时可能抛出的任何异常:

try {
      Resources.classForName(testClassName);
      Class implClass = Resources.classForName(implClassName);
      logConstructor = implClass.getConstructor(new Class[]{Class.class});
} catch (Throwable t) {
}