44
55namespace Php \Support \Laravel \Traits \Models ;
66
7+ use Illuminate \Cache \RedisStore ;
78use Illuminate \Database \Eloquent \Model ;
89use Illuminate \Support \Facades \Cache ;
910use Illuminate \Support \Facades \Config ;
11+ use Php \Support \Laravel \Traits \Models \Cachers \CacherContract ;
12+ use Php \Support \Laravel \Traits \Models \Cachers \DummyCacher ;
13+ use Php \Support \Laravel \Traits \Models \Cachers \RedisCacher ;
1014
1115/**
1216 * @mixin Model
1317 */
1418trait HasModelEntityCache
1519{
20+ public static bool $ cacheEnable = true ;
21+
22+ public static function disableCache (): void
23+ {
24+ static ::$ cacheEnable = false ;
25+ }
26+
1627 public static function bootHasModelEntityCache (): void
1728 {
1829 static ::registerEventsForCache ();
1930 }
2031
32+ protected static array $ cacheStores = [];
33+
34+ protected static function resolveStoreDriver (): CacherContract
35+ {
36+ return static ::$ cacheStores [static ::class] ??= static ::resolveStoreDriverCls ();
37+ }
38+
39+ protected static function getEntityCacheResolver (): ?CacherContract
40+ {
41+ $ cacheResolverCls = Config::get ('cache.resolver.class ' );
42+ if (class_exists ($ cacheResolverCls )) {
43+ return $ cacheResolverCls (static ::class, Cache::getStore ());
44+ }
45+
46+ return null ;
47+ }
48+
49+ protected static function resolveStoreDriverCls (): CacherContract
50+ {
51+ if ($ cacheResolverCls = static ::getEntityCacheResolver ()) {
52+ return $ cacheResolverCls ;
53+ }
54+
55+ return $ cacheResolver ?? match (Cache::getStore ()::class) {
56+ RedisStore::class => new RedisCacher (static ::class, Cache::getStore ()),
57+ default => new DummyCacher (static ::class),
58+ };
59+ }
60+
2161 protected static function registerEventsForCache (): void
2262 {
2363 static ::saved ($ fn = static ::cacheForgetFn ());
@@ -51,42 +91,12 @@ public static function cacheForgetByKey(string $key): bool
5191 return true ;
5292 }
5393
54- return Cache:: forget ( static ::cachePrefixKey ( $ key) );
94+ return static ::resolveStoreDriver ()-> forgetByKey ( $ key );
5595 }
5696
57- protected static function cacheForgetCollection (string $ key = ' list:* ' ): bool
97+ protected static function cacheForgetCollection (string $ key = null ): bool
5898 {
59- return static ::removeByTemplate (static ::cachePrefixKey ($ key ));
60- }
61-
62- private static function removeByTemplate (string $ template )
63- {
64- /** @var \Illuminate\Cache\RedisStore $store */
65- $ store = Cache::getStore ();
66- $ client = $ store ->connection ()->client ();
67-
68- if (Config::get ('database.redis.client ' ) === 'predis ' ) {
69- $ key = $ store ->getPrefix () . $ template ;
70- } else {
71- $ key = $ client ->_prefix ($ template );
72- }
73-
74- $ lua = <<<LUA
75- local keys = unpack(redis.call('keys', KEYS[1]))
76- if not keys then
77- return 0
78- end
79-
80- return redis.call('del', keys)
81- LUA ;
82-
83- $ result = $ client ->eval (
84- $ lua ,
85- 1 ,
86- $ key
87- );
88-
89- return $ result > 0 ;
99+ return static ::resolveStoreDriver ()->cacheForgetCollection ($ key );
90100 }
91101
92102 protected static function cacheKeyName (): string
@@ -96,23 +106,14 @@ protected static function cacheKeyName(): string
96106
97107 protected static function cachePrefixKey (string $ key = null , string $ prefix = null ): string
98108 {
99- $ prefix ??= class_basename (static ::class);
100-
101- return "app:models: $ prefix: $ key " ;
109+ return static ::resolveStoreDriver ()->prefixKey ($ key , $ prefix );
102110 }
103111
104112 protected static function cacheTtl (): int
105113 {
106114 return 60 * 60 ;
107115 }
108116
109- public static bool $ cacheEnable = true ;
110-
111- public static function disableCache (): void
112- {
113- static ::$ cacheEnable = false ;
114- }
115-
116117 public static function remember (callable $ fn , string $ key ): mixed
117118 {
118119 if (!static ::$ cacheEnable ) {
0 commit comments