尝试使用Spring Data JPA创建自定义存储库时,找不到类型错误的属性

dnc*_*253 39 java spring repository spring-data-jpa

我有一个Media实体,它有一些用户上传文件的基本字段.为了保存上传文件的字节,我想创建一个包含该功能的自定义存储库.按照Spring文档中的步骤,我创建了一个如下所示的界面:

public interface MediaBytesRepository
{
    public byte[] getBytes(Media media) throws IOException;
    public void saveBytes(Media media, byte[] bytes) throws IOException;
    public void appendBytes(Media media, byte[] bytes) throws IOException;
    public void deleteBytes(Media media) throws IOException;
    public boolean bytesExist(Media media) throws IOException;
}
Run Code Online (Sandbox Code Playgroud)

然后我提供了一个名为的接口的实现 MediaBytesRepositoryImpl

有了这个,我创建了以下界面:

public interface MediaRepository extends JpaRepository<Media, Long>, MediaBytesRepository
{
}
Run Code Online (Sandbox Code Playgroud)

现在,当我启动服务器时,我得到以下堆栈跟踪:

SEVERE: Exception sending context initialized event to listener instance of class org.springframework.web.context.ContextLoaderListener
org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'mediaRepository': FactoryBean threw exception on object creation; nested exception is java.lang.IllegalArgumentException: Could not create query metamodel for method public abstract void com.foo.bar.core.media.MediaBytesRepository.saveBytes(com.foo.bar.core.media.Media,byte[]) throws java.io.IOException!
    at org.springframework.beans.factory.support.FactoryBeanRegistrySupport.doGetObjectFromFactoryBean(FactoryBeanRegistrySupport.java:149)
.....
Caused by: java.lang.IllegalArgumentException: Could not create query metamodel for method public abstract void com.foo.bar.core.media.MediaBytesRepository.saveBytes(com.foo.bar.core.media.Media,byte[]) throws java.io.IOException!
    at org.springframework.data.jpa.repository.query.JpaQueryLookupStrategy$CreateQueryLookupStrategy.resolveQuery(JpaQueryLookupStrategy.java:92)
    at org.springframework.data.jpa.repository.query.JpaQueryLookupStrategy$CreateIfNotFoundQueryLookupStrategy.resolveQuery(JpaQueryLookupStrategy.java:162)
    at org.springframework.data.jpa.repository.query.JpaQueryLookupStrategy$AbstractQueryLookupStrategy.resolveQuery(JpaQueryLookupStrategy.java:68)
    at org.springframework.data.repository.core.support.RepositoryFactorySupport$QueryExecutorMethodInterceptor.<init>(RepositoryFactorySupport.java:280)
    at org.springframework.data.repository.core.support.RepositoryFactorySupport.getRepository(RepositoryFactorySupport.java:148)
    at org.springframework.data.repository.core.support.RepositoryFactoryBeanSupport.getObject(RepositoryFactoryBeanSupport.java:125)
    at org.springframework.data.repository.core.support.RepositoryFactoryBeanSupport.getObject(RepositoryFactoryBeanSupport.java:41)
    at org.springframework.beans.factory.support.FactoryBeanRegistrySupport.doGetObjectFromFactoryBean(FactoryBeanRegistrySupport.java:142)
    ... 20 more
 Caused by: java.lang.IllegalArgumentException: No property save found for type class com.foo.bar.core.media.Media
    at org.springframework.data.mapping.PropertyPath.<init>(PropertyPath.java:73)
    at org.springframework.data.mapping.PropertyPath.<init>(PropertyPath.java:92)
    at org.springframework.data.mapping.PropertyPath.create(PropertyPath.java:319)
    at org.springframework.data.mapping.PropertyPath.create(PropertyPath.java:333)
    at org.springframework.data.mapping.PropertyPath.create(PropertyPath.java:301)
    at org.springframework.data.mapping.PropertyPath.from(PropertyPath.java:265)
    at org.springframework.data.mapping.PropertyPath.from(PropertyPath.java:239)
    at org.springframework.data.repository.query.parser.Part.<init>(Part.java:70)
    at org.springframework.data.repository.query.parser.PartTree$OrPart.<init>(PartTree.java:180)
    at org.springframework.data.repository.query.parser.PartTree$Predicate.buildTree(PartTree.java:260)
    at org.springframework.data.repository.query.parser.PartTree$Predicate.<init>(PartTree.java:240)
    at org.springframework.data.repository.query.parser.PartTree.<init>(PartTree.java:68)
    at org.springframework.data.jpa.repository.query.PartTreeJpaQuery.<init>(PartTreeJpaQuery.java:57)
    at org.springframework.data.jpa.repository.query.JpaQueryLookupStrategy$CreateQueryLookupStrategy.resolveQuery(JpaQueryLookupStrategy.java:90)
    ... 27 more
Run Code Online (Sandbox Code Playgroud)

我发现了这个类似的帖子,但那里的建议(所有相同的包,命名约定)都是我已经在做的事情.我的所有媒体类和接口都在同一个包中,我使用的是"Impl"后缀.

有人可以说明为什么我会收到此错误以及如何解决此问题?谢谢.

Ral*_*lph 74

你写了:

那里的建议(所有在相同的包,命名约定)是我已经在做的事情.

你不可以.

重命名你MediaBytesRepositoryMediaRepositoryCustom.

当然,您需要MediaRepositoryCustom具有名称的实现MediaRepositoryImpl.

  • 犯了同样的错误...总结它应该是:1)YourInterfaceName 2)YourInterfaceNameCustom 3)YourInterfaceNameImpl (27认同)
  • 看起来我误解了应该如何命名.在您回答之后,我再次查看了文档,并意识到我的实现类的名称需要是Spring Data接口的名称+"Impl",而不是我的接口名称+"Impl".所以,我能够保留我的接口`MediaBytesRepository`的名称,我只需要命名实现`MediaRepositoryImpl`而不是'MediaBytesRepositoryImpl`.谢谢您的帮助. (21认同)

小智 6

您必须将您的impl类命名为"InterfaceNameImpl".实现的默认后缀是Impl,我们可以根据需要进行更改:

<repositories base-package="com.acme.repository" repository-impl-postfix="FooBar" />
Run Code Online (Sandbox Code Playgroud)

自定义接口的名称无关紧要.