经过一周的搜索,我找到了为什么我的spring项目无法启动的答案,我自己发现了这个问题,我使用kotlin创建了jpa实体类,这应该是允许的(我在互联网上看到了多个示例),但在我的例子中失败了。
为了展示一个示例,我创建了两个文件,都用自动生成的id和一个字符串描述同一个实体bean,一个文件是纯java,一个文件是kotlin
java版本:
@Entity
public class Example {
@Id
@GeneratedValue
Long Id;
String name;
public Example() {} //for jpa
public Example(Long Id, String name) {
this.Id = Id;
this.name = name;
}
}
它工作正常,应用程序启动时没有问题。
现在有一个kotlin版本:
@Entity
open class Example(@Id @GeneratedValue var Id : Long,
var name : String){
}
现在尝试运行应用程序失败,出现了一个通用的java.lang.noclassdeffounderror,它来自另一个试图使用示例类的类(当然,我不会同时保留两个版本)。我也知道现在它不能单独工作,因为不需要arg构造函数,但它甚至还没有检测到类!
我分析了kotlin编译器生成的内容,并注意到自动生成的@metadata注解是罪魁祸首。我甚至尝试向java版本的类中添加一个空的类,以查看发生了什么,它确实给出了相同的noclassdeffounderror。我还应该注意,kotlin集成是有效的,因为它不是唯一的文件(我有用于Crudepository接口的kotlin文件,它可以工作?…)
所以我的问题是,我如何解决这个问题?是否可以禁用元数据注解,或者我做错了什么?
注意:我以前能够将kotlin类与spring一起使用,当时我将所有内容都放在一个文件中,似乎将代码拆分为较小的文件会把所有内容都搞乱
这个实体类是通过Crudepository这样使用的(注意它是如何使用kotlin的,将其移植到java没有任何区别)
@Repository
interface FileRepo : CrudRepository<Example, Long> {}
不同的管理器类会执行以下操作:
@Controller
public class FileUploadController {
private final FileRepo fileRepo;
@Autowired
public FileUploadController(FileRepo fileRepo) {
this.fileRepo = fileRepo;
}
...
Example tosave = new Example(Idhere, nameHere);
this.fileRepo.save(tosave);
这是我的gradle项目:
plugins {
id 'org.springframework.boot' version '2.5.2'
id 'io.spring.dependency-management' version '1.0.11.RELEASE'
id 'java'
id 'org.jetbrains.kotlin.jvm' version '1.5.20'
}
group = 'pl.szpring'
version = '0.0.1-SNAPSHOT'
sourceCompatibility = '1.8'
repositories {
mavenCentral()
}
dependencies {
implementation 'org.springframework.boot:spring-boot-starter-data-jpa'
implementation 'org.springframework.boot:spring-boot-starter-thymeleaf'
implementation 'org.springframework.boot:spring-boot-starter-web'
testImplementation('org.springframework.boot:spring-boot-starter-test')
implementation "org.jetbrains.kotlin:kotlin-stdlib-jdk8"
runtimeOnly "com.h2database:h2:1.4.200"
}
test {
useJUnitPlatform()
}
compileKotlin {
kotlinOptions {
jvmTarget = "1.8"
}
}
compileTestKotlin {
kotlinOptions {
jvmTarget = "1.8"
}
}
完整错误日志(引用使用CRUDEPository的类:
org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'fileUploadController' defined in file [(path here)\java\main\pl\szpring\wysylanie\FileUploadController.class]: Unsatisfied dependency expressed through constructor parameter 1; nested exception is org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'fileRepo' defined in pl.szpring.wysylanie.storage.FileRepo defined in @EnableJpaRepositories declared on JpaRepositoriesRegistrar.EnableJpaRepositoriesConfiguration: Invocation of init method failed; nested exception is java.lang.NoClassDefFoundError: kotlin/reflect/full/KClasses
at org.springframework.beans.factory.support.ConstructorResolver.createArgumentArray(ConstructorResolver.java:800) ~[spring-beans-5.3.8.jar:5.3.8]
at org.springframework.beans.factory.support.ConstructorResolver.autowireConstructor(ConstructorResolver.java:229) ~[spring-beans-5.3.8.jar:5.3.8]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.autowireConstructor(AbstractAutowireCapableBeanFactory.java:1354) ~[spring-beans-5.3.8.jar:5.3.8]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBeanInstance(AbstractAutowireCapableBeanFactory.java:1204) ~[spring-beans-5.3.8.jar:5.3.8]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:564) ~[spring-beans-5.3.8.jar:5.3.8]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:524) ~[spring-beans-5.3.8.jar:5.3.8]
at org.springframework.beans.factory.support.AbstractBeanFactory.lambda$doGetBean$0(AbstractBeanFactory.java:335) ~[spring-beans-5.3.8.jar:5.3.8]
at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:234) ~[spring-beans-5.3.8.jar:5.3.8]
at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:333) ~[spring-beans-5.3.8.jar:5.3.8]
at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:208) ~[spring-beans-5.3.8.jar:5.3.8]
at org.springframework.beans.factory.support.DefaultListableBeanFactory.preInstantiateSingletons(DefaultListableBeanFactory.java:944) ~[spring-beans-5.3.8.jar:5.3.8]
at org.springframework.context.support.AbstractApplicationContext.finishBeanFactoryInitialization(AbstractApplicationContext.java:918) ~[spring-context-5.3.8.jar:5.3.8]
at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:583) ~[spring-context-5.3.8.jar:5.3.8]
at org.springframework.boot.web.servlet.context.ServletWebServerApplicationContext.refresh(ServletWebServerApplicationContext.java:145) ~[spring-boot-2.5.2.jar:2.5.2]
at org.springframework.boot.SpringApplication.refresh(SpringApplication.java:754) ~[spring-boot-2.5.2.jar:2.5.2]
at org.springframework.boot.SpringApplication.refreshContext(SpringApplication.java:434) ~[spring-boot-2.5.2.jar:2.5.2]
at org.springframework.boot.SpringApplication.run(SpringApplication.java:338) ~[spring-boot-2.5.2.jar:2.5.2]
at org.springframework.boot.SpringApplication.run(SpringApplication.java:1343) ~[spring-boot-2.5.2.jar:2.5.2]
at org.springframework.boot.SpringApplication.run(SpringApplication.java:1332) ~[spring-boot-2.5.2.jar:2.5.2]
at pl.szpring.wysylanie.MainKt.main(main.kt:39) ~[main/:na]```
1条答案
按热度按时间s1ag04yj1#
事实证明,错误日志一直在暗示问题所在,我缺少kotlin reflect dependency(此处为gradle):