繁体   English   中英

从命令行运行时混合Java和Kotlin代码的ClassNotFoundException

[英]ClassNotFoundException for mixed java and kotlin code when running from command line

我感慨JavaKotlin中,我想从运行演示项目的代码command line 对于仅Java,我可以使用java -jar foo.jar运行该程序,但是当我使用Kotlin代码中的任何类时, 它将生成java.lang.NoClassDefFoundError: kotlin/jvm/internal/Intrinsics

我尝试了不同的解决方案,并检查了jar文件。 它包含两个类,但我猜jar中缺少kotlin-runtime

这是build.gradle文件

plugins {
    id 'java-library'
    id 'org.jetbrains.kotlin.jvm'
}

sourceSets {
    main.java.srcDirs += 'src/main/kotlin/'
    test.java.srcDirs += 'src/test/kotlin/'
}

dependencies {
    implementation "org.jetbrains.kotlin:kotlin-stdlib-jdk8"
    testImplementation 'junit:junit:4.12'
}

jar {
    manifest {
        attributes 'Main-Class': 'com.mallaudin.App'
    }
    from {
        configurations.compile.collect {
            it.isDirectory()? it: zipTree(it)
        }
    }
}

生成的jar文件的内容

.
├── com
│   └── mallaudin
│       ├── App.class
│       └── User.class
└── META-INF
    ├── basics.kotlin_module
    └── MANIFEST.MF

MANIFEST.MF内容

Manifest-Version: 1.0
Main-Class: com.mallaudin.App

运行jar表单命令行时出现异常

allaudin@geek ~/Desktop/KotlinLab (master) $ java -jar basics/build/libs/basics.jar 
Exception in thread "main" java.lang.NoClassDefFoundError: kotlin/jvm/internal/Intrinsics
    at com.mallaudin.User.<init>(User.kt)
    at com.mallaudin.App.main(App.java:5)
Caused by: java.lang.ClassNotFoundException: kotlin.jvm.internal.Intrinsics
    at java.base/jdk.internal.loader.BuiltinClassLoader.loadClass(BuiltinClassLoader.java:583)
    at java.base/jdk.internal.loader.ClassLoaders$AppClassLoader.loadClass(ClassLoaders.java:190)
    at java.base/java.lang.ClassLoader.loadClass(ClassLoader.java:499)
    ... 2 more

问题在于您制作胖子的方式。 当你使用更近,并建议implementation对你的依赖范围,你只增加了脂肪罐子的内容compile配置。

您应该用运行时组件的完整集合runtimeClasspath替换胖子罐中要使用的配置。

那是:

jar {
  manifest {
    attributes 'Main-Class': 'com.mallaudin.App'
  }
  from {
    configurations.runtimeClasspath.collect {
      it.isDirectory()? it: zipTree(it)
    }
  }
}  

查看文档以了解Java项目的不同依赖项配置。

因此,我找到了解决方案。 build.gradle文件中, 我已将implementation配置替换为compile ,并且现在可以运行了。 我相信它也应该与implementation工作,但事实并非如此。 现在jar看起来像这样

.
├── com
├── kotlin
├── META-INF
└── org

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM