Merge remote-tracking branch 'origin/v12/dev' into v13/dev
This commit is contained in:
@@ -9,6 +9,9 @@ namespace Umbraco.Cms.Core.Cache;
|
||||
/// </summary>
|
||||
public class ObjectCacheAppCache : IAppPolicyCache, IDisposable
|
||||
{
|
||||
private static readonly TimeSpan _readLockTimeout = TimeSpan.FromSeconds(5);
|
||||
private static readonly TimeSpan _writeLockTimeout = TimeSpan.FromSeconds(5);
|
||||
|
||||
private readonly ReaderWriterLockSlim _locker = new(LockRecursionPolicy.SupportsRecursion);
|
||||
private bool _disposedValue;
|
||||
|
||||
@@ -33,7 +36,10 @@ public class ObjectCacheAppCache : IAppPolicyCache, IDisposable
|
||||
Lazy<object?>? result;
|
||||
try
|
||||
{
|
||||
_locker.EnterReadLock();
|
||||
if (_locker.TryEnterReadLock(_readLockTimeout) is false)
|
||||
{
|
||||
throw new TimeoutException("Timeout exceeded to the memory cache when getting item");
|
||||
}
|
||||
result = MemoryCache.Get(key) as Lazy<object?>; // null if key not found
|
||||
}
|
||||
finally
|
||||
@@ -195,7 +201,10 @@ public class ObjectCacheAppCache : IAppPolicyCache, IDisposable
|
||||
{
|
||||
try
|
||||
{
|
||||
_locker.EnterWriteLock();
|
||||
if (_locker.TryEnterWriteLock(_writeLockTimeout) is false)
|
||||
{
|
||||
throw new TimeoutException("Timeout exceeded to the memory cache when clearing item");
|
||||
}
|
||||
if (MemoryCache[key] == null)
|
||||
{
|
||||
return;
|
||||
@@ -223,8 +232,10 @@ public class ObjectCacheAppCache : IAppPolicyCache, IDisposable
|
||||
var isInterface = type.IsInterface;
|
||||
try
|
||||
{
|
||||
_locker.EnterWriteLock();
|
||||
|
||||
if (_locker.TryEnterWriteLock(_writeLockTimeout) is false)
|
||||
{
|
||||
throw new TimeoutException("Timeout exceeded to the memory cache when clearing by type");
|
||||
}
|
||||
// ToArray required to remove
|
||||
foreach (var key in MemoryCache
|
||||
.Where(x =>
|
||||
@@ -259,7 +270,10 @@ public class ObjectCacheAppCache : IAppPolicyCache, IDisposable
|
||||
{
|
||||
try
|
||||
{
|
||||
_locker.EnterWriteLock();
|
||||
if (_locker.TryEnterWriteLock(_writeLockTimeout) is false)
|
||||
{
|
||||
throw new TimeoutException("Timeout exceeded to the memory cache when clearing by generic type");
|
||||
}
|
||||
Type typeOfT = typeof(T);
|
||||
var isInterface = typeOfT.IsInterface;
|
||||
|
||||
@@ -296,7 +310,10 @@ public class ObjectCacheAppCache : IAppPolicyCache, IDisposable
|
||||
{
|
||||
try
|
||||
{
|
||||
_locker.EnterWriteLock();
|
||||
if (_locker.TryEnterWriteLock(_writeLockTimeout) is false)
|
||||
{
|
||||
throw new TimeoutException("Timeout exceeded to the memory cache when clearing generic type with predicate");
|
||||
}
|
||||
Type typeOfT = typeof(T);
|
||||
var isInterface = typeOfT.IsInterface;
|
||||
|
||||
@@ -338,7 +355,10 @@ public class ObjectCacheAppCache : IAppPolicyCache, IDisposable
|
||||
{
|
||||
try
|
||||
{
|
||||
_locker.EnterWriteLock();
|
||||
if (_locker.TryEnterWriteLock(_writeLockTimeout) is false)
|
||||
{
|
||||
throw new TimeoutException("Timeout exceeded to the memory cache when clearing with prefix");
|
||||
}
|
||||
|
||||
// ToArray required to remove
|
||||
foreach (var key in MemoryCache
|
||||
@@ -365,7 +385,10 @@ public class ObjectCacheAppCache : IAppPolicyCache, IDisposable
|
||||
|
||||
try
|
||||
{
|
||||
_locker.EnterWriteLock();
|
||||
if (_locker.TryEnterWriteLock(_writeLockTimeout) is false)
|
||||
{
|
||||
throw new TimeoutException("Timeout exceeded to the memory cach when clearing by regex");
|
||||
}
|
||||
|
||||
// ToArray required to remove
|
||||
foreach (var key in MemoryCache
|
||||
|
||||
@@ -13,8 +13,7 @@ public class LockingMechanism : ILockingMechanism
|
||||
{
|
||||
private readonly IDistributedLockingMechanismFactory _distributedLockingMechanismFactory;
|
||||
private readonly ILogger<LockingMechanism> _logger;
|
||||
private readonly object _lockQueueLocker = new();
|
||||
private readonly object _dictionaryLocker = new();
|
||||
private readonly object _locker = new();
|
||||
private StackQueue<(DistributedLockType lockType, TimeSpan timeout, Guid instanceId, int lockId)>? _queuedLocks;
|
||||
private HashSet<int>? _readLocks;
|
||||
private Dictionary<Guid, Dictionary<int, int>>? _readLocksDictionary;
|
||||
@@ -35,12 +34,12 @@ public class LockingMechanism : ILockingMechanism
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
public void ReadLock(Guid instanceId, TimeSpan? timeout = null, params int[] lockIds) => LazyReadLockInner(instanceId, timeout, lockIds);
|
||||
public void ReadLock(Guid instanceId, TimeSpan? timeout = null, params int[] lockIds) => EagerReadLockInner(instanceId, timeout, lockIds);
|
||||
|
||||
public void ReadLock(Guid instanceId, params int[] lockIds) => ReadLock(instanceId, null, lockIds);
|
||||
|
||||
/// <inheritdoc />
|
||||
public void WriteLock(Guid instanceId, TimeSpan? timeout = null, params int[] lockIds) => LazyWriteLockInner(instanceId, timeout, lockIds);
|
||||
public void WriteLock(Guid instanceId, TimeSpan? timeout = null, params int[] lockIds) => EagerReadLockInner(instanceId, timeout, lockIds);
|
||||
|
||||
public void WriteLock(Guid instanceId, params int[] lockIds) => WriteLock(instanceId, null, lockIds);
|
||||
|
||||
@@ -64,7 +63,7 @@ public class LockingMechanism : ILockingMechanism
|
||||
/// <param name="lockIds">Array of lock object identifiers.</param>
|
||||
private void EagerWriteLockInner(Guid instanceId, TimeSpan? timeout, params int[] lockIds)
|
||||
{
|
||||
lock (_dictionaryLocker)
|
||||
lock (_locker)
|
||||
{
|
||||
foreach (var lockId in lockIds)
|
||||
{
|
||||
@@ -106,7 +105,7 @@ public class LockingMechanism : ILockingMechanism
|
||||
/// <param name="lockIds">Array of lock object identifiers.</param>
|
||||
private void EagerReadLockInner(Guid instanceId, TimeSpan? timeout, params int[] lockIds)
|
||||
{
|
||||
lock (_dictionaryLocker)
|
||||
lock (_locker)
|
||||
{
|
||||
foreach (var lockId in lockIds)
|
||||
{
|
||||
@@ -219,7 +218,7 @@ public class LockingMechanism : ILockingMechanism
|
||||
|
||||
private void LazyLockInner(DistributedLockType lockType, Guid instanceId, TimeSpan? timeout = null, params int[] lockIds)
|
||||
{
|
||||
lock (_lockQueueLocker)
|
||||
lock (_locker)
|
||||
{
|
||||
if (_queuedLocks == null)
|
||||
{
|
||||
@@ -239,7 +238,7 @@ public class LockingMechanism : ILockingMechanism
|
||||
/// <param name="instanceId">Instance ID of the scope to clear.</param>
|
||||
public void ClearLocks(Guid instanceId)
|
||||
{
|
||||
lock (_dictionaryLocker)
|
||||
lock (_locker)
|
||||
{
|
||||
_readLocksDictionary?.Remove(instanceId);
|
||||
_writeLocksDictionary?.Remove(instanceId);
|
||||
@@ -294,7 +293,7 @@ public class LockingMechanism : ILockingMechanism
|
||||
/// </summary>
|
||||
public void EnsureLocks(Guid scopeInstanceId)
|
||||
{
|
||||
lock (_lockQueueLocker)
|
||||
lock (_locker)
|
||||
{
|
||||
if (!(_queuedLocks?.Count > 0))
|
||||
{
|
||||
|
||||
Reference in New Issue
Block a user