gpt4 book ai didi

java - QueryDsl 投影 ElementCollection

转载 作者:行者123 更新时间:2023-12-04 10:21:19 30 4
gpt4 key购买 nike

我试图弄清楚如何使用枚举列表(@ElementCollection)对实体进行 DTO 投影。不幸的是,缺少 QueryDsl 文档,在这里我只能找到版本 3 的结果 不是 适用于版本 4。

@Entity
public class User {
private String username;

@Enumerated(EnumType.STRING)
@ElementCollection(targetClass = Permission.class)
private Set<Permission> permissions;
}

而且我想要一个带有权限枚举或简单字符串的集合/列表/数组的 DTO(无论如何都会转换为 JSON)。一个简单的构造函数表达式不起作用:
List<UserDto> users = new JPAQueryFactory(eM).select(
Projections.constructor(UserDto.class,
QUser.user.username, QUser.user.permissions))
.from(QUser.user)
.fetch();

给我 org.hibernate.QueryException: not an entity
所有带有 .transform() 的例子我见过使用 groupBy 并返回 Map 。我正在动态生成这些查询,我想要一个 DTO 列表,有时不是 DTO 列表,有时是 Map。

编辑:

如果我要编写 native PostgreSQL 查询,则类似这样的事情:
select id, username, array_remove(array_agg(up.permissions), null) as permissions
from users u
left join users_permissions up on up.uid = u.id
group by u.id;

编辑2:

我想这就是我必须用 JPQL 做的事情吗? :呕吐:
List<UserDto> users = (List<UserDto>) eM.getEntityManager().createQuery(
"SELECT u.id, u.username, u.tenantId, u.fullname, u.active, u.localeKey, perms " +
"FROM User u " +
"LEFT JOIN u.permissions perms")
.unwrap(org.hibernate.query.Query.class)
.setResultTransformer(
new ResultTransformer() {
private Map<Long, UserDto> res = new HashMap<>();

@Override
public Object transformTuple(Object[] tuple, String[] aliases) {
UserDto u = res.get(tuple[0]);
if (u == null) {
u = new UserDto((Long) tuple[0], (String) tuple[1], "", (String) tuple[2], (String) tuple[3], (boolean) tuple[4], (String) tuple[5], EnumSet.of((Permission) tuple[6]));
res.put(u.getId(), u);
} else {
u.getPermissions().add((Permission) tuple[6]);
}

return null;
}

@Override
public List<UserDto> transformList(List tuples) {
return new ArrayList<>(res.values());
}
})
.getResultList();

最佳答案

好吧,我终于想通了。在这种情况下,您实际上必须使用转换器,这是有道理的,因为您想要聚合多行。

我不得不翻遍QueryDsl's unit tests .如果您不使用 IDE,静态导入实际上会使其变得棘手,但请像我一样在 Github 上阅读它。我几乎有了解决方案,但我使用了 Expressions.set() , 而不是 GroupBy.set() :

List<UserDto> users = new JPAQueryFactory(eM.getEntityManager())
.selectFrom(QUser.user)
.leftJoin(QUser.user.permissions, perm)
.transform(
groupBy(QUser.user.id)
.list(Projections.constructor(UserDto.class,
QUser.user.id, QUser.user.username, Expressions.stringTemplate("''"), QUser.user.tenantId,
QUser.user.fullname, QUser.user.active, QUser.user.localeKey, GroupBy.set(perm))));

这比 JPQL/Hibernate-ResultTransformer 版本更好看。

关于java - QueryDsl 投影 ElementCollection,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/60833916/

30 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com