2011-04-08 20 views
2

我想建立一個簡單的JDBC Spring模板的應用程序,我使用的web框架是檢票口,並在碼頭6 Web服務器(通過碼頭的Maven插入)。另外,我正在用Eclipse構建應用程序。問題,在網絡環境下的NoClassDefFoundError錯誤春/檢票/德比/碼頭

出於某種原因,我正在與德比的JDBC類的NoClassDefFoundError。我假設我會得到一個沒有找到的類未找到的異常,所以我猜猜別的事情正在發生。 derby類是類路徑的一部分,即WEB-INF/lib目錄。你認爲這個問題是什麼?

我對這個問題的看法:它不是一個「在類路徑中找不到的jar」錯誤,但更多的是Java或Spring動態加載該類以及何時加載它的問題。

我使用Eclipse作爲開發工具,但它可能不是問題的一部分。我仍然在命令行上使用Maven並獲得相同的問題。

以下是錯誤:

WicketMessage:

java.lang.NoClassDefFoundError: Could not initialize class org.apache.derby.jdbc.EmbeddedDriver 
    at java.lang.Class.forName0(Native Method) 
    at java.lang.Class.forName(Class.java:169) 
    at org.apache.commons.dbcp.BasicDataSource.createDataSource(BasicDataSource.java:1130) 
    at org.apache.commons.dbcp.BasicDataSource.getConnection(BasicDataSource.java:880) 
    at org.springframework.jdbc.datasource.DataSourceUtils.doGetConnection(DataSourceUtils.java:113) 
    at org.springframework.jdbc.datasource.DataSourceUtils.getConnection(DataSourceUtils.java:79) 
    at org.springframework.jdbc.core.JdbcTemplate.execute(JdbcTemplate.java:577) 
    at org.springframework.jdbc.core.JdbcTemplate.execute(JdbcTemplate.java:619) 
    at wicketspring.easy.jdbc.JdbcWicketSpringHandler.data(JdbcWicketSpringHandler.java:39) 
    at WICKET_wicketspring.easy.jdbc.JdbcWicketSpringHandler$$FastClassByCGLIB$$f1187cb6.invoke(<generated>) 
    at net.sf.cglib.proxy.MethodProxy.invoke(MethodProxy.java:191) 
    at org.apache.wicket.proxy.LazyInitProxyFactory$CGLibInterceptor.intercept(LazyInitProxyFactory.java:319) 
    at WICKET_wicketspring.easy.jdbc.JdbcWicketSpringHandler$$EnhancerByCGLIB$$e8f0e174.data(<generated>) 
    at wicketspring.easy.HomePage.<init>(HomePage.java:91) 
    at wicketspring.easy.HomePage.<init>(HomePage.java:47) 

這裏是applicationContext.xml中:使用構造公共wicketspring.easy.HomePage()

根本原因無法實例頁面適用於春季:

<beans> 
    <bean id="dataSource" class="org.apache.commons.dbcp.BasicDataSource"> 
     <property name="driverClassName" value="org.apache.derby.jdbc.EmbeddedDriver" /> 
     <property name="url"><value>jdbc:derby:wicketspringdb</value></property> 
     <property name="username"><value></value></property> 
     <property name="password"><value></value></property> 
    </bean> 
    <bean id="jdbcTemplate" class="org.springframework.jdbc.core.JdbcTemplate"> 
     <property name="dataSource" ref="dataSource" /> 
    </bean> 
</beans> 
<beans> 
    <import resource="classpath:common.xml"/> 
    <bean id="jdbcHandler" class=wicketspring.easy.jdbc.JdbcWicketSpringHandler"> 
     <property name="jdbcTemplate" ref="jdbcTemplate" /> 
    </bean> 

</beans> 


... 
Another stack trace system out. 

Page.java:74) - At [2b] -- java.lang.NoClassDefFoundError: Could not initialize class org.apache.derby.jdbc.EmbeddedDriver 
java.lang.NoClassDefFoundError: Could not initialize class org.apache.derby.jdbc.EmbeddedDriver 
     at wicketspring.easy.HomePage.<init>(HomePage.java:72) 
     at wicketspring.easy.HomePage.<init>(HomePage.java:47) 
     at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method) 
     at sun.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java: 
39) 
     at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorIm 
pl.java:27) 

...

這裏是java代碼,代碼編譯和我可以打印出類但我不能實例化它。奇怪?

Java代碼:

package wicketspring.easy; 

import java.util.List; 

import org.apache.wicket.Application; 
import org.apache.wicket.PageParameters; 
import org.apache.wicket.markup.html.WebPage; 
import org.apache.wicket.markup.html.basic.Label; 
import org.apache.wicket.markup.html.list.ListItem; 
import org.apache.wicket.markup.html.list.ListView; 
import org.apache.wicket.model.CompoundPropertyModel; 
import org.apache.wicket.proxy.IProxyTargetLocator; 
import org.apache.wicket.proxy.LazyInitProxyFactory; 
import org.slf4j.Logger; 
import org.slf4j.LoggerFactory; 

import model.LoadableDetachableList; 
import model.SelectionOptionBean; 
import wicketspring.easy.jdbc.JdbcWicketSpringHandler; 
import wicketspring.easy.service.IStateListService; 
import wicketspring.easy.service.StateListServiceImpl; 

import org.apache.derby.jdbc.EmbeddedDriver; 

public class HomePage extends WebPage { 

    private final JdbcWicketSpringHandler jdbcWicketSpringHandler; 

    public HomePage(final PageParameters parameters) { 

     super(parameters);   
     jdbcWicketSpringHandler = (JdbcWicketSpringHandler) LazyInitProxyFactory.createProxy(JdbcWicketSpringHandler.class, 
       new IProxyTargetLocator() { 
        private static final long serialVersionUID = 1L; 
        public Object locateProxyTarget() { 
         return ((WicketApplication) Application.get()).context().getBean("jdbcHandler"); 
        } 
       });  

     /// WEIRD BECAUSE IT REACHES THIS POINT!!! 
     LOGGER.debug("At [1] -- " + EmbeddedDriver.class); 
     try { 
      LOGGER.debug("At [2] -- " + new org.apache.derby.jdbc.EmbeddedDriver()); 
     } catch (NoClassDefFoundError ne) { 
       // STACK TRACE ERROR HERE!!!! 
      LOGGER.debug("At [2b] -- " + ne); 
      ne.printStackTrace(); 
     } catch (Exception e) { 
      LOGGER.debug("At [2] -- " + e); 
      e.printStackTrace(); 
     } 
     try { 

      LOGGER.debug("At -- " + Class.forName("org.apache.derby.jdbc.EmbeddedDriver"));  
     } catch (NoClassDefFoundError ne) { 
      LOGGER.debug("At [3b] -- " + ne); 
      ne.printStackTrace(); 
     } catch (Exception e) { 
      LOGGER.debug("At [3] -- " + e); 
      e.printStackTrace(); 
     } 

     /// ERROR FOR STACKOVERFLOW IS GENERATED FROM THIS LINE!!!! 
     LOGGER.debug("At HomePage - jdbcHandler [3]: " + jdbcWicketSpringHandler.toStringJdbcTemplate()); 
     LOGGER.debug("At HomePage - jdbcHandler [3]: " + jdbcWicketSpringHandler.data());   

     ... 

} // End of Class // 

編輯: 我可能會丟失一個jar文件是春天JDBC或二溴氯丙烷的依賴。

這裏是我的WEB-INF/lib目錄列表:

antlr-2.7.6.jar 
aopalliance-1.0.jar 
avalon-framework-4.1.3.jar 
axis-1.4.jar 
axis-jaxrpc-1.4.jar 
cglib-nodep-2.2.jar 
commons-collections-3.1.jar 
commons-dbcp-1.2.2.jar 
commons-logging-1.1.jar 
commons-pool-1.3.jar 
derby-10.6.1.0.jar 
dom4j-1.6.1.jar 
hibernate-core-3.5.1-Final.jar 
jetty-6.1.4.jar 
jetty-management-6.1.4.jar 
jetty-util-6.1.4.jar 
jta-1.1.jar 
log4j-1.2.14.jar 
logkit-1.0.1.jar 
mx4j-3.0.1.jar 
mx4j-tools-3.0.1.jar 
servlet-api-2.5-6.1.4.jar 
servlet-api-2.5.jar 
slf4j-api-1.5.8.jar 
slf4j-log4j12-1.4.2.jar 
spring-2.5.6.jar 
spring-aop-2.5.6.jar 
spring-beans-2.5.6.jar 
spring-context-2.5.6.jar 
spring-core-2.5.6.jar 
spring-jdbc-2.5.6.jar 
spring-test-2.5.6.jar 
spring-tx-2.5.6.jar 
testRunWrapper-1.0.0.jar 
wicket-1.4.13.jar 
wicket-ioc-1.4.13.jar 
wicket-spring-1.4.13.jar 
xml-apis-1.0.b2.jar 
+1

Eclipse未正確部署項目。看起來像'derby.jar'沒有被部署到正確的位置(或者可能根本就沒有)。在SO上已經有一個'NoClassDefFoundError'和'ClassNotFoundException'的問題。 – 2011-04-08 16:24:59

+0

我使用Eclipse進行開發,但在命令行上使用maven。 Derby包含在目標/ WEB-INF/lib/derby.jar和WebContent/WEB-INF/lib/derby.jar中。我認爲這是彈簧加載豆時更多的問題。 – 2011-04-08 16:26:39

回答

1

所以「無法初始化類org.apache.derby.jdbc.EmbeddedDriver」誤差實際上是其他一些不太明顯的類加載問題的主要症狀。

我使用碼頭作爲Web服務器和Spring作爲下的Java6的框架。

我相信有一個類加載的問題,涉及到MBeanServer類。

而且我確實忽略了發生在啓動時出現錯誤:「致:java.lang.LinkageError的:裝載機約束衝突:裝載機(ORG/mortbay的實例/碼頭/ Web應用程序/ WebAppClassLoader)先前啓動的加載針對不同類型(java.lang.ClassLoader.defineClass1)(本地方法) 在java.lang.ClassLoader.defineClassCond(ClassLoader.java:632) at java.lang.ClassLoader.defineClass(ClassLoader。 java:616) at java.security.SecureClassLoader.defineClass(SecureClassLoader.java:141)「

我在我的WEB-INF/lib目錄中搜索了這個類。它被包含在mx4j:jar中。 Mx4j是jetty-management.jar的依賴項。我並不真的需要碼頭管理,所以我從我的POM文件中刪除了該引用。

基本上包含MBeanServer(來自mx4j)導致某種類加載問題,其中org.apache.derby.jdbc.EmbeddedDriver無法正確加載。我從我的web應用程序中刪除它,並且應用程序開始正常工作。

+0

很高興你能用它! – 2011-04-11 13:59:22

+0

這個錯誤非常具有誤導性,我在考慮classpath問題。 – 2011-04-11 17:46:34

-1

你確定你的derby.jar包含org.apache.derby.jdbc.EmbeddedDriver類?你可能想檢查你是否有正確的版本。

如果您正在使用Maven來打包應用程序,然後將罐子名字最終被derby.jar與連接到它沒有版本號很奇怪。

+0

WEB-INF/lib/derby-10.6.1.0.jar我會得到一個ClassNotFound異常。另外,我在運行時有一個工具來檢查一個類是否可用。該類在運行時可用,但出於某種原因,I或Spring無法實例化它。 – 2011-04-08 17:20:37

+0

不確定爲什麼你會在這種情況下進行投票,檢查以確保你有正確的版本 - 並且該類存在 - 是此類問題的有效的第一步。 – 2011-04-08 19:45:41

+0

我說我有正確的版本和類存在。 – 2011-04-08 20:06:41

0

有時候這些錯誤是因爲你在你的classpath中有兩次Derby。對於現代JDK,Derby的驅動程序是「自動加載的」,這意味着JDK將在類路徑中查找JDBC驅動程序並自動加載它們。所以你可能會檢查你的系統類路徑以及你的應用程序庫;也許你有第二個Derby的副本隱藏在路徑的某個地方,並且例外情況是試圖告訴你兩個版本的Derby有衝突。

+0

這當然有可能。 – 2011-04-08 19:23:16

3

消息Could not initialize class org.apache.derby.jdbc.EmbeddedDriver意味着,在這一點上,JVM已經嘗試和失敗,初始化這個類。

的JVM會失敗,如果一個異常被拋出和類的靜態初始化中沒有抓到初始化類。唯一的理由,JVM將試圖初始化EmbeddedDriver類不止一次將是:

  • 一些異常初始化類被拋出,這個例外是在別的地方捕獲,並且計劃繼續,
  • 一些例外初始化該類被拋出,但隨後的程序進入finally塊,這finally塊中的JVM試圖再次加載類。

EmbeddedDriver的靜態初始化程序(source)調用boot()方法。但是,這種方法會調用其他代碼的一小部分,因此很難確定問題出在哪裏。我有一個看看一些org.apache.commons.dbcp.BasicDataSourcesource的,但似乎在你的堆棧跟蹤的行號不與源一致。我不知道你正在使用哪個版本的commons-dbcp。

如果你有沒有其他的輸出信息,也沒有蹤跡去,你最好的選擇可能是德比的源連接到您的調試器,通過它一步,看看發生了什麼事情。


順便說一句,這是完全可能的「打印」尚未初始化類。考慮下面的類:

class St1 { 
    static { 
     System.out.println("In static initializer"); 
    } 
} 

public class St2 { 
    public static void main(String[] args) { 
     System.out.println(St1.class); 
     System.out.println(new St1()); 
    } 
} 

當我運行St2類,我得到下面的輸出:

 
class St1 
In static initializer 
[email protected] 
+0

好評。這就是我的想法。這很有趣,因爲它沒有抱怨公共池沒有被添加,我認爲這是dbcp的依賴。我添加了commons-pool,但仍然出現錯誤。我會繼續挖掘。我應該擁有所有的依賴關係。 – 2011-04-08 19:22:40