由DateFormat引起的线程安全问题

本文探讨了一个在测试环境中遇到的插入重复主键问题,通过分析发现是由于SimpleDateFormat在多线程环境下非线程安全所导致。文章详细介绍了问题的背景、代码示例及解决方案,强调了在设计时考虑线程安全的重要性。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

有一次在测试环境中有个插入重复主键的问题,代码如下

@Transactional
    public void lending(OrderExtend order) {

Date date = DateUtil.getCountyTime();

...................................

                        
        // 更新限额金额
                        String nowDate = DateUtil.timeToString(date, DateUtil.DATE_FORMAT_23);


OrderLimit limit = orderLimitMapper.selectLimitByDate(nowDate, order.getAppPackage());
                        if (limit == null) {//
                            SystemOption record = new SystemOption();
                            record.setOptionGroup("dailyorderlimit");
                            record.setOptionKey(order.getAppPackage());
                            List<SystemOption> list = systemOptionMapper.selectBySelective(record);

                            limit = new OrderLimit();
                            limit.setAppName(order.getAppName());
                            limit.setAppPackage(order.getAppPackage());
                            limit.setLimitTime(date);
                            limit.setApplyNumber(1);
                            limit.setApplyAmount(order.getLendingAmount());
                            limit.setUpdateTime(date);
                            limit.setMaxNumber(Integer.valueOf(list.get(0).getOptionValue()));
                            orderLimitMapper.insertSelective(limit);
                        } else {
                            limit.setLimitTime(date);
                            limit.setUpdateTime(date);
                            limit.setApplyAmount(order.getLendingAmount());
                            orderLimitMapper.updateOrderLimitAmount(limit);
                        }


}


public class DateUtil {

    public static SimpleDateFormat DATE_FORMAT_23 = new SimpleDateFormat("yyyy-MM-dd");

public static String timeToString(Date d, DateFormat dateFormat) { if (d == null) { return null; } return dateFormat.format(d); } }

原因是orderLimitMapper.selectLimitByDate找不到值,结果插入导致重复的唯一键。然后分析居然是sql里传入的时间不对,传入的时间是个莫名奇妙的日期,但这个时间是在方法内定义的一个局部变量啊,应该不是线程安全啊。结果我想错了,因为DATE_FORMAT_23是一个静态变量,在方法区的变量照样是在堆里的,同样会遇到线程安全的问题。网上一查果然SimpleDateFormat不是线程安全的

转载于:https://www.cnblogs.com/zjhgx/p/10145367.html

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值