Hibernate - CriteriaQuery在一对多关系上复制记录

ca1c2owp  于 2023-03-03  发布在  其他
关注(0)|答案(1)|浏览(160)
    • bounty将在3天后过期**。回答此问题可获得+100声望奖励。KenobiBastila希望引起更多人关注此问题。
    • 导言**

我有一个遗留的代码,我不得不给予维护。我有一个代码,加载所有的子实体从一个文档实体。它加载罚款,但是,在'一对多'关系("修订"),它带来了重复的记录。我试图使用独特的,但它没有解决这个问题。

    • 问题描述**

我有一个名为Documento的类,它有几个子实体。所有实体都是ManyToMany,除了"revisoes"是oneToMany。下面的代码加载了所有实体,但"revisoes"有重复的记录。
我如何以这样的方式解决它,"修订"不会带来重复的记录?

    • 代码**
@Entity
@Table(name = "documentos")
public class Documento extends Model {

    @NotFound(action = NotFoundAction.IGNORE)
    @ManyToOne(fetch = FetchType.EAGER)
    private TipoDeDocumento tipoDeDocumento;

    @Column(length = 250, nullable = false, unique = true)
    private String codigo;

    @NotFound(action = NotFoundAction.IGNORE)
    @ManyToMany(fetch = FetchType.EAGER)
    private Set<QuesitosNormas> quesitosNormas;

    @ManyToMany(fetch = FetchType.LAZY)
    private Set<PontoDeDistribuicao> pontosDistribuicao;

    @ManyToMany(fetch = FetchType.LAZY)
    private Set<Processo> processos;

    @Cascade(org.hibernate.annotations.CascadeType.ALL)
    @OneToMany(cascade = CascadeType.ALL, fetch = FetchType.LAZY, orphanRemoval = true, mappedBy = "documento")
    private Collection<DocumentoRevisao> revisoes;
@Override
    public Documento find(Long id, Session session, boolean closeSession) {
        try {
            CriteriaBuilder criteriaBuilder = session.getCriteriaBuilder();
            
            CriteriaQuery<Documento> criteriaQuery = criteriaBuilder.createQuery(Documento.class);
      
            Root<Documento> rootDocument = criteriaQuery.from(Documento.class);
            rootDocument.fetch("quesitosNormas", JoinType.LEFT); // ManyToMany
            rootDocument.fetch("pontosDistribuicao", JoinType.LEFT); // ManyToMany
            rootDocument.fetch("processos", JoinType.LEFT); // ManyToMany
            rootDocument.fetch("tipoDeDocumento",JoinType.LEFT); //OneToOne
            rootDocument.fetch("revisoes", JoinType.LEFT); // OneToMany
            //
            //
            criteriaQuery.select(rootDocument);
            criteriaQuery.where(criteriaBuilder.equal(rootDocument.get("id"), id));
            criteriaQuery.distinct(true);

            Query<Documento> query = session.createQuery(criteriaQuery);
           
            Documento singleResult = query.getSingleResult();

            return singleResult;

        } catch (Exception ex) {
            throw ex;
        } finally {
            if (session != null && closeSession) {
                session.close();
            }
        }
    }
    • 参考资料**

Hibernate Criteria fetches duplicates - one to many association
hibernate OneToMany criteria returns duplicates
Duplicated results in Hibernate OneToMany List
https://davidecerbo.medium.com/one-to-many-relationship-gets-duplicate-objects-without-using-any-tricks-a55012611539

lrpiutwd

lrpiutwd1#

1.试试这个-

criteriaQuery.setResultTransformer(Criteria.DISTINCT_ROOT_ENTITY);
--criteriaQuery.distinct(true);

1.而不是集合,

@Cascade(org.hibernate.annotations.CascadeType.ALL)
@OneToMany(cascade = CascadeType.ALL, fetch = FetchType.LAZY, orphanRemoval = true, mappedBy = "document")
private Collection<DocumentoRevisao> revisoes;

可以像这样使用Set

@Cascade(org.hibernate.annotations.CascadeType.ALL)
@OneToMany(cascade = CascadeType.ALL, fetch = FetchType.LAZY, orphanRemoval = true, mappedBy = "documento")
private Set<DocumentoRevisao> revisoes;

相关问题