列队中如何锁定已经开始执行的数据?

疑问

在列队中系统会 1 分站一次执行数据库中已经支付完成的订单 ( check = 1) 并且是已经完成的订单 ( ck = 1 ),那么在订单多的是就会出现 订单 1000 已经在执行,下次的列队执行又开始了导致了 订单 1000 被多次重复执行

一个小型商城,订单执行是调取其他 API 在订单支付完成的时候直接调用一下接口就可以,但是我遇到了列队间隔时间比较短就导致部分订单重复执行

我的想法是在一开始查询的时候就给数据库字段加上一个 lock = 1 ,在列队的时候查询 ( check = 1 , ck = 0 ,lock = 0 )的数据,但是这样我的订单列表 lock = 1 的操作还没完成, 下一个列队执行依旧会出现重复执行的问题?

换一个思路,列队执行的时候检测有没有其他列队正在执行,如果有就等待列队执行完成,如果没有则开始处理数据。这种事可行的

但我还是想弄懂 不去阻塞如何确保数据完美执行?

我是想明白怎么在 多任务 中确保数据不会被多个任务重复调用。我这里是用列队来表示,我有多个列队来处理数据,可能两个列队同时执行,那么找到的数据就会有部分同步的,怎么避免获取到数据出现一致?

thanks.
《L05 电商实战》
从零开发一个电商项目,功能包括电商后台、商品 & SKU 管理、购物车、订单管理、支付宝支付、微信支付、订单退款流程、优惠券等
《L03 构架 API 服务器》
你将学到如 RESTFul 设计风格、PostMan 的使用、OAuth 流程,JWT 概念及使用 和 API 开发相关的进阶知识。
最佳答案

或者优化队列,每次下单的时候,使用redis 的 zset 记录 orderid 和 created_at,其他 created_at 为 score,订单完成的时候移除这个 orderid, 这样一分钟只需要查一下 redis 的zset,性能比查询大的数据库快太多了

4年前 评论
讨论数量: 4

$schedule->job(new Job)->withoutOverlapping(); 这样可否

4年前 评论

你描述的像是调度任务而不是队列,对于调度任务你可以使用withoutOverlapping 防止重复执行,但是默认是通过文件系统实现的,所以只支持单机。如果是队列系统,可能是你的队列只支持单slave。

4年前 评论
StringKe

@Kamicloud @woaini 我的思路是在不避免重复执行的时候处理数据(现阶段就是数据会出现重复)

4年前 评论

或者优化队列,每次下单的时候,使用redis 的 zset 记录 orderid 和 created_at,其他 created_at 为 score,订单完成的时候移除这个 orderid, 这样一分钟只需要查一下 redis 的zset,性能比查询大的数据库快太多了

4年前 评论

讨论应以学习和精进为目的。请勿发布不友善或者负能量的内容,与人为善,比聪明更重要!