首页 > 其他分享 >两个定时任务的并发问题,导致数据处理的顺序和状态变得混乱

两个定时任务的并发问题,导致数据处理的顺序和状态变得混乱

时间:2024-12-29 22:54:11浏览次数:1  
标签:状态 并发 任务 数据处理 定时 推送 数据

1. 背景:

有两个定时任务在特定时间触发,同时对数据进行操作,且任务之间存在并发执行的场景。主要涉及的表为 lingyejun_task,涉及到的操作有:数据插入、推送、状态更新和错误处理。

定时任务A负责生成数据,定时任务B负责将生成好的数据处理并推送到第三方系统,由于出问题的时候定时任务A生成数据是一条一条循环生成,并没有声明事务,所以会有一些不符合预期的情况发生,下面让我们详细看看。

2. 事件流程(简化描述):

  • 10点:定时任务A执行,写入 3 条订单明细数据(其实一共有12条数据,但并未放到一个事务中)。导致定时任务B也在这个时间点触发的时候,任务B只能查到这 3 条数据并进行推送。由于并发,任务B在处理时错误地将这 3 条数据的状态更新为“已推送”,实际应该将12条数据全部推送完毕才应该改为已推送。这里已经生成了12条数据,只是在当时并发时,只把推送任务B触发前三条推送了,且推送成功了,后9条没推送。

  • 11点:任务B执行时,将后面的9条数据进行了推送,但是下游系统有订单号唯一键校验,推送失败,将这9条数据更改为推送失败。在此时任务A又生成了 4 条新的数据。接着进行推送,推送了 4 条新生成的数据,推送失败,报错信息为:“没有满足 msg contains 逻辑”。由于错误,任务B按失败处理,并根据唯一键重新更新状态,将 4 条数据标记为失败。

  • 12点:查询时,系统最终查到 16 条数据,任务再次推送数据。此时报错信息为:“Data is duplicated, please check”,任务按成功处理,并将状态更新为成功。然而,系统实际上只有前三条数据是成功推送的,后 13 条数据没有推送成功。

3. 问题分析:

  • 并发问题:两个定时任务在相同或接近的时间点触发,导致数据写入、推送和状态更新操作的顺序出现了问题,造成了资源竞争和数据不一致。任务A和任务B可能试图同时处理相同的数据。

  • 错误的状态更新:由于任务A的错误(将3条数据退单),任务2在执行时认为这些数据已经存在,因此没有进行正确的推送。最终导致状态更新和数据推送顺序错乱。

  • 推送失败:11点任务B推送时,报错“没有满足 msg contains 逻辑”,这可能是由于并发导致的查询结果不一致,或者推送接口的逻辑判断出现了问题。

  • 数据重复问题:12点再进行推送时,系统提示“Data is duplicated”,这说明系统检测到重复数据。实际上,这表明任务A和任务B的处理逻辑并未正确处理数据的唯一性或排他性,导致数据处理出现问题。

  • 部分成功,部分失败:虽然最终显示“成功”,但实际上,只有前三条数据推送成功,其余13条数据失败。系统没有正确识别哪些数据推送成功,哪些失败,导致错误的状态更新。

4. 解决方案与优化建议:

  • 同步机制:考虑使用同步机制(如分布式锁、任务队列)来确保两个任务不会同时操作相同的数据或资源,避免并发冲突。

    • 可以使用 Redis 或数据库锁来控制任务的并发执行,确保任务之间不会相互干扰。
  • 任务分隔与调度优化:对定时任务的执行进行错峰调度,避免两个任务在相同时间点执行。可以使用调度框架(如 Quartz)来优化任务的执行时机。

  • 数据状态检查:在推送数据之前,进行严格的数据状态检查,确保数据状态正确且没有重复,避免出现状态更新错误。比如,在任务执行前,检查目标数据是否已存在并已被其他任务处理。

  • 事务控制:使用数据库事务来保证数据一致性。对于涉及多步操作(如写入、更新、推送)的任务,可以考虑将其放入一个事务中,确保任务的一致性。如果某一部分操作失败,则回滚整个任务的执行。

  • 推送逻辑的改进:推送失败时,采用更明确的错误处理和重试机制。避免因一次错误导致所有数据的失败标记。可以在推送过程中记录详细的错误信息,并根据具体的错误进行细化处理。

  • 日志与监控:加强任务执行的日志记录和监控。对于每个定时任务,记录其执行的详细过程、成功与失败的情况、数据变更和状态更新等。通过日志分析可以帮助及时发现并解决问题。

  • 异常捕获与重试机制:对推送失败进行合理的异常捕获和重试机制,避免一次错误导致整个流程的中断。

5. 总结:

本问题的核心是并发操作导致的资源竞争和数据一致性问题,主要体现在定时任务之间没有有效的同步和协调,导致数据写入、推送和状态更新的顺序错误。为解决这一问题,需要在任务执行时引入更严格的同步控制、事务管理和错误处理机制,同时优化任务调度和数据处理逻辑,确保并发任务间的数据一致性和稳定性。

 

本篇文章如有帮助到您,请给「翎野君」点个赞,感谢您的支持。

首发链接:https://www.cnblogs.com/lingyejun/p/18639756

标签:状态,并发,任务,数据处理,定时,推送,数据
From: https://www.cnblogs.com/lingyejun/p/18639756

相关文章

  • Java 大视界 -- Java 大数据测试框架与实践:确保数据处理质量(十二)
           ......
  • Go 并发之goroutine和Channel讲解
    目录1并发1.1简介1.2Goroutine1.2.1简介1.2.2特点1.2.3检测数据访问冲突1.2.4示例1.3通道(Channel)1.3.1普通通道1.3.1.1简介1.3.1.2声明通道1.3.1.3普通通道示例1.3.2带缓冲区通道1.3.2.1简介1.3.2.2带缓冲区通道示例1.3.3遍历1.3.3.1for遍历1.3.3.2range遍历......
  • Go 并发之WaitGroup,并发锁,Context
    目录1Go并发1.1WaitGroup1.2并发锁1.2.1互斥锁1.2.2读写互斥锁1.2.3sync.Once1.2.4sync.Map1.3Context1.3.1简介1.3.2主要功能1.3.3使用示例1.3.3.1取消信号1.3.3.2设置超时1.3.3.3传递值1Go并发1.1WaitGroupsync.WaitGroup是Go标准库提供的一种同步原语,常......
  • 高级java每日一道面试题-2024年12月27日-并发篇-锁的优化机制了解吗 ?
    如果有遗漏,评论区告诉我进行补充面试官:锁的优化机制了解吗?我回答:在Java高级面试中,锁的优化机制是一个重要且常见的考点。以下是对Java锁优化机制的详细解释:一、锁的基本概念锁是多线程编程中至关重要的同步机制,用于确保线程间共享数据的正确性。然而,使用锁也会引......
  • Java技术深度解析:探索并发编程的艺术与实战
    Java技术深度解析:探索并发编程的艺术与实战在当今的软件开发领域,高效处理多任务、充分利用多核CPU资源已成为衡量应用性能的关键指标之一。Java,作为一种广泛应用于企业级开发的编程语言,凭借其强大的并发处理能力,在众多编程语言中脱颖而出。本文将深入探讨Java并发编程的核......
  • C# 和 Go 的协同开发:打造高效并发与企业级应用的最佳实践
    在现代软件开发中,微服务架构和分布式系统成为主流。开发者面临着多种挑战,其中最常见的两个需求是高并发处理和复杂的企业级业务逻辑。C#和Go作为两种广泛使用的编程语言,各自有独特的优势,在应对这些挑战时能够发挥不同的作用。C#强调企业级开发的完整性和稳定性,特别适合构......
  • 从高并发到企业级应用:C# 和 Go 的完美结合
    在现代软件开发中,随着微服务架构和分布式系统的广泛应用,开发者需要应对各种高并发、高性能的需求。而在选择编程语言时,C#和Go是两种非常流行且各具优势的语言,分别擅长不同的应用场景。C#,以其强大的企业级开发支持和丰富的生态系统在后端、桌面和Web开发中占据重要地位;而......
  • Java 并发编程:掌握多线程的四个核心要点
    Java并发编程是后端开发中至关重要的一部分,它涉及到如何有效地使用多核处理器、提高程序的执行效率,并确保线程安全。无论是面试还是实际项目开发,掌握多线程编程的核心要点都至关重要。本文将围绕Java多线程编程的四个核心要点展开,帮助读者深入理解并发编程的基本原理、应用......
  • 【Java 并发编程】详解
    Java并发编程在当今的软件开发领域,随着多核处理器的广泛应用以及对系统性能要求的不断提高,Java并发编程变得愈发重要。它允许我们充分利用计算机的多核资源,同时处理多个任务,提高程序的执行效率和响应能力。然而,并发编程并非易事,它涉及到诸多复杂的概念、机制以及需要注......
  • Python读取栅格图像并对像元数据处理后导出到表格文件中
      本文介绍基于Python语言中的gdal模块,读取一景.tif格式的栅格遥感影像文件,提取其中每一个像元的像素数值,对像素值加以计算(辐射定标)后,再以一列数据的形式将计算后的各像元像素数据保存在一个.csv格式文件中的方法。  首先,我们明确一下本文的需求。现在有一个栅格遥感影像文件......