lorenzo/row-locker

用于通过 CakePHP ORM 锁定数据库行的插件

安装次数: 11,015

依赖关系: 0

建议者: 0

安全: 0

星标: 19

关注者: 4

分支: 7

开放问题: 1

类型:cakephp-plugin

2.0.0 2020-02-18 14:01 UTC

This package is auto-updated.

Last update: 2024-09-19 17:56:44 UTC


README

此插件通过在行的字段中存储时间戳和锁所有者的名称来简单实现行锁定。

在像 CMS 一样的系统中,当许多人同时尝试更改相同的记录时,行锁定可能很有用。通过锁定行,您可以防止或警告用户避免可能的数据覆盖。

安装

您可以使用 composer 将此插件安装到您的 CakePHP 应用程序中。

composer require lorenzo/row-locker

注意:上面的命令将安装与 CakePHP4 兼容的包。请参阅版本部分安装与 CakePHP3 兼容的包。

然后启用插件

bin/cake plugin load RowLocker

配置

您希望应用 RowLocker 的任何表都需要以下列

  • locked_time: DATETIME
  • locked_by (可选) 可以是识别您的用户的任何类型(INT,VARCHAR,UUID...)
  • locked_session (可选) VARCHAR(100) 用于调试目的

用法

要使用 RowLocker,首先需要将 LockableInterfaceLockableTrait 添加到您的实体中

use RowLocker\LockableInterface;
use RowLocker\LockableTrait;
...

class Article extends Entity implements LockableInterface
{
    use LockableTrait;

    ...
}

最后,将行为添加到您的 Table 类中

class ArticlesTable extends Table
{
    public function initialize()
    {
        ...
        $this->addBehavior('RowLocker.RowLocker');
    }
}

锁定行

要锁定任何行,首先加载它,然后对其调用 lock()。锁将保持5分钟

$article = $articlesTable->get($id);
$article->lock($userId, $sessionId); // both arguments are actaully optional
$articlesTable->save($article);

RowLocker 提供了一个使用 autoLock 查找器对一行或多行执行上述操作的快捷方式

$article = $articlesTable
    ->findById($id)
    ->find('autoLock', ['lockingUser' => $userId, 'lockingSession' => $sessionId])
    ->firstOrFail(); // This locks the row

$article->isLocked(); // return true

解锁行

只需在实体中调用 unlock()

$article->unlock();
$articlesTable->save($article);

查找未锁定行

要查找未锁定行(或由同一用户拥有的锁),请使用 unlocked 查找器

$firstUnlocked = $articlesTable
    ->find('unlocked', ['lockingUser' => $userId])
    ->firstOrFail();

安全锁定行

在高并发系统(许多用户尝试锁定同一行)中,强烈建议使用提供的 lockingMonitor() 函数

$safeLocker = $articlesTable->lockingMonitor();
// Safely lock the row
$safeLocker(function () use ($id, $userId, $sessionId) {
    $article = $articlesTable
        ->findById($id)
        ->find('autoLock', ['lockingUser' => $userId, 'lockingSession' => $sessionId])
        ->firstOrFail();
});

锁定监视器执行的操作是在 SERIALIZABLE 事务中运行内部可调用对象。

版本

RowLocker 有几个版本,每个版本都与 CakePHP 的不同版本兼容。通过下载标签或检出正确的分支来使用适当的版本。

  • 1.x 标签与 CakePHP 3.x 及更高版本兼容。
  • 2.x 标签与 CakePHP 4.0.x 兼容且稳定可用。