我有以下dao方法:
@Override
public List<AdminRole> findAll() {
Session session = sessionFactory.getCurrentSession();
Criteria criteria = session.createCriteria(AdminRole.class);
criteria.setResultTransformer(Criteria.DISTINCT_ROOT_ENTITY);
return criteria.list();
}
实际上我想从数据库中检索所有条目。
有时我看到重复。当我使用AdminRole添加用户时会发生这种情况。
我已经读过,当我使用EAGER
获取类型时,可能会修复以下行:
criteria.setResultTransformer(Criteria.DISTINCT_ROOT_ENTITY);
但这对我没有帮助。
我的映射:
@Entity
@Table(name = "terminal_admin_role")
public class AdminRole {
@Id
@Column(name = "role_id", nullable = false, unique = true)
@GeneratedValue(strategy = GenerationType.SEQUENCE, generator = "user_id")
@SequenceGenerator(name = "user_id", sequenceName = "user_id")
private Long adminId;
@Column(name = "role")
private String role;
public AdminRole(String role) {
this.role = role;
}
public AdminRole() {
}
// get set
@Override
public String toString(){
return role;
}
@Override
public boolean equals(Object o) {
if (this == o) {
return true;
}
if (!(o instanceof AdminRole)) {
return false;
}
AdminRole adminRole = (AdminRole) o;
if (!role.equals(adminRole.role)) {
return false;
}
return true;
}
@Override
public int hashCode() {
return role.hashCode();
}
}
和
@Entity
@Table(name = "terminal_admin")
public class TerminalAdmin {
@ManyToMany(fetch=FetchType.EAGER,cascade=CascadeType.ALL)
@JoinTable(name = "admin_role", joinColumns = {
@JoinColumn(name = "admin_id", nullable = false) },
inverseJoinColumns = { @JoinColumn(name = "role_id",
nullable = false) })
private Set<AdminRole> adminRoles;
//...
}
我无法切换抓取类型。
我不想把这个列表放进去。
答案 0 :(得分:2)
没有理由使用DISTINCT_ROOT_ENTITY
或类似内容,您只需要:
session.createCriteria(AdminRole.class).list();
如果你得到重复项,那么你真的在数据库中拥有它们。检查直接或通过级联来保存AdminRole
的代码。
当从其他实体级联PERSIST
/ MERGE
操作时,请确保将操作级联到持久/分离AdminRole
实例,而不是瞬态(新)实例。< / p>
答案 1 :(得分:1)
我的钱是乱搞hashCode / equals覆盖和Hibernate代理。
然而,一旦你关闭了Hibernate会话,所有的赌注都会被关闭。 [...]因此,如果你在会话之间保留对象的集合,你将开始经历奇怪的行为(主要是集合中的重复对象)。
首先我会像org.apache.commons.lang3
那样使用它(对于Hibernate实体来说显然太昂贵了,但是对它们来说工作正常,如果有效则应该验证我的预感):
import org.apache.commons.lang3.builder.EqualsBuilder;
import org.apache.commons.lang3.builder.HashCodeBuilder;
import org.apache.commons.lang3.builder.ToStringBuilder;
@Override
public String toString() {
return ToStringBuilder.reflectionToString(this);
}
@Override
public int hashCode() {
return HashCodeBuilder.reflectionHashCode(this);
}
@Override
public boolean equals(Object other) {
return EqualsBuilder.reflectionEquals(this, other);
}
如果这样可行,你可以采用更便宜的方式:
@Override
public int hashCode() {
HashCodeBuilder hcb = new HashCodeBuilder();
hcb.append(role);
return hcb.toHashCode();
}
@Override
public boolean equals(Object obj) {
if (this == obj) {
return true;
}
if (!(obj instanceof AdminRole)) {
return false;
}
AdminRole that = (AdminRole) obj;
EqualsBuilder eb = new EqualsBuilder();
eb.append(role, that.role);
return eb.isEquals();
}