美文网首页
Laravel利用模型观察者处理缓存

Laravel利用模型观察者处理缓存

作者: 起个名字好难_98 | 来源:发表于2020-04-25 17:07 被阅读0次

还在为项目中缓存的管理而感到心累,操作DB后忘了清理缓存?缓存与DB不一致?等......话不多说先看思路

利用模型观察者Observer去监听模型更新、删除等操作,拿到当前操作模型,找出缓存key,删掉即可。原理很简单,下面看一下代码

先封装一个基础类

<?php

namespace App\Observers;

use Illuminate\Database\Eloquent\Model;

class Observer
{
    // 可监听的操作 creating created updating updated saving saved deleting deleted restoring restored

    /**
     * 当前操作模型
     *
     * @var Model
     */
    protected $model;

    /**
     * 获取所有的缓存key
     *
     * @return array
     */
    protected function getCacheKeys(): array
    {
        return [];
    }

    /**
     * 清理缓存
     *
     * @return int 删除数量
     */
    protected function clearCache(): int
    {
        $keys = $this->getCacheKeys();
        if ($keys === []) {
            return 0;
        }
        $redis = redis();
        $cacheKeys = [];
        foreach ($keys as $key) {
            // 如果是通配符,查一下所有的缓存key
            if (strpos($key, '*')) {
                $cacheKeys = array_merge($cacheKeys, $redis->keys($key));
            } else {
                $cacheKeys[] = $key;
            }
        }

        // 去重并删除缓存
        return $redis->del(array_unique($cacheKeys));
    }
}

定义一个GoodsSpu模型的观察者类GoodsSpuObserver.php 重点是getCacheKeys这个函数,配置好返回需要清理的缓存key,每个模型配置这个函数即可

<?php

namespace App\Observers;

use App\Common\RedisKey;
use App\Models\GoodsSpu;

class GoodsSpuObserver extends Observer
{
    public function saving(GoodsSpu $goodsSpu)
    {
        $this->model = $goodsSpu;

        parent::clearCache();
    }

    public function deleted(GoodsSpu $goodsSpu)
    {
        $this->model = $goodsSpu;

        parent::clearCache();
    }

    protected function getCacheKeys(): array
    {
        return [
            // 商品详情key
            sprintf(RedisKey::GOODS_DETAIL, $this->model->getAttribute('enterprise_id'), $this->model->getAttribute('id')),
        ];
    }
}

接着注册一下GoodsSpuObserver

App\Providers\AppServiceProvider中加入
// SPU表观察者
GoodsSpu::observe(new GoodsSpuObserver());

测试一下更新记录的时候缓存是不是会自动被刷掉

// 简单的更新一下记录
$goodsSpu = GoodsSpu::query()->where('id', '=', 1)->first();
$goodsSpu->update([
    'updated_at' => time()
]);

return 'success';

观察一下redis

image.png

结束

相关文章

网友评论

      本文标题:Laravel利用模型观察者处理缓存

      本文链接:https://www.haomeiwen.com/subject/ciukwhtx.html