使用数据库事务重试Laravel PHP脚本10秒


Retrying Laravel PHP script with database transaction for 10 seconds

我使用Laravel 4.2,我有一个巨大的try/catch块运行数据库事务。有多种类型的异常

$startTime = 0;
try {
DB::beginTransaction();
//code
DB::commit();
}catch(Exception1 $e){
DB::rollBack();
//so something with this, save in db and throw new Exception
if($startTime < 10) retry the whole process
}catch(Exception2 $e){
DB::rollBack();
//so something with this, save in db and throw new Exception
if($startTime < 10) retry the whole process
}catch(Exception $e){
DB::rollBack();
//so something with this, save in db and throw new Exception
if($startTime < 10) retry the whole process
}

我希望整个进程重试10秒。每次失败,我都需要回滚更改并再试一次。

我怎样才能正确地做这件事?谢谢。

我会将"try"中的整个代码包装成执行事务/回滚的函数,并运行该函数,只要它返回false并且它开始运行不到10秒。我在脑子里打字,也许我漏掉了什么,但我希望你能明白:

function doIt() {
  try {
    DB::beginTransaction();
    /**
     * whatever
     */
    DB::commit();
    return true;
  } catch (Exception $e) {
    DB::rollBack();
    /**
     * do something more if you need
     */
    return false;
  }
}
$start = time();
do {
  $IdidIt = doIt();
} while(!$IdidIt && (time() - $start <= 10));

更新,根据注释:

function tryFor10Seconds(Closure $closure) {
  $runTheClosure = function ($closure) {
    try {
      DB::beginTransaction();
      $closure();
      DB::commit();
      return true;
    } catch (Exception $e) {
      DB::rollBack();
      // handle the exception if needed, log it or whatever
      return false;
    }
  };
  $start = time();
  do {
    $result = $runTheClosure($closure);
  } while(!$result && (time() - $start <= 10));
  return $result;
}

基本上你可以这样调用它:

$success = tryFor10Seconds(function() use ($model1, $model2, $whatever) {
  $model1->save();
  $model2->save();
  $whatever->doSomethingWithDB();
});
if (!$success) {
  // :(
}