Laravel Eloquent模型中乐观锁的实现

发布时间 - 2023-04-21 00:00:00    点击率:

本篇文章给大家带来了关于laravel的相关知识,其中主要跟大家介绍laravel eloquent模型中乐观锁的实现,有代码示例,感兴趣的朋友下面一起来看一下吧,希望对大家有帮助。

在app/Utils/Traits目录下创建OptimisticLockTrait.php,代码如下:
namespace App\Utils\Traits;use Illuminate\Database\Eloquent\Builder;trait OptimisticLockTrait{

    /**
     * @var array $optimisticConditions
     * @var array $bindings
     */
    protected $optimisticConditions, $bindings;
    /**
     * @var string $optimisticConditionRaw
     */
    protected $optimisticConditionRaw;

    /**
     * save 时增加乐观锁条件
     * @param Builder $builder
     */
    protected function performUpdate(Builder $builder)
    {
        if (!empty($this->optimisticConditions)) {
            foreach ($this->optimisticConditions as $field => $value) {
                if (is_array($value)) {
                    $count = count($value);
                    if ($count >= 3) {
                        switch (strtoupper($value[1])) {
                            case 'IN':
                                $builder->whereIn($value[0], $value[2]);
                                break;
                            case 'NOT IN':
                                $builder->whereNotIn($value[0], $value[2]);
                                break;
                            case 'BETWEEN':
                                $builder->whereBetween($value[0], $value[2]);
                                break;
                            case 'NOT BETWEEN':
                                $builder->whereNotBetween($value[0], $value[2]);
                                break;
                            default:
                                $builder->where($value[0], $value[1], $value[2]);
                        }
                    } else {
                        $builder->where($value);
                    }
                } else {
                    $builder->where($field, $value);
                }
            }
        }
        // 原始条件注入
        if ($this->optimisticConditionRaw)
            $builder->whereRaw($this->optimisticConditionRaw, $this->bindings);

        return $this->clearOptimistic()->perFormUpdating($builder);

    }


    /**
     * updating with optimistic
     *
     * @param Builder $builder
     * @return bool
     */
    protected function perFormUpdating(Builder $builder)
    {

        // If the updating event returns false, we will cancel the update operation so
        // developers can hook Validation systems into their models and cancel this
        // operation if the model does not pass validation. Otherwise, we update.
        if ($this->fireModelEvent('updating') === false) {
            return false;
        }

        // First we need to create a fresh query instance and touch the creation and
        // update timestamp on the model which are maintained by us for developer
        // convenience. Then we will just continue saving the model instances.
        if ($this->usesTimestamps()) {
            $this->updateTimestamps();
        }

        // Once we have run the update operation, we will fire the "updated" event for
        // this model instance. This will allow developers to hook into these after
        // models are updated, giving them a chance to do any special processing.
        $dirty = $this->getDirty();
        $res = 0;
        if (count($dirty) > 0) {
            $res = $this->setKeysForSaveQuery($builder)->update($dirty);

            $this->syncChanges();

            $this->fireModelEvent('updated', false);
        }
        return !empty($res);
    }

    // 清除乐观锁条件
    function clearOptimistic()
    {
        $this->optimisticConditions = null;
        $this->optimisticConditionRaw = null;
        return $this;
    }


    // 设置乐观锁条件字段名列表
    function setOptimistic(array $optimisticConditions)
    {
        $this->optimisticConditions = $optimisticConditions;
        return $this;
    }

    // 设置乐观锁原始条件字段名列表
    function setOptimisticRaw(string $optimisticConditionRaw, array $bindings = [])
    {
        $this->optimisticConditionRaw = $optimisticConditionRaw;
        $this->bindings = $bindings;
        return $this;
    }}

乐观锁使用说明

1、在模型中(Models)或模型父类使用

/**
* App\Models\BaseModel
* @mixin \Eloquent
* @method static \Illuminate\Database\Eloquent\Builder|BaseModel newModelQuery()
* @method static \Illuminate\Database\Eloquent\Builder|BaseModel newQuery()
* @method static \Illuminate\Database\Eloquent\Builder|BaseModel query()
*/class BaseModel extends Model{
  use OptimisticLockTrait;}

2、使用方法:

 $ord = Order::find(1);
 $ord->payment_status = 1;
 if(!$model->setOptimistic(['payment_status' => 0]))->save())
   throws new Exception('订单已付过款了');

或者使用原始SQL方式:

 $ord = Order::find(1);
 $ord->payment_status = 1;
 if(!$model->setOptimisticRaw('payment_status = ?',[1]))->save())
   throws new Exception('订单已付过款了');

如果同一对象小涉及到多次更新,则可以清除锁条件

$ord->clearOptimistic();

以上就是乐观锁的实现方式,在实际开发中比较常用也很有必要。

推荐学习:《laravel视频教程》


# laravel  # php  # sql  # 父类  # 对象  # 字段名  # 感兴趣  # 也很  # 带来了  # 给大家  # 有必要  # 涉及到  # 则可  # 相关知识  # 目录下 


相关栏目: 【 网站优化151355 】 【 网络推广146373 】 【 网络技术251813 】 【 AI营销90571


相关推荐: 如何自己制作一个网站链接,如何制作一个企业网站,建设网站的基本步骤有哪些?  如何制作一个表白网站视频,关于勇敢表白的小标题?  Laravel API资源(Resource)怎么用_格式化Laravel API响应的最佳实践  合肥制作网站的公司有哪些,合肥聚美网络科技有限公司介绍?  青岛网站建设如何选择本地服务器?  Laravel如何使用Service Provider注册服务_Laravel服务提供者配置与加载  Laravel如何实现API版本控制_Laravel版本化API设计方案  网站制作报价单模板图片,小松挖机官方网站报价?  DeepSeek是免费使用的吗 DeepSeek收费模式与Pro版本功能详解  Laravel如何实现用户注册和登录?(Auth脚手架指南)  Laravel全局作用域是什么_Laravel Eloquent Global Scopes应用指南  高端网站建设与定制开发一站式解决方案 中企动力  详解Oracle修改字段类型方法总结  1688铺货到淘宝怎么操作 1688一键铺货到自己店铺详细步骤  公司网站制作需要多少钱,找人做公司网站需要多少钱?  简单实现jsp分页  Laravel策略(Policy)如何控制权限_Laravel Gates与Policies实现用户授权  详解免费开源的.NET多类型文件解压缩组件SharpZipLib(.NET组件介绍之七)  网站制作大概多少钱一个,做一个平台网站大概多少钱?  Laravel怎么实现软删除SoftDeletes_Laravel模型回收站功能与数据恢复【步骤】  Laravel路由Route怎么设置_Laravel基础路由定义与参数传递规则【详解】  bing浏览器学术搜索入口_bing学术文献检索地址  Laravel如何生成URL和重定向?(路由助手函数)  Laravel项目结构怎么组织_大型Laravel应用的最佳目录结构实践  微博html5版本怎么弄发语音微博_语音录制入口及时长限制操作【教程】  Linux后台任务运行方法_nohup与&使用技巧【技巧】  北京网页设计制作网站有哪些,继续教育自动播放怎么设置?  手机网站制作平台,手机靓号代理商怎么制作属于自己的手机靓号网站?  济南网站建设制作公司,室内设计网站一般都有哪些功能?  python中快速进行多个字符替换的方法小结  如何快速查询网址的建站时间与历史轨迹?  bootstrap日历插件datetimepicker使用方法  jquery插件bootstrapValidator表单验证详解  如何在Ubuntu系统下快速搭建WordPress个人网站?  Java类加载基本过程详细介绍  微博html5版本怎么弄发超话_超话进入入口及发帖格式要求【教程】  Android利用动画实现背景逐渐变暗  C#如何调用原生C++ COM对象详解  Win11怎么关闭资讯和兴趣_Windows11任务栏设置隐藏小组件  iOS发送验证码倒计时应用  Laravel如何实现API资源集合?(Resource Collection教程)  如何快速上传自定义模板至建站之星?  如何快速生成高效建站系统源代码?  Laravel Admin后台管理框架推荐_Laravel快速开发后台工具  如何快速搭建FTP站点实现文件共享?  详解Nginx + Tomcat 反向代理 负载均衡 集群 部署指南  Laravel怎么使用Intervention Image库处理图片上传和缩放  如何为不同团队 ID 动态生成多个“认领值班”按钮  Laravel中Service Container是做什么的_Laravel服务容器与依赖注入核心概念解析  如何解决hover在ie6中的兼容性问题