jpql(JPA)中重复的父级和子级数据

问题描述 投票:0回答:1

我有一个Production类和ProductionDetail实体类,其中Production表的ID是一个外键,作为ProductionDetail实体类中的production_id,所以我两个都有映射的实体类都在下面给出

生产实体类:

@Entity
@Table(name = "tbl_production")
@XmlRootElement

public class TblProduction implements Serializable {

    private static final long serialVersionUID = 1L;
    @Id
    @Basic(optional = false)
    @NotNull
    @Size(min = 1, max = 45)
    @Column(name = "ID")
    private String id;

    @Column(name = "PRODUCTION_DATE")
    @Temporal(TemporalType.DATE)
    private Date productionDate;

    @Column(name = "START_DATETIME")
    @Temporal(TemporalType.TIMESTAMP)
    private Date startDatetime;

    @Column(name = "END_DATETIME")
    @Temporal(TemporalType.TIMESTAMP)
    private Date endDatetime;

    @Size(max = 45)
    @Column(name = "MACHINE_UUID")
    private String machineUuid;

    **Relation with Production Details Table**
    @OneToMany(mappedBy = "production")
    @XmlElement(name = "productionDetails")
    private List<TblProductionDetail> productionDetailList = new ArrayList<>();


    @PrimaryKeyJoinColumn(name = "MACHINE_UUID", referencedColumnName = "UUID")
    @ManyToOne(fetch = FetchType.LAZY)
    private MstMachine mstMachine;

    @XmlTransient
    public MstMachine getMstMachine() {
       return this.mstMachine;
   }
} 

生产详细信息实体类:

    @Entity
    @Table(name = "tbl_production_detail")
    @XmlRootElement
    public class TblProductionDetail implements Serializable {

        private static final long serialVersionUID = 1L;
        @Id
        @Basic(optional = false)
        @NotNull
        @Size(min = 1, max = 45)
        @Column(name = "ID")
        private String id;
        @Size(max = 45)
        @Column(name = "COMPONENT_ID")
        private String componentId;
        @Size(max = 45)
        @Column(name = "PRODUCTION_ID")
        private String productionId;

        **Relation with Production Class** 
        @ManyToOne
        @JoinColumn(name = "PRODUCTION_ID", referencedColumnName = "ID", insertable = false, 
                    updatable = false)
        private TblProduction production;

        @Transient
        public String componentCode;
        @Transient
        public String componentName;


        @PrimaryKeyJoinColumn(name = "COMPONENT_ID", referencedColumnName = "ID")  
        @ManyToOne(fetch = FetchType.LAZY)
        private MstComponent mstComponent;

        @XmlTransient
        public MstComponent getMstComponent() {
            return this.mstComponent;
        }
        public void setMstComponent(MstComponent mstComponent) {
            this.mstComponent = mstComponent;
        }
    }

ParentList类:

  public class TblProductionList {
      private List<TblProduction> productionList = new ArrayList<>();;  
      public TblProductionList() {
            productionList = new ArrayList<>();
      }
      public List<TblProduction> getTblProductions() {
            return productionList;
      }
      public void setTblProductions(List<TblProduction> tblProductionList) {
            this.productionList = tblProductionList;
      }
  }

BusinessLogic(DAO类):

       public TblProductionList getJson() {
            TblProductionList response = new TblProductionList();
            StringBuilder retrieveQuery = new StringBuilder();

            retrieveQuery.append(" SELECT prod FROM TblProduction prod ");
            retrieveQuery.append(" JOIN FETCH prod.productionDetailList ");
            retrieveQuery.append(" WHERE prod.endDatetime IS NULL ");
            retrieveQuery.append(" AND prod.machineUuid IS NOT NULL ");
            retrieveQuery.append(" AND NOT EXISTS (SELECT tpt FROM 
            TblProductionThset tpt WHERE prod.id = tpt.productionId) ");
            retrieveQuery.append(" AND EXISTS (SELECT mmfd FROM 
            MstMachineFileDef mmfd WHERE prod.machineUuid = mmfd.machineUuid 
            AND mmfd.hasThreshold = 1) ");
            retrieveQuery.append(" ORDER BY prod.id ");
            Query query = 
            entityManager.createQuery(retrieveQuery.toString());
            List thresholdList = query.getResultList();       
            response.setTblProductions(thresholdList);

            return response;
        }

根据数据库,我正在获得预期的主子数据,如下所示enter image description here

设计此实体类后,我希望我将获得3条主记录,其中每条记录都有2条详细记录。但是我得到了6个重复的主记录和12个子记录。有人可以向我建议我的代码哪里出错了吗?请检查我从API获取的JSON数据。

enter image description here

java jpa jax-rs jpql
1个回答
0
投票

将数组列表更改为哈希集,然后记录将不会重复。

© www.soinside.com 2019 - 2024. All rights reserved.