【问题标题】:Clojure Leiningen compile error with multiple projects - ClassNotFoundExceptionClojure Leiningen 编译多个项目时出错 - ClassNotFoundException
【发布时间】:2013-10-15 21:24:19
【问题描述】:

我有一个 clojure 库旋转,由我自己的项目 api 使用。我有第二个项目叫做 pipeline,它使用 api,并且不直接接触旋转。

我已尝试清除我的 .lein 文件夹,并在编译前始终使用 lein clean。

我看到了什么:

  1. Rotary 编译和安装正确。我可以从两个 repl 中使用它 和独立的 jars。
  2. Api 可以正确编译和安装。使用 repl 和独立 jar 中的旋转工作的函数。

如果我从 api 中注释掉旋转库,那么使用 api 的管道项目可以正常编译,并且所有非旋转功能都可以正常工作。这一切对我来说都很有意义。

但是,当我在 api 中保留旋转时,在我安装它之后,管道项目在编译时出错。

我非常不明白为什么 api 会与旋转一起使用,而管道会出错,尤其是当我可以通过注释掉它来将其缩小到旋转时。如果旋转代码有问题,那么我预计旋转 / api 无法编译,特别是因为管道不直接使用旋转。

附上错误,取自管道项目lein compile命令:

Exception in thread "main" java.lang.ExceptionInInitializerError, compiling:(channel.clj:1)
at clojure.lang.Compiler$InvokeExpr.eval(Compiler.java:3387)
at clojure.lang.Compiler.compile1(Compiler.java:7035)
at clojure.lang.Compiler.compile1(Compiler.java:7025)
at clojure.lang.Compiler.compile(Compiler.java:7097)
at clojure.lang.RT.compile(RT.java:387)
at clojure.lang.RT.load(RT.java:427)
at clojure.lang.RT.load(RT.java:400)
at clojure.core$load$fn__4890.invoke(core.clj:5415)
at clojure.core$load.doInvoke(core.clj:5414)
at clojure.lang.RestFn.invoke(RestFn.java:408)
at clojure.core$load_one.invoke(core.clj:5227)
at clojure.core$load_lib.doInvoke(core.clj:5264)
at clojure.lang.RestFn.applyTo(RestFn.java:142)
at clojure.core$apply.invoke(core.clj:603)
at clojure.core$load_libs.doInvoke(core.clj:5298)
at clojure.lang.RestFn.applyTo(RestFn.java:137)
at clojure.core$apply.invoke(core.clj:603)
at clojure.core$require.doInvoke(core.clj:5381)
at clojure.lang.RestFn.invoke(RestFn.java:619)
at pipeline.core$loading__4784__auto__.invoke(core.clj:1)
at clojure.lang.AFn.applyToHelper(AFn.java:159)
at clojure.lang.AFn.applyTo(AFn.java:151)
at clojure.lang.Compiler$InvokeExpr.eval(Compiler.java:3382)
at clojure.lang.Compiler.compile1(Compiler.java:7035)
at clojure.lang.Compiler.compile1(Compiler.java:7025)
at clojure.lang.Compiler.compile(Compiler.java:7097)
at clojure.lang.RT.compile(RT.java:387)
at clojure.lang.RT.load(RT.java:427)
at clojure.lang.RT.load(RT.java:400)
at clojure.core$load$fn__4890.invoke(core.clj:5415)
at clojure.core$load.doInvoke(core.clj:5414)
at clojure.lang.RestFn.invoke(RestFn.java:408)
at clojure.core$load_one.invoke(core.clj:5227)
at clojure.core$compile$fn__4895.invoke(core.clj:5426)
at clojure.core$compile.invoke(core.clj:5425)
at user$eval7.invoke(NO_SOURCE_FILE:1)
at clojure.lang.Compiler.eval(Compiler.java:6511)
at clojure.lang.Compiler.eval(Compiler.java:6501)
at clojure.lang.Compiler.eval(Compiler.java:6477)
at clojure.core$eval.invoke(core.clj:2797)
at clojure.main$eval_opt.invoke(main.clj:297)
at clojure.main$initialize.invoke(main.clj:316)
at clojure.main$null_opt.invoke(main.clj:349)
at clojure.main$main.doInvoke(main.clj:427)
at clojure.lang.RestFn.invoke(RestFn.java:421)
at clojure.lang.Var.invoke(Var.java:419)
at clojure.lang.AFn.applyToHelper(AFn.java:163)
at clojure.lang.Var.applyTo(Var.java:532)
at clojure.main.main(main.java:37)
Caused by: java.lang.ExceptionInInitializerError
at java.lang.Class.forName0(Native Method)
at java.lang.Class.forName(Class.java:249)
at clojure.lang.RT.loadClassForName(RT.java:2056)
at clojure.lang.RT.load(RT.java:419)
at clojure.lang.RT.load(RT.java:400)
at clojure.core$load$fn__4890.invoke(core.clj:5415)
at clojure.core$load.doInvoke(core.clj:5414)
at clojure.lang.RestFn.invoke(RestFn.java:408)
at clojure.core$load_one.invoke(core.clj:5227)
at clojure.core$load_lib.doInvoke(core.clj:5264)
at clojure.lang.RestFn.applyTo(RestFn.java:142)
at clojure.core$apply.invoke(core.clj:603)
at clojure.core$load_libs.doInvoke(core.clj:5298)
at clojure.lang.RestFn.applyTo(RestFn.java:137)
at clojure.core$apply.invoke(core.clj:603)
at clojure.core$require.doInvoke(core.clj:5381)
at clojure.lang.RestFn.invoke(RestFn.java:436)
at api.db.dynamo$loading__4784__auto__.invoke(dynamo.clj:1)
at api.db.dynamo__init.load(Unknown Source)
at api.db.dynamo__init.<clinit>(Unknown Source)
at java.lang.Class.forName0(Native Method)
at java.lang.Class.forName(Class.java:249)
at clojure.lang.RT.loadClassForName(RT.java:2056)
at clojure.lang.RT.load(RT.java:419)
at clojure.lang.RT.load(RT.java:400)
at clojure.core$load$fn__4890.invoke(core.clj:5415)
at clojure.core$load.doInvoke(core.clj:5414)
at clojure.lang.RestFn.invoke(RestFn.java:408)
at clojure.core$load_one.invoke(core.clj:5227)
at clojure.core$load_lib.doInvoke(core.clj:5264)
at clojure.lang.RestFn.applyTo(RestFn.java:142)
at clojure.core$apply.invoke(core.clj:603)
at clojure.core$load_libs.doInvoke(core.clj:5298)
at clojure.lang.RestFn.applyTo(RestFn.java:137)
at clojure.core$apply.invoke(core.clj:603)
at clojure.core$require.doInvoke(core.clj:5381)
at clojure.lang.RestFn.invoke(RestFn.java:457)
at api.db.core$loading__4784__auto__.invoke(core.clj:1)
at api.db.core__init.load(Unknown Source)
at api.db.core__init.<clinit>(Unknown Source)
at java.lang.Class.forName0(Native Method)
at java.lang.Class.forName(Class.java:249)
at clojure.lang.RT.loadClassForName(RT.java:2056)
at clojure.lang.RT.load(RT.java:419)
at clojure.lang.RT.load(RT.java:400)
at clojure.core$load$fn__4890.invoke(core.clj:5415)
at clojure.core$load.doInvoke(core.clj:5414)
at clojure.lang.RestFn.invoke(RestFn.java:408)
at clojure.core$load_one.invoke(core.clj:5227)
at clojure.core$load_lib.doInvoke(core.clj:5264)
at clojure.lang.RestFn.applyTo(RestFn.java:142)
at clojure.core$apply.invoke(core.clj:603)
at clojure.core$load_libs.doInvoke(core.clj:5298)
at clojure.lang.RestFn.applyTo(RestFn.java:137)
at clojure.core$apply.invoke(core.clj:603)
at clojure.core$require.doInvoke(core.clj:5381)
at clojure.lang.RestFn.invoke(RestFn.java:436)
at api.thing$loading__4784__auto__.invoke(thing.clj:1)
at api.thing__init.load(Unknown Source)
at api.thing__init.<clinit>(Unknown Source)
at java.lang.Class.forName0(Native Method)
at java.lang.Class.forName(Class.java:249)
at clojure.lang.RT.loadClassForName(RT.java:2056)
at clojure.lang.RT.load(RT.java:419)
at clojure.lang.RT.load(RT.java:400)
at clojure.core$load$fn__4890.invoke(core.clj:5415)
at clojure.core$load.doInvoke(core.clj:5414)
at clojure.lang.RestFn.invoke(RestFn.java:408)
at clojure.core$load_one.invoke(core.clj:5227)
at clojure.core$load_lib.doInvoke(core.clj:5264)
at clojure.lang.RestFn.applyTo(RestFn.java:142)
at clojure.core$apply.invoke(core.clj:603)
at clojure.core$load_libs.doInvoke(core.clj:5298)
at clojure.lang.RestFn.applyTo(RestFn.java:137)
at clojure.core$apply.invoke(core.clj:603)
at clojure.core$require.doInvoke(core.clj:5381)
at clojure.lang.RestFn.invoke(RestFn.java:436)
at pipeline.jobs.channel$loading__4784__auto__.invoke(channel.clj:1)
at clojure.lang.AFn.applyToHelper(AFn.java:159)
at clojure.lang.AFn.applyTo(AFn.java:151)
at clojure.lang.Compiler$InvokeExpr.eval(Compiler.java:3382)
... 48 more

Caused by: java.lang.ClassNotFoundException: com.amazonaws.services.dynamodbv2.model.BatchGetItemResult
at java.net.URLClassLoader$1.run(URLClassLoader.java:202)
at java.security.AccessController.doPrivileged(Native Method)
at java.net.URLClassLoader.findClass(URLClassLoader.java:190)
at java.lang.ClassLoader.loadClass(ClassLoader.java:306)
at sun.misc.Launcher$AppClassLoader.loadClass(Launcher.java:301)
at java.lang.ClassLoader.loadClass(ClassLoader.java:247)
at java.lang.Class.forName0(Native Method)
at java.lang.Class.forName(Class.java:171)
at rotary.client__init.__init0(Unknown Source)
at rotary.client__init.<clinit>(Unknown Source)
... 129 more

【问题讨论】:

    标签: java clojure compilation leiningen


    【解决方案1】:

    当我尝试加载依赖项的多个版本时会发生这种情况,因为我的两个依赖项依次依赖于具有不同版本的同一个库。您可以通过运行来检查这一点:

    lein deps :tree
    

    然后查找重复的依赖项并将exclude 语句添加到其中一个依赖项,因此只有一个依赖项试图满足要求。

    [org.jclouds.driver/jclouds-slf4j "1.5.5"                  
      :exclusions [org.slf4j/slf4j-api]]
    

    我也曾在希望您提供填充特定界面的库的项目中看到这一点,但我使用了错误的版本。例如,使用带有错误版本的 jClouds 的托盘,尽管这比重叠依赖项要少得多。
    如果这些都不是,那么很有可能freenode.net 上#clojure irc 频道中的某个人将能够引导您完成调试。

    【讨论】:

    • 感谢您的提示。您能指出重复的依赖项是什么样的吗?我可能已经发现了问题,在 API 和旋转项目中,我有以下依赖项:[rotary "0.4.3"] [com.amazonaws/aws-java-sdk "1.5.8"] 并且在管道中,旋转不调用 java-sdk: [com.cemerick/bandalore "0.0.3"] [com.amazonaws/aws-java-sdk "1.3.21.1"] 所以这似乎是一个不同的项目但是我怎么能让他们都使用不同的java的版本?我必须修补bandalore 才能使用最新版本吗?
    • 使用需要不同版本的多个项目确实很棘手,幸运的是几乎总是不必要的。首先尝试为 [com.cemerick/bandalore "0.0.3"] 添加排除项:exclusions [com.amazonaws/aws-java-sdk "1.3.21.1"]。在大多数情况下,我已经解决了这个问题。
    • 要回答您上述评论的问题,重复的依赖项看起来就是这样。
    • 感谢您的帮助!我正在查看文档,但这是否意味着如果我将bandalore 排除为dep,我必须修补bandalore 才能使用1.5.8?因此,如果 bandalore 可以在不打补丁的情况下与 1.5.8 一起工作,这可能可以工作,但否则这不会中断并需要一种方法来为每个依赖项指定两个版本的 aws-java-sdk?跨度>
    • 是的,您理解正确。有些人将此称为“依赖地狱”,这真的很令人沮丧。有一些方法可以使用类加载器来解决它,尽管它不是为了装腔作势;-)
    猜你喜欢
    • 1970-01-01
    • 2022-12-24
    • 2017-01-07
    • 1970-01-01
    • 2011-10-31
    • 2018-12-30
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多