Winter CMS resources and help articles

Simple and to the point. Optimized by the community.

Lock backend records to prevent updates by different users

0
by mjauvin, last modified on September 14th, 2023

To prevent concurrent access to record updates from the backend, use the following trick:

use BackendAuth;
use Cache;
use Flash;
use Redirect;
use Request;
use Session;

public function boot()
{   
    Event::listen('backend.page.beforeDisplay', function ($controller, $action, $params) {
        if ($action === 'update') {
            $recordId = $params[0];
            if (! $model = $controller->formFindModelObject($recordId)) {
                return;
            }
            $cacheKey = sprintf("%s-%d", str_replace('\\', '-', get_class($model)), $recordId);

            $cacheValue = [
                'ip' => Request::ip(),
                'token' => Session::get('_token'),
                'user' => BackendAuth::getUser()->login,
            ];

            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']) {
                $user = strtoupper(array_get($lock, 'user'));
                Flash::error("Opening in PREVIEW mode, user {$user} is updating the record.");
                return Redirect::to($controller->actionUrl('preview',$recordId));
            }
        } else if ($cacheKey = Session::pull('lastLock')) {
            // unlock record for any other backend page access
            Cache::forget($cacheKey);
        }
    });
}

Discussion

1 comment

0
AIC BV
Post on October 20th, 2023 8:10 AM

You need this check to prevent errors in setting pages

if (!method_exists($controller, 'formFindModelObject')) {
    return;
}
We use cookies to measure the performance of this website. Do you want to accept these cookies?