微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

为什么我在存储库上收到错误“找不到属性”?

如何解决为什么我在存储库上收到错误“找不到属性”?

我的项目使用 java spring 和 mongodb 存储库。

这里是存储库定义:

@Repository
public interface InfoRepository extends MongoRepository<Info,String> {
    List<InfoDto> findAll();
}

这里是信息定义:

@Document("info")
@Data
public class Info{
    @Id
    private String id = null;
    private String name;
    private String companyName;
    private String email;
    private Address address;
    private String website;
}

这是 InfoDto 类的定义:

@Data
public class InfoDto {
    private String name;
    private String companyName;
    private Address address;
}

当我开始运行项目 IU 时出现此错误

'findAll()' in '...repository.InfoRepository' clashes with 'findAll()' 
in 'org.springframework.data.mongodb.repository.MongoRepository'; attempting to use incompatible return type

为了防止冲突,我更改了存储库函数名称

List<InfoDto> findAll();

为此:

List<InfoDto> findAllMakeProjection();

但在我进行上述更改并运行该函数后,出现此错误

org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'infoServiceImpl' defined in file 
[...\InfoServiceImpl.class]: 
Unsatisfied dependency expressed through constructor parameter 0; nested exception is org.springframework.beans.factory.BeanCreationException: 
Error creating bean with name 'infoRepository' defined in ".../repository.InfoRepository" defined in @EnableMongoRepositories 
declared on MongoRepositoriesRegistrar.EnableMongoRepositoriesConfiguration: 
Invocation of init method Failed; nested exception is org.springframework.data.mapping.PropertyReferenceException: 
No property findAllMakeProjection found for type Info!

知道为什么会出现错误以及如何修复它吗?

解决方法

List<T> findAll() 是 MongoRepository 接口中提供的方法,因此无法在子接口中更改其返回类型。您最多可以将返回类型更改为 List 实现,例如 ArrayList<T>LinkedList<T>

如果将方法名称更改为 List<InfoDto> findAllMakeProjection(),Spring Data MongoDB 将尝试使用属性名称构建查询,但没有命名属性,因此会引发错误。

但允许在方法名中的 By 字之前添加任何内容,例如findAllByfindEverythingByfindDataByBy 之后的任何内容都将用作过滤器(where 条件),如果我们在 By 之后不添加任何内容,它将像 findAll(无过滤器)

因此,相应地更改方法名称,您将能够运行查询。

,

这里发生的是 findAll() 是为 Spring Data JPA 保留的默认内置存储库方法名称。因此,如果您在自定义存储库中引入自己的 findAll()(无论是 JPARespository 还是 MongoRepository),它都会与 JPA 提供的 findAll() 发生冲突。

将方法名称更改为 List<InfoDto> findAllMakeProjection(); 将使 JPA 使用 JPQL 构建查询,因此它将尝试从方法名称中提取实体属性,除非您使用 @Query 注释定义查询。

因此,如果您想这样做,它应该类似于 findAllBySomeConditionfindBySomeCondition

例如:findByNameAndCompanyName(),findByEmail(),findAllByCompanyName()

最好的方法是删除 List<InfoDto> findAll(); 中的 InfoRepository。不过,你可以打电话

@Autowired
private InfoRepository infoRepository;

.......


infoRepository.findAll();

所以这将返回一个 List<Info>

而且您不能像以前那样直接通过 MongoRepository 重新生成 DTO 对象列表。它最初将返回一个模型对象列表(List<Info>)。为了返回 DTO 列表,

@Repository
public interface InfoRepository extends MongoRepository<Info,String> {
    @Query(value="select new com.foo.bar.InfoDto(i.name,i.companyName,i.address) from Info i")
    List<InfoDto> findAllInfos();
}

您可能需要有点棘手,并使用从实体到 DTO 的映射地址做其他事情。

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。

相关推荐


Selenium Web驱动程序和Java。元素在(x,y)点处不可单击。其他元素将获得点击?
Python-如何使用点“。” 访问字典成员?
Java 字符串是不可变的。到底是什么意思?
Java中的“ final”关键字如何工作?(我仍然可以修改对象。)
“loop:”在Java代码中。这是什么,为什么要编译?
java.lang.ClassNotFoundException:sun.jdbc.odbc.JdbcOdbcDriver发生异常。为什么?
这是用Java进行XML解析的最佳库。
Java的PriorityQueue的内置迭代器不会以任何特定顺序遍历数据结构。为什么?
如何在Java中聆听按键时移动图像。
Java“Program to an interface”。这是什么意思?