在我的应用程序中,我有一个记录锁定机制,可以防止两个人同时处于记录的编辑 View 中。以下是在编辑 View 中调用记录时锁定记录的函数:
public function lockRecord($id = null) {
$this->loadModel('User');
$this->Model->id = $id;
$current = $this->Model->read(null, $id);
//Get the current logged-in user's ID
$userid = $current['Model']['requester_id'];
//Get the current lock expiry time
$lock_time = $this->Model->find('first', array(
'fields'=>array('Model.lock_expiry_time'),
'conditions'=>array('Model.id'=>$id)
)
);
//Get the ID of the user who has the record lock (if any)
$logged_user = $this->Model->find('first', array(
'fields'=>array('Model.lock_key'),
'conditions'=>array('Model.id'=>$id)
)
);
//Get that same user's full name
$full_name = $this->User->find('first', array(
'joins' => array(
array(
'table' => 'recordtable',
'alias' => 'Model',
'type' => 'INNER',
'conditions' => array('Model.lock_key = User.id')
)
)
)
);
$this->set('lock_time', $lock_time);
$this->set(compact($current));
$this->set(compact($logged_user));
$this->set(compact($full_name));
if(AuthComponent::user('id') != $logged_user['Msr']['lock_key'] && date("Y-m-d H:i:s") < $lock_time['Msr']['lock_expiry_time']) {
$this->Session->setFlash(__('This MSR is locked for editing by ' . $full_name['User']['full_name'] . '. Please try again in a few minutes or wait for this user to close the document.<br/>
(Lock expires at '. $lock_time['Msr']['lock_expiry_time'] . ')'));
$this->redirect(array('action' => 'view', $id));
} else {
//Set a new lock key and expiry time if the record is free for editing
$locksession = $this->Msr->query("UPDATE msrs SET lock_key = {$userid}, lock_expiry_time = ADDTIME(NOW(), '00:05:00') WHERE id = {$id}");
$this->set('locksession', $locksession);
}
}
当用户保存更改时,将调用unlockRecord函数来释放 key ,重置lock_expiry_time,并将用户重定向到“View” View :
public function unlockRecord($id = null) {
//Get a list of security groups
$groups = $this->Session->read('groups');
$this->Msr->id = $id;
//Reset the lock_key and the lock_expiry_time
$locksession = $this->Msr->query("UPDATE msrs SET lock_key = '', lock_expiry_time = '' WHERE id = {$id} ");
//If the module admin manually releases the lock, display a message
if(in_array('msr_module_admin', $groups)) {
$this->Session->setFlash(__('The MSR has been unlocked and is available for editing.'));
}
$this->redirect(array('action'=>'view', $id));
}
还有其他三个条件可以释放锁:
--管理员通过单击链接手动解除锁定。
--用户完全退出系统。
--锁定在设置后五分钟就会过期。
我需要在编辑 View 中的记录不再处于事件状态时随时释放锁定。例如,如果用户点击到另一个站点或点击我自己站点中的不同链接;任何使他们离开在编辑 View 中打开的记录的东西。 lock_key 应设置为“”,lock_expiry_time 设置为“”。我怎样才能做到这一点?
最佳答案
在网络编程中不可能可靠地识别出您网站上的页面已被用户放弃。
如果她关闭计算机/设备或断开网络连接,您的网站会发生什么情况?没有什么。如果她在编辑您的页面时点击书签栏中的链接,会发生什么?没有什么。你再也不会收到她的消息了。这就是为什么你的锁有过期时间。
因此,为了解决您的问题,您需要考虑缩短到期时间和/或减少页面放弃机会的方法。
一个选择:在使用 ajax-style 的编辑页面中放置一些 Javascript每隔一段时间请求一次,通过保活请求访问您的网站。您可以将其设置为每分钟访问您的网站。每次收到keepalive请求,都可以将过期时间延长90秒。
另一种选择:您可能已经注意到 StackOverflow 页面会抛出一个浏览器对话框,显示“您想离开此站点吗?”如果您在编辑帖子时按“后退”按钮。因此,每当您放弃页面时,实际上都会抛出该对话框。他们使用 onbeforeunload
浏览器中的事件。您可以执行相同的操作,在激活编辑页面时启用对话框,并在用户保存页面时禁用它。
浏览器不允许网页在页面卸载时强制执行除对话框之外的任何类型的操作。这样的功能很容易被网络蠕虫用来传播恶意软件。
关于php - 卸载事件页面时重置数据库字段值,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/43140951/