@@ -15,7 +15,7 @@ internal class RedisCacheService<T>(IRedisClient redisClient, IOptions<CacheConf
1515 private readonly CacheConfigurationOptions _config = options . Value ;
1616 private readonly string _moduleName = typeof ( T ) . Assembly . GetName ( ) . Name ! ;
1717 private readonly TimeSpan _lockExpiry = options . Value . DistributedLockDuration ;
18- private readonly TimeSpan _lockRetryDelay = TimeSpan . FromMilliseconds ( 20 ) ;
18+ private readonly TimeSpan _lockRetryDelay = TimeSpan . FromMilliseconds ( 10 ) ;
1919
2020 public async ValueTask < T > GetOrCreateAsync ( string key , Func < CancellationToken , ValueTask < T > > factory ,
2121 TimeSpan ? expiration = null , IReadOnlyCollection < string > ? tags = null , CancellationToken token = default )
@@ -24,29 +24,35 @@ public async ValueTask<T> GetOrCreateAsync(string key, Func<CancellationToken, V
2424 ? KeyFormatHelper . GetPrefixedKey ( key )
2525 : KeyFormatHelper . GetPrefixedKey ( key , _moduleName ) ;
2626
27- var lockKey = $ " { prefixedKey } :lock" ;
27+ var lockKey = KeyFormatHelper . GetLockKey ( prefixedKey ) ;
2828 var lockValue = Guid . NewGuid ( ) . ToString ( ) ;
2929
3030 while ( true )
3131 {
3232 token . ThrowIfCancellationRequested ( ) ;
3333
34- // Acquire lock before getting the value
35- var lockAcquired = await AcquireLockAsync ( lockKey , lockValue ) ;
34+ var isLocked = await _redisDatabase . Database . KeyExistsAsync ( lockKey ) ;
3635
37- if ( ! lockAcquired )
36+ if ( isLocked )
3837 {
3938 await WaitForLockReleaseAsync ( lockKey , token ) ;
4039 continue ;
4140 }
4241
4342 var cachedValue = await _redisDatabase . GetAsync < T > ( prefixedKey ) ;
44-
4543 if ( cachedValue != null )
4644 {
47- await ReleaseLockAsync ( lockKey , lockValue ) ;
4845 return cachedValue ;
4946 }
47+
48+ var lockAcquired = await AcquireLockAsync ( lockKey , lockValue ) ;
49+
50+ if ( ! lockAcquired )
51+ {
52+ await WaitForLockReleaseAsync ( lockKey , token ) ;
53+ continue ;
54+ }
55+
5056 break ;
5157 }
5258
@@ -58,7 +64,6 @@ public async ValueTask<T> GetOrCreateAsync(string key, Func<CancellationToken, V
5864 }
5965 finally
6066 {
61- // Release the lock
6267 await ReleaseLockAsync ( lockKey , lockValue ) ;
6368 }
6469 }
@@ -119,7 +124,7 @@ public async ValueTask RemoveByTagAsync(string tag, CancellationToken token = de
119124 var tagKey = _config . KeyPrefixForIsolation == KeyPrefix . None
120125 ? KeyFormatHelper . GetTagKey ( tag )
121126 : KeyFormatHelper . GetTagKey ( tag , _moduleName ) ;
122-
127+
123128 var keys = await _redisDatabase . SetMembersAsync < string > ( tagKey ) ;
124129 if ( keys . Length > 0 )
125130 {
0 commit comments