PHP队列执行任务的时候,如何防止进程之间抢夺资源?
phpcn_u747
phpcn_u747 2017-03-23 14:58:35
0
2
1267

PHP队列执行任务的时候,如何防止进程之间抢夺资源?
比如视频转码队列,每分钟会起一个进程去处理视频转码任务,每次从数据库获取10条
进程1已经获取了ID为10的视频去处理,一分钟后,如何防止进程2 拿到其他进程已经处理过的?
处理完成后,有异步通知,但是异步通知会有延迟,所以视频状态有可能修改不及时

phpcn_u747
phpcn_u747

모든 응답(2)
数据分析师

PHP 큐가 작업을 실행할 때 프로세스가 리소스를 빼앗는 것을 방지하는 방법은 무엇입니까? - PHP 중국어 웹사이트 Q&A - PHP 큐가 작업을 실행할 때 프로세스가 리소스를 빼앗는 것을 방지하는 방법은 무엇입니까? - PHP 중국어 웹사이트 Q&A

둘러보고 알아보세요. .

阿神

实际上有一个非常简单的办法,你可以利用数据库操作的原子性来实现,不需要那么复杂的锁机制,甚至队列。就按你的方法来,假设任务数据表 task 里有两个字段 id, status,我们定义status三个状态

0: 待处理
1: 正在处理
2: 处理完成

假设你有一堆 PHP 进程都用如下 SQL 语句去取出数据库里的待处理任务

SELECT * FROM task WHERE status = 0

取出来以后,我们为了防止其他用户不再重复取出要把它的状态标记为 1

UPDATE task SET status = 1 WHERE id = xxx

但是等等,这样就会产生如你所说的资源抢夺,但如果加上一个简单的技巧就可以避免,你把语句变成这样

UPDATE task SET status = 1 WHERE id = xxx AND status = 0

熟悉一点数据库的人可能会说这样还是避免不了抢夺,只是避免了重复写入。
我要说的是,能避免重复写入就够了,我们的进程在执行完这条操作后,去获取 affected_rows ,即更新的条数,根据数据库的原子性,只有第一个抢占的进程才会返回 1,它可以进行后面的操作。而剩下返回 0 的进程,直接进入下一个等待流程即可。

최신 다운로드
더>
웹 효과
웹사이트 소스 코드
웹사이트 자료
프론트엔드 템플릿