【问题标题】:Laravel 4.2 prevent query from running at the same timeLaravel 4.2 防止查询同时运行
【发布时间】:2016-06-08 19:37:03
【问题描述】:

使用 laravel 4.2,我有一个每分钟运行一次的 Cron 作业,它以类似的方式从数据库中获取作业列表:

$records = DB::table('jobs')->where('finished', '=', 0)->
whereBetween('created_at', [Carbon::now(),Carbon::now()->addMinutes(2)])->get();
// Process records
..

完成后,它会将“finished”字段更新为1。

现在由于 cron 作业每分钟都在运行,我需要确保如果 cron 作业在前一个作业完成之前开始,它不会运行或不选择相同的记录。

【问题讨论】:

  • 听起来你需要一个合适的队列系统。为了模拟这一点,您可以在 cron 进程读取的文件系统(或类似 memcached 的东西)上设置某种标志,以查看作业当前是否正在运行以允许它重新安排自己。请小心,因为即使您确保这些东西不会同时运行,它们也可能会不同步(如果您完全关心它们的运行顺序)。
  • @Emn1ty 在我的情况下订单是不必要的,但是我想看看是否有比将所有行 ID 存储在文件中更简单/更好的解决方案
  • 使用事务怎么样?
  • @Daenu 这是一个好主意,只是在测试它。带锁它应该可以工作
  • 很高兴我为解决方案做出了贡献

标签: php laravel laravel-4 cron race-condition


【解决方案1】:

使用事务和 lockForUpdate 解决了这个问题:

DB::beginTransaction();
$records = DB::table('jobs')->where('finished', '=', 0)->lockForUpdate()->get();
// process
DB::commit();

【讨论】:

    猜你喜欢
    • 2015-04-18
    • 1970-01-01
    • 1970-01-01
    • 2023-01-30
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-05-11
    • 1970-01-01
    相关资源
    最近更新 更多