Lock backend records to prevent updates by different users
0
To prevent concurrent access to record updates from the backend, use the following trick:
use BackendAuth;
use Cache;
use Carbon\Carbon;
use Flash;
use Redirect;
use Request;
use Session;
public function boot()
{
Event::listen('backend.page.beforeDisplay', function ($controller, $action, $params) {
if (!method_exists($controller, 'formFindModelObject')) {
return;
}
if ($action === 'update') {
$recordId = $params[0];
if (! $model = $controller->formFindModelObject($recordId)) {
return;
}
$controller->initForm($model);
$cacheKey = sprintf("%s-%d", str_replace('\\', '-', get_class($model)), $recordId);
$cacheValue = [
'ip' => Request::ip(),
'token' => Session::get('_token'),
'user' => BackendAuth::getUser()->login,
'ts' => Carbon::now()->timestamp,
];
if (!$lock = Cache::get($cacheKey)) {
// lock the record for an hour
Cache::put($cacheKey, $cacheValue, 3600);
if ($lastLock = Session::get('lastLock')) {
Cache::forget($lastLock);
}
Session::put('lastLock', $cacheKey);
} elseif ($lock['token'] !== $cacheValue['token']) {
$ts = (new Carbon(array_get($lock, 'ts')))->toDateTimeString();
$user = strtoupper(array_get($lock, 'user'));
Flash::error("Opening in PREVIEW mode, user {$user} is updating the record.");
return Redirect::back();
}
} else if ($cacheKey = Session::pull('lastLock')) {
// unlock record for any other backend page access
Cache::forget($cacheKey);
}
});
}
You need this check to prevent errors in setting pages