在一个事务的service方法里插入数据并且开启新的线程查询新增数据不一致

批量新增品牌数据, 然后新增完之后,在事务方法里开启线程执行所有品牌数量查询
代码如下, 只展示相关代码

    @Transactional(rollbackFor = Exception.class)
    @Override
    public void add(BrandEntity brand) {
//        baseMapper.insert(brand);
        List<BrandEntity> list = new ArrayList();
        for (int i=0;i<10;i++){
            list.add(brand);
        }
        brandDao.insertBatch(list);
        Runnable runnable = new Runnable() {
            @Override
            public void run() {
                Integer threadCount = brandDao.selectCount(null);
                System.out.println("子线程==============================");
                System.out.println("子线程==============================");
                System.out.println("子线程==============================");
                System.out.println("子线程==============================");
                System.out.println("子线程品牌数量:"+threadCount);
                System.out.println("子线程==============================");
                System.out.println("子线程==============================");
                System.out.println("子线程==============================");
                System.out.println("子线程==============================");
            }
        };
        Thread child = new Thread(runnable, "子线程");
        child.start();

        Integer mainCount = brandDao.selectCount(null);
        System.out.println("主线程>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>");
        System.out.println("主线程>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>");
        System.out.println("主线程>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>");
        System.out.println("主线程>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>");
        System.out.println("主线程品牌数量:"+mainCount);
        System.out.println("主线程>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>");
        System.out.println("主线程>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>");
        System.out.println("主线程>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>");
        System.out.println("主线程>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>");
        try {
            //让主线程,休眠, 事务未提交, 证明子线程读取的数据是事务未提交前的数据
            Thread.sleep(2000);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
    }

第一次插入10个品牌数据 , 控制台打印如下

2021-09-25 14:55:01.160 DEBUG 9124 --- [io-10001-exec-7] c.a.g.product.dao.BrandDao.selectCount   : ==>  Preparing: SELECT COUNT( 1 ) FROM pms_brand 
2021-09-25 14:55:01.160 DEBUG 9124 --- [io-10001-exec-7] c.a.g.product.dao.BrandDao.selectCount   : ==> Parameters: 
2021-09-25 14:55:01.161 DEBUG 9124 --- [io-10001-exec-7] c.a.g.product.dao.BrandDao.selectCount   : <==      Total: 1
2021-09-25 14:55:01.161 DEBUG 9124 --- [            子线程] c.a.g.product.dao.BrandDao.selectCount   : ==>  Preparing: SELECT COUNT( 1 ) FROM pms_brand 
主线程>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
主线程>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
主线程>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
主线程>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
主线程品牌数量:25
主线程>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
主线程>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
主线程>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
主线程>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
2021-09-25 14:55:01.161 DEBUG 9124 --- [            子线程] c.a.g.product.dao.BrandDao.selectCount   : ==> Parameters: 
2021-09-25 14:55:01.163 DEBUG 9124 --- [            子线程] c.a.g.product.dao.BrandDao.selectCount   : <==      Total: 1
子线程==============================
子线程==============================
子线程==============================
子线程==============================
子线程品牌数量:15
子线程==============================
子线程==============================
子线程==============================
子线程==============================

第二次插入10个品牌数据 , 控制台打印如下

2021-09-25 14:55:07.328 DEBUG 9124 --- [io-10001-exec-8] c.a.g.product.dao.BrandDao.selectCount   : ==>  Preparing: SELECT COUNT( 1 ) FROM pms_brand 
2021-09-25 14:55:07.328 DEBUG 9124 --- [io-10001-exec-8] c.a.g.product.dao.BrandDao.selectCount   : ==> Parameters: 
2021-09-25 14:55:07.329 DEBUG 9124 --- [            子线程] c.a.g.product.dao.BrandDao.selectCount   : ==>  Preparing: SELECT COUNT( 1 ) FROM pms_brand 
2021-09-25 14:55:07.329 DEBUG 9124 --- [            子线程] c.a.g.product.dao.BrandDao.selectCount   : ==> Parameters: 
2021-09-25 14:55:07.329 DEBUG 9124 --- [io-10001-exec-8] c.a.g.product.dao.BrandDao.selectCount   : <==      Total: 1
主线程>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
主线程>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
主线程>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
主线程>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
主线程品牌数量:35
主线程>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
主线程>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
主线程>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
主线程>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
2021-09-25 14:55:07.329 DEBUG 9124 --- [            子线程] c.a.g.product.dao.BrandDao.selectCount   : <==      Total: 1
子线程==============================
子线程==============================
子线程==============================
子线程==============================
子线程品牌数量:25
子线程==============================
子线程==============================
子线程==============================
子线程==============================

从控制打印可以发现: 子线程 和 主线程所读取的数据不一致
原因就是: 子线程在service事务方法里面读取了事务未提交前的数据, 应该在service事务方法执行完之后再开启子线程读取数据库的数据

<think>好的,我需要回答用户关于医疗器械研发中是否涉及数据库事务处理或系统事务管理IT技术的问题。首先,我要理解用户的问题核心。用户想知道在医疗器械研发过中,是否有用到事务处理相关的技术,比如数据库事务或者系统层面的管理。 接下来,我需要查看提供的引用资料。引用1提到系统架构中的视图层、控制器层、服务层和DAO层,其中服务层处理业务逻辑,包括验证数据和与数据库交互,DAO层负责具体的数据操作。这涉及到数据库操作,事务管理通常在这样的分层架构中出现,尤其是在需要保证数据一致性的场景下。例如,当新增或修改设备信息时,可能需要事务来确保所有操作要么全部成功,要么全部回滚。 引用2讨论了医疗器械销售系统的开发,使用SSM框架和MySQL数据库。SSM框架中的Spring提供了事务管理功能,通常用于处理业务逻辑中的事务,确保数据操作的原子性、一致性、隔离性和持久性(ACID)。这说明在类似的系统中,事务处理是必要的,尤其是在处理订单、库存等关键业务时。 引用3提到使用数据库技术存储医疗器械信息,确保安全可靠。事务处理在数据库中是保证数据完整性的关键机制,尤其是在并发操作或复杂业务流中,比如同时更新多个表或记录时,事务能防止数据一致。 引用4是关于Java的Web开发技术,虽然直接涉及事务,但Java生态中的框架(如Spring)通常集成了事务管理功能,支持声明式事务和编事务,这在系统开发中会被广泛应用。 综合这些信息,医疗器械研发中的系统开发确实会涉及事务处理。例如,在设备信息管理、订单处理、库存更新等场景中,需要确保多个数据库操作要么全部成功,要么全部失败。比如,当用户提交一个设备入库操作时,系统可能需要同时更新库存表和设备信息表,这时事务管理就能确保两个操作的一致性。此外,使用Spring框架的事务管理可以简化开发,通过注解或配置管理事务边界,保证业务逻辑的正确执行。 用户可能还关心事务处理的具体应用场景和技术实现,比如在分布式系统中如何处理事务,或者如何保证高并发下的数据一致性。因此,在回答时应该涵盖这些方面,并提供实际例子,帮助用户更好地理解事务处理在医疗器械系统中的重要性。</think>医疗器械研发中**涉及数据库事务处理及系统事务管理技术**,尤其是在系统开发阶段。以下是具体分析: --- ### 一、数据库事务处理的应用 1. **数据一致性需求** 在医疗器械研发系统中,涉及设备信息录入、库存管理、订单处理等场景时,需要保证多个操作的原子性。例如: - 新增设备时需同时更新库存表和设备信息表,若中途失败需回滚所有操作 - 订单支付需同步扣减库存、生成物流记录,需通过事务确保一致性 此类场景必须使用数据库事务,避免出现部分成功导致数据矛盾[^3]。 2. **技术实现方式** - **MySQL事务**:通过`BEGIN TRANSACTION`、`COMMIT`、`ROLLBACK`命令实现ACID特性 - **Spring声明式事务**:在Java系统中,通过`@Transactional`注解自动管理事务边界[^4] ```java @Service public class DeviceService { @Transactional public void addDevice(Device device) { deviceDao.insert(device); // 插入设备信息 inventoryDao.updateStock(); // 更新库存 } } ``` --- ### 二、系统事务管理的必要性 1. **复杂业务流** 如医疗器械采购流包含:资格审核→合同生成→付款→发货→验收,涉及多系统交互。此时需要: - **分布式事务**:通过Seata、XA协议等实现跨系统操作的一致性[^2] - **补偿机制**:在微服务架构中采用Saga模式回滚已完成的子任务[^1] 2. **高并发场景** 当多用户同时操作同一设备库存时,需通过事务隔离级别(如`READ_COMMITTED`)和乐观锁(版本号控制)防止脏读、幻读等问题。 --- ### 三、典型应用场景示例 | 场景 | 事务技术应用 | 技术实现 | |---------------------|---------------------------------------|------------------------------| | 设备信息批量导入 | 全部成功或全部回滚 | MySQL事务+Spring事务管理 | | 采购合同生效 | 合同状态更新+审批记录写入+通知发送 | 分布式事务框架[^2] | | 库存预警自动补货 | 库存数据更新+供应商接口调用+订单生成 | Saga模式+消息队列 | ---
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值