Пример #1
0
        public void Dispose()
        {
            if (_completed)
            {
                return;
            }

            _completed = true;

            if (!AcquiredLocks.Value.ContainsKey(_resource))
            {
                return;
            }

            AcquiredLocks.Value[_resource]--;

            if (AcquiredLocks.Value[_resource] != 0)
            {
                return;
            }

            try
            {
                Release(_connection, _resource);
                AcquiredLocks.Value.Remove(_resource);
            }
            finally
            {
                _storage.ReleaseConnection(_connection);
            }
        }
Пример #2
0
 public void Dispose()
 {
     // Timer callback may be invoked after the Dispose method call,
     // so we are using lock to avoid unsynchronized calls.
     lock (_lockObject)
     {
         _timer?.Dispose();
         _transaction.Dispose();
         _storage.ReleaseConnection(_connection);
         _connection = null;
     }
 }
Пример #3
0
        public SqlServerDistributedLock([NotNull] SqlServerStorage storage, [NotNull] string resource, TimeSpan timeout)
        {
            if (storage == null)
            {
                throw new ArgumentNullException(nameof(storage));
            }
            if (String.IsNullOrEmpty(resource))
            {
                throw new ArgumentNullException(nameof(resource));
            }
            if (timeout.TotalSeconds + CommandTimeoutAdditionSeconds > Int32.MaxValue)
            {
                throw new ArgumentException(
                          $"The timeout specified is too large. Please supply a timeout equal to or less than {Int32.MaxValue - CommandTimeoutAdditionSeconds} seconds", nameof(timeout));
            }
            if (timeout.TotalMilliseconds > Int32.MaxValue)
            {
                throw new ArgumentException(
                          $"The timeout specified is too large. Please supply a timeout equal to or less than {(int)TimeSpan.FromMilliseconds(Int32.MaxValue).TotalSeconds} seconds", nameof(timeout));
            }

            _storage  = storage;
            _resource = resource;

            if (!AcquiredLocks.Value.ContainsKey(_resource) || AcquiredLocks.Value[_resource] == 0)
            {
                _connection = storage.CreateAndOpenConnection();

                try
                {
                    Acquire(_connection, _resource, timeout);
                }
                catch (Exception)
                {
                    storage.ReleaseConnection(_connection);
                    throw;
                }

                if (!_storage.IsExistingConnection(_connection))
                {
                    _timer = new Timer(ExecuteKeepAliveQuery, null, KeepAliveInterval, KeepAliveInterval);
                }

                AcquiredLocks.Value[_resource] = 1;
            }
            else
            {
                AcquiredLocks.Value[_resource]++;
            }
        }
Пример #4
0
        public void Dispose()
        {
            if (_completed)
            {
                return;
            }

            _completed = true;

            if (!AcquiredLocks.Value.ContainsKey(_resource))
            {
                return;
            }

            AcquiredLocks.Value[_resource]--;

            if (AcquiredLocks.Value[_resource] != 0)
            {
                return;
            }

            lock (_lockObject)
            {
                // Timer callback may be invoked after the Dispose method call,
                // so we are using lock to avoid unsynchronized calls.

                try
                {
                    AcquiredLocks.Value.Remove(_resource);

                    _timer?.Dispose();

                    if (_connection.State == ConnectionState.Open)
                    {
                        // Session-scoped application locks are held only when connection
                        // is open. When connection is closed or broken, for example, when
                        // there was an error, application lock is already released by SQL
                        // Server itself, and we shouldn't do anything.
                        Release(_connection, _resource);
                    }
                }
                finally
                {
                    _storage.ReleaseConnection(_connection);
                    _connection = null;
                }
            }
        }
Пример #5
0
        public void Dispose()
        {
            if (_completed)
            {
                return;
            }

            _completed = true;

            if (!AcquiredLocks.Value.ContainsKey(_resource))
            {
                return;
            }

            AcquiredLocks.Value[_resource]--;

            if (AcquiredLocks.Value[_resource] != 0)
            {
                return;
            }

            lock (_lockObject)
            {
                // Timer callback may be invoked after the Dispose method call,
                // so we are using lock to avoid unsynchronized calls.

                try
                {
                    AcquiredLocks.Value.Remove(_resource);

                    _timer?.Dispose();

                    Release(_connection, _resource);
                }
                finally
                {
                    _storage.ReleaseConnection(_connection);
                    _connection = null;
                }
            }
        }
Пример #6
0
        public SqlServerDistributedLock([NotNull] SqlServerStorage storage, [NotNull] string resource, TimeSpan timeout)
        {
            if (storage == null)
            {
                throw new ArgumentNullException(nameof(storage));
            }
            if (String.IsNullOrEmpty(resource))
            {
                throw new ArgumentNullException(nameof(resource));
            }

            _storage  = storage;
            _resource = resource;

            if (!AcquiredLocks.Value.ContainsKey(_resource) || AcquiredLocks.Value[_resource] == 0)
            {
                _connection = storage.CreateAndOpenConnection();

                try
                {
                    Acquire(_connection, _resource, timeout);
                }
                catch (Exception)
                {
                    storage.ReleaseConnection(_connection);
                    throw;
                }

                if (!_storage.IsExistingConnection(_connection))
                {
                    _timer = new Timer(ExecuteKeepAliveQuery, null, KeepAliveInterval, KeepAliveInterval);
                }

                AcquiredLocks.Value[_resource] = 1;
            }
            else
            {
                AcquiredLocks.Value[_resource]++;
            }
        }
Пример #7
0
        private void ReleaseLock(string resource, Guid lockId, bool onDisposing)
        {
            try
            {
                if (_lockedResources.ContainsKey(resource))
                {
                    if (_lockedResources[resource].Contains(lockId))
                    {
                        if (_lockedResources[resource].Remove(lockId) &&
                            _lockedResources[resource].Count == 0 &&
                            _lockedResources.Remove(resource) &&
                            _dedicatedConnection.State == ConnectionState.Open)
                        {
                            // Session-scoped application locks are held only when connection
                            // is open. When connection is closed or broken, for example, when
                            // there was an error, application lock is already released by SQL
                            // Server itself, and we shouldn't do anything.
                            SqlServerDistributedLock.Release(_dedicatedConnection, resource);
                        }
                    }
                }

                if (_lockedResources.Count == 0)
                {
                    _storage.ReleaseConnection(_dedicatedConnection);
                    _dedicatedConnection = null;
                }
            }
            catch (Exception)
            {
                if (!onDisposing)
                {
                    throw;
                }
            }
        }
Пример #8
0
 public void Dispose()
 {
     _transaction.Dispose();
     _storage.ReleaseConnection(_connection);
 }