gpt4 book ai didi

java - 如何使用 JPA 中的规范连接多个列?

转载 作者:行者123 更新时间:2023-12-02 09:29:32 24 4
gpt4 key购买 nike

我正在尝试将查询转换为 JPA 规范,该查询包含带有 OR 条件的 JOIN 操作。

这是查询:

select u from User u inner join Operation o on (u.id = o.verificateur1 or u.id = o.verificateur2) where o.id not in (:ids)

我尝试编写规范,但我不知道如何使用 OR 条件连接多个列。

public class UserSpecification {

public static Specification<User> UsersNotInSelectedOperations(final List<Long> operationId ){

return new Specification<User>() {
@Override
public Predicate toPredicate(Root<User> root, CriteriaQuery<?> criteriaQuery, CriteriaBuilder criteriaBuilder) {
Join<User, Operation> userJoinOp = root.join("fk_user1_id");
final Path<User> users = userJoinOp.get("id");
return criteriaBuilder.not(users.in(operationId));
}
};
}

}

用户实体:

@Entity
@Table(name = "aigle_user")
public class User extends AbstractEntity implements UserDetails {

private static final long serialVersionUID = 2840226091237599675L;

@Column(name = "mail", nullable = true)
private String mail;

@Column(name = "password")
private String password;

@Column(name = "is_activated")
private boolean isActivated;

@Column(name = "is_admin")
private boolean isAdmin;

@ManyToMany(cascade = { CascadeType.PERSIST })
@LazyCollection(LazyCollectionOption.FALSE)
@JoinTable(name = "aigle_group_user", joinColumns = @JoinColumn(name = "fk_user_id", referencedColumnName = "id"), inverseJoinColumns = @JoinColumn(name = "fk_group_id", referencedColumnName = "id"))
private Set<Group> groups;

@ManyToMany(cascade = { CascadeType.PERSIST })
@LazyCollection(LazyCollectionOption.FALSE)
@JoinTable(name = "aigle_role_user", joinColumns = @JoinColumn(name = "fk_user_id", referencedColumnName = "id"), inverseJoinColumns = @JoinColumn(name = "fk_role_id", referencedColumnName = "id"))
private Set<Role> roles;

@OneToMany(cascade = CascadeType.ALL, fetch = FetchType.LAZY, mappedBy = "destinataire", orphanRemoval = true)
private Set<Tache> taches;

@Column(name = "last_name", unique = false)
private String lastName;

@Column(name = "first_name", unique = false)
private String firstName;

@Column(name = "telephone")
private String telephone;

private String salesforceId;

-----
}

运营实体

public class Operation extends OperationField {

...
@ManyToOne(cascade = CascadeType.PERSIST, fetch = FetchType.LAZY)
@JoinColumn(name = "fk_user1_id")
private User verificateur1;

@ManyToOne(cascade = CascadeType.PERSIST, fetch = FetchType.LAZY)
@JoinColumn(name = "fk_user2_id")
private User verificateur2;
.....
}

我希望有一个规范来替换上面的查询

最佳答案

您可以尝试使用子查询来代替连接表达式

    public static Specification<User> UsersNotInSelectedOperations(final List<Long> operationIds) {
return (root, query, builder) -> {
Subquery<Operation> subquery = query.subquery(Operation.class);
Root<Operation> operation = subquery.from(Operation.class);

Predicate predicate1_1 = builder.equal(operation.get("verificateur1").get("id"), root.get("id"));
Predicate predicate1_2 = builder.equal(operation.get("verificateur2").get("id"), root.get("id"));

Predicate predicate1 = builder.or(predicate1_1, predicate1_2);
Predicate predicate2 = operation.get("id").in(operationIds).not();

subquery.select(operation).where(predicate1, predicate2);

return builder.exists(subquery);
};
}

使用此规范,您将获得如下所示的 HQL 查询

from User u
where exists( // subquery ->
from Operation o
where (o.verificateur1.id = u.id or o.verificateur2.id = u.id) // predicate 1
and o.id not in (:ids) // predicate 2
// <- subquery
)

from User uselect u from User u

的更短替代品

我编写了这段代码,但没有运行,因此需要修改

关于java - 如何使用 JPA 中的规范连接多个列?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/58096427/

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