zoukankan      html  css  js  c++  java
  • 联合主键

    近期找一个数据不一致的问题,花了一周时间找bug,感觉很经典。虽然是填离职同事留下的坑。由于插入了很多错误数据,还需要一周的时间去手动修改错误数据(1千多条错误数据)。很坑啊有木有!!

    他的代码是这样的:

    @Entity
    public class PaymentDetailVO implements Serializable {
        @Id
        public Long duesdetailid;
    
        public String paymenttype;
        @Id
        public String paymethod;
    
        public BigDecimal payamount;
    
        
    }
    // 前面代码省略
    
        paymentdetailsql.append("select t.id as duesdetailid,")
                                            .append("  '1' as paymenttype,")
                                            .append(" ddl.value as paymethod,")
                                            .append(" (sum(ts.price)-nvl(sum(tr.returnamount),0)-nvl(sum(tc.ticketprice),0)) as  payamount")
                                            .append(" from Ticketturnoverdetail t ")
                                            .append(" left join ticketsell ts on t.id = ts.turnoverdetailid ")
                                            .append(" left join ticketreturn tr on t.id=tr.turnoverdetailid ")
                                            .append(" left join ticketcancel tc on t.id=tc.turnoverdetailid ")
                                            .append(" left join digitaldictionarydetail ddl on ddl.digitaldictionaryid=50 and ddl.code=ts.paymethod")
                                            .append("  where (ts.paymethod <> '0' and ts.paymethod <> '2' and ts.paymethod <> '3')   and t.id=:id")
                                            .append(" group by ddl.value,'1',t.id")
                                            .append(" union all")
                                            .append(" select t.id as duesdetailid,")
                                            .append("  '1' as paymenttype,")
                                            .append(" ddl.value as paymethod,")
                                            .append(" (sum(ts.price)-nvl(sum(tr.returnamount),0)-nvl(sum(tc.ticketprice),0)) as  payamount")
                                            .append(" from Ticketturnoverdetail t ")
                                            .append(" left join ticketsellagent ts on t.id = ts.turnoverdetailid ")
                                            .append(" left join ticketreturn tr on t.id=tr.turnoverdetailid ")
                                            .append(" left join ticketcancel tc on t.id=tc.turnoverdetailid ")
                                            .append(" left join digitaldictionarydetail ddl on ddl.digitaldictionaryid=50 and ddl.code=ts.paymethod")
                                            .append("  where (ts.paymethod <> '0' and ts.paymethod <> '2' and ts.paymethod <> '3')   and t.id=:id")
                                            .append(" group by ddl.value,'1',t.id");
                            Query ticketquery = JPA.em().createNativeQuery(paymentdetailsql.toString(),PaymentDetailVO.class);
                            ticketquery.setParameter("id", ticketturnoverdetail.getId());
                            List<PaymentDetailVO> paymentdetaillist = new ArrayList<PaymentDetailVO>();
                            try {
                                paymentdetaillist = ticketquery.getResultList();
                            } catch (Exception e) {
                                e.printStackTrace();
                                play.Logger.error("=============:%s", e.getMessage());
                            }
                            for(PaymentDetailVO paymentdetail : paymentdetaillist){
                                PaymentDetail _paymentdetail = new PaymentDetail();
                                _paymentdetail.duesdetailid=paymentdetail.duesdetailid;
                                _paymentdetail.paymenttype=paymentdetail.paymenttype;
                                _paymentdetail.paymethod=paymentdetail.paymethod;
                                _paymentdetail.payamount=paymentdetail.payamount;
                                _paymentdetail.createtime=new Date();
                                _paymentdetail.save();
                            }
    
    //后面代码省略

    看出问题了么?他使用

    duesdetailid和paymethod作为联合主键,但是查询语句用的是union all 将2个group by 给连接起来。插入paymentdetail 的时候jpa认为是第一条和第二条是同一条数据,导致第一条数据插入了2次,而第二条没有插入。

    如何修改呢?只要把外面再套一层group by 就行了。然后paymenttype也要加入联合主键。前面加上@Id


  • 相关阅读:
    java练习6
    java练习5
    java练习4
    java练习3
    java练习2
    java练习1
    用代码实现判断字符串的开头和结尾
    语句练习题2
    语句练习题1
    值类型和引用类型的区别
  • 原文地址:https://www.cnblogs.com/feiyunaima/p/6758418.html
Copyright © 2011-2022 走看看