Esempio n. 1
0
        public async Task <ICacheEntry> GetOrAddAsync(string key, Func <string, Stream, ICacheControl, Task> valueFactory, ICacheControl cacheControl, CancellationToken ct)
        {
            using (await _rwLock.ReadLockAsync())
            {
                ICacheEntry found = GetInternal(key);
                if (!(found is EmptyCacheEntry))
                {
                    found.Ref(); // this entry remain valid after releasing the lock
                    return(found);
                }
            }

            using (await _rwLock.WriteLockAsync())
            {
                ICacheEntry found = GetInternal(key);
                if (!(found is EmptyCacheEntry))
                {
                    found.Ref(); // this entry remain valid after releasing the lock
                    return(found);
                }

                var randomPath = await _fs.WriteAtomicAsync((sink, cancel) => valueFactory(key, sink, cacheControl), _cacheTmpPath, ct).ConfigureAwait(false);

                var tmpEntry = new DiskCacheEntry(key, randomPath, this);
                if (!cacheControl.NoStore)
                {
                    SetInternal(key, tmpEntry);
                }

                var entry = GetInternal(key);
                entry.Ref();
                return(entry);
            }
        }
        public void TestBlockingAsync()
        {
            var l = new AsyncReaderWriterLock();

            for (var i = 0; i < 2; i++)
            {
                var readReleaserTask = l.ReadLockAsync();
                AssertEqualValue(() => l.CurrentReaders, 1, readReleaserTask);
                AssertTaskCompleted(readReleaserTask);

                var readReleaserTask2 = l.ReadLockAsync();
                AssertEqualValue(() => l.CurrentReaders, 2, readReleaserTask2);
                AssertTaskCompleted(readReleaserTask2);

                var writeReleaserTask = l.WriteLockAsync();
                AssertEqualValue(() => l.AcquiredWriteLock, true, writeReleaserTask);
                AssertEqualValue(() => l.Writing, false, writeReleaserTask);
                Assert.That(writeReleaserTask.IsCompleted, Is.False);

                readReleaserTask.Result.Dispose();
                Assert.That(l.CurrentReaders, Is.EqualTo(1));
                Assert.That(writeReleaserTask.IsCompleted, Is.False);

                readReleaserTask2.Result.Dispose();
                Assert.That(l.CurrentReaders, Is.EqualTo(0));
                AssertEqualValue(() => l.Writing, true, writeReleaserTask);
                AssertTaskCompleted(writeReleaserTask);

                readReleaserTask = l.ReadLockAsync();
                AssertEqualValue(() => l.ReadersWaiting, 1, readReleaserTask);
                Assert.That(readReleaserTask.IsCompleted, Is.False);

                var writeReleaserTask2 = l.WriteLockAsync();
                AssertEqualValue(() => l.WritersWaiting, 1, writeReleaserTask2);
                Assert.That(writeReleaserTask2.IsCompleted, Is.False);

                writeReleaserTask.Result.Dispose();
                AssertEqualValue(() => l.WritersWaiting, 0, writeReleaserTask2);
                AssertEqualValue(() => l.Writing, true, writeReleaserTask2);
                Assert.That(readReleaserTask.IsCompleted, Is.False);
                AssertTaskCompleted(writeReleaserTask2);

                writeReleaserTask2.Result.Dispose();
                AssertEqualValue(() => l.Writing, false, writeReleaserTask2);
                AssertEqualValue(() => l.ReadersWaiting, 0, readReleaserTask);
                AssertEqualValue(() => l.CurrentReaders, 1, readReleaserTask);
                AssertTaskCompleted(readReleaserTask);

                readReleaserTask.Result.Dispose();
                Assert.That(l.ReadersWaiting, Is.EqualTo(0));
                Assert.That(l.WritersWaiting, Is.EqualTo(0));
                Assert.That(l.CurrentReaders, Is.EqualTo(0));
                Assert.That(l.Writing, Is.False);
            }
        }
        public async Task TestInvaildExitReadLockUsageAsync()
        {
            var l             = new AsyncReaderWriterLock();
            var readReleaser  = await(l.ReadLockAsync());
            var readReleaser2 = await(l.ReadLockAsync());

            readReleaser.Dispose();
            readReleaser2.Dispose();
            Assert.Throws <InvalidOperationException>(() => readReleaser.Dispose());
            Assert.Throws <InvalidOperationException>(() => readReleaser2.Dispose());
        }
Esempio n. 4
0
        ///<summary>Gets all files that directly depend on the specified file.</summary>
        public async Task <IEnumerable <string> > GetDirectDependentsAsync(string fileName)
        {
            fileName = Path.GetFullPath(fileName);

            using (await rwLock.ReadLockAsync())
            {
                GraphNode fileNode;
                if (!nodes.TryGetValue(fileName, out fileNode))
                {
                    return(Enumerable.Empty <string>());
                }
                return(fileNode.Dependents.Select(d => d.FileName));
            }
        }
        public void TestMixingSyncAndAsync()
        {
            var l            = new AsyncReaderWriterLock();
            var readReleaser = l.ReadLock();

            Assert.That(l.CurrentReaders, Is.EqualTo(1));

            var readReleaserTask = l.ReadLockAsync();

            AssertEqualValue(() => l.CurrentReaders, 2, readReleaserTask);
            AssertTaskCompleted(readReleaserTask);

            readReleaser.Dispose();
            Assert.That(l.CurrentReaders, Is.EqualTo(1));

            readReleaserTask.Result.Dispose();
            Assert.That(l.CurrentReaders, Is.EqualTo(0));

            var writeReleaser = l.WriteLock();

            Assert.That(l.AcquiredWriteLock, Is.True);

            var writeReleaserTask = l.WriteLockAsync();

            AssertEqualValue(() => l.WritersWaiting, 1, writeReleaserTask);
            Assert.That(writeReleaserTask.IsCompleted, Is.False);

            readReleaserTask = Task.Run(() => l.ReadLock());
            AssertEqualValue(() => l.ReadersWaiting, 1, readReleaserTask);
            Assert.That(readReleaserTask.IsCompleted, Is.False);

            var readReleaserTask2 = l.ReadLockAsync();

            AssertEqualValue(() => l.ReadersWaiting, 2, readReleaserTask2);
            Assert.That(readReleaserTask2.IsCompleted, Is.False);

            writeReleaser.Dispose();
            AssertEqualValue(() => l.WritersWaiting, 0, writeReleaserTask);
            AssertEqualValue(() => l.Writing, true, writeReleaserTask);
            AssertTaskCompleted(writeReleaserTask);
            Assert.That(readReleaserTask.IsCompleted, Is.False);
            Assert.That(readReleaserTask2.IsCompleted, Is.False);

            writeReleaserTask.Result.Dispose();
            AssertEqualValue(() => l.CurrentReaders, 2, readReleaserTask);
            AssertEqualValue(() => l.ReadersWaiting, 0, readReleaserTask2);
            AssertTaskCompleted(readReleaserTask);
            AssertTaskCompleted(readReleaserTask2);
        }
        public void TestWritePriorityOverReadAsync()
        {
            var l = new AsyncReaderWriterLock();

            for (var i = 0; i < 2; i++)
            {
                var writeReleaser = l.WriteLock();
                Assert.That(l.AcquiredWriteLock, Is.True);

                var readReleaserTask = l.ReadLockAsync();
                AssertEqualValue(() => l.ReadersWaiting, 1, readReleaserTask);

                var writeReleaserTask = l.WriteLockAsync();
                AssertEqualValue(() => l.WritersWaiting, 1, writeReleaserTask);

                writeReleaser.Dispose();
                AssertEqualValue(() => l.WritersWaiting, 0, writeReleaserTask);
                AssertEqualValue(() => l.ReadersWaiting, 1, readReleaserTask);
                AssertTaskCompleted(writeReleaserTask);

                writeReleaserTask.Result.Dispose();
                AssertEqualValue(() => l.ReadersWaiting, 0, readReleaserTask);
                AssertTaskCompleted(readReleaserTask);

                readReleaserTask.Result.Dispose();
            }
        }
Esempio n. 7
0
            internal async Threading.Task AttachFileObserverEvent(string fileName)
            {
                if (!File.Exists(fileName))
                {
                    return;
                }

                fileName = Path.GetFullPath(fileName);

                using (await rwLock.ReadLockAsync())
                {
                    if (_watchedFiles.Contains(fileName))
                    {
                        return;
                    }
                }

                using (await rwLock.WriteLockAsync())
                {
                    _watchedFiles.Add(fileName);
                }

                _watcher = new FileSystemWatcher();

                _watcher.Path         = Path.GetDirectoryName(fileName);
                _watcher.Filter       = Path.GetFileName(fileName);
                _watcher.NotifyFilter = NotifyFilters.Attributes | NotifyFilters.LastWrite | NotifyFilters.Size;

                _watcher.Changed += async(s, e) => await UpdateBundles(null, true);

                _watcher.EnableRaisingEvents = true;
            }
        public void TestOperationAfterDisposeAsync()
        {
            var l = new AsyncReaderWriterLock();

            l.Dispose();

            Assert.ThrowsAsync <ObjectDisposedException>(() => l.ReadLockAsync());
            Assert.ThrowsAsync <ObjectDisposedException>(() => l.WriteLockAsync());
        }
Esempio n. 9
0
        public async Task ValueFactoryRequiresReadLockHeldByOther()
        {
            var lck = new AsyncReaderWriterLock();
            var readLockAcquiredByOther = new AsyncManualResetEvent();
            var writeLockWaitingByOther = new AsyncManualResetEvent();

            var lazy = new AsyncLazy <object>(
                async delegate
            {
                await writeLockWaitingByOther;
                using (await lck.ReadLockAsync())
                {
                    return(new object());
                }
            });

            var writeLockTask = Task.Run(async delegate
            {
                await readLockAcquiredByOther;
                var writeAwaiter = lck.WriteLockAsync().GetAwaiter();
                writeAwaiter.OnCompleted(delegate
                {
                    using (writeAwaiter.GetResult())
                    {
                    }
                });
                writeLockWaitingByOther.Set();
            });

            // Kick off the value factory without any lock context.
            var resultTask = lazy.GetValueAsync();

            using (await lck.ReadLockAsync())
            {
                readLockAcquiredByOther.Set();

                // Now request the lazy task again.
                // This would traditionally deadlock because the value factory won't
                // be able to get its read lock while a write lock is waiting (for us to release ours).
                // This unit test verifies that the AsyncLazy<T> class can avoid deadlocks in this case.
                await lazy.GetValueAsync();
            }
        }
        public void TestPartialReleasingReadLockAsync()
        {
            var l = new AsyncReaderWriterLock();
            var readReleaserTask = l.ReadLockAsync();

            AssertEqualValue(() => l.CurrentReaders, 1, readReleaserTask);
            AssertTaskCompleted(readReleaserTask);

            var readReleaserTask2 = l.ReadLockAsync();

            AssertEqualValue(() => l.CurrentReaders, 2, readReleaserTask);
            AssertTaskCompleted(readReleaserTask2);

            var writeReleaserTask = l.WriteLockAsync();

            AssertEqualValue(() => l.AcquiredWriteLock, true, writeReleaserTask);
            AssertEqualValue(() => l.Writing, false, writeReleaserTask);
            Assert.That(writeReleaserTask.IsCompleted, Is.False);

            var readReleaserTask3 = l.ReadLockAsync();

            AssertEqualValue(() => l.ReadersWaiting, 1, readReleaserTask3);
            Assert.That(readReleaserTask3.IsCompleted, Is.False);

            readReleaserTask.Result.Dispose();
            Assert.That(writeReleaserTask.IsCompleted, Is.False);
            Assert.That(readReleaserTask3.IsCompleted, Is.False);

            readReleaserTask2.Result.Dispose();
            AssertEqualValue(() => l.Writing, true, writeReleaserTask);
            AssertEqualValue(() => l.ReadersWaiting, 1, readReleaserTask3);
            AssertTaskCompleted(writeReleaserTask);
            Assert.That(readReleaserTask3.IsCompleted, Is.False);

            writeReleaserTask.Result.Dispose();
            AssertEqualValue(() => l.ReadersWaiting, 0, readReleaserTask3);
            AssertTaskCompleted(readReleaserTask3);
        }
Esempio n. 11
0
        public async Task AttachFileObserver(IBundleDocument document, string fileName, Func <string, bool, Task> updateBundle)
        {
            _document       = document;
            _bundleFileName = document.FileName;
            fileName        = Path.GetFullPath(fileName);

            if (!File.Exists(fileName))
            {
                return;
            }

            _watcher = new FileSystemWatcher
            {
                Path   = Path.GetDirectoryName(fileName),
                Filter = Path.GetFileName(fileName),
                //_watcher.NotifyFilter = NotifyFilters.Attributes | NotifyFilters.LastWrite | NotifyFilters.Size;
                NotifyFilter = NotifyFilters.Attributes |
                               NotifyFilters.CreationTime |
                               NotifyFilters.FileName |
                               NotifyFilters.LastAccess |
                               NotifyFilters.LastWrite |
                               NotifyFilters.Size
            };

            using (await _rwLock.ReadLockAsync())
            {
                if (WatchedFiles.ContainsKey(_bundleFileName) && WatchedFiles[_bundleFileName].Any(s => s.Item1.Equals(fileName, StringComparison.OrdinalIgnoreCase)))
                {
                    return;
                }
            }

            _changeEvent = (_, __) => Changed(updateBundle);

            _watcher.Changed += _changeEvent;
            _watcher.Deleted += (_, __) => Deleted(fileName);

            if (_extensions.Any(e => fileName.EndsWith(e, StringComparison.OrdinalIgnoreCase)))
            {
                _watcher.Renamed += (_, renamedEventArgument) => Renamed(renamedEventArgument, updateBundle);
            }

            _watcher.EnableRaisingEvents = true;

            using (await _rwLock.WriteLockAsync())
            {
                if (!WatchedFiles.ContainsKey(_bundleFileName))
                {
                    WatchedFiles.Add(_bundleFileName, new HashSet <Tuple <string, FileSystemWatcher> >());
                }

                WatchedFiles[_bundleFileName].Add(new Tuple <string, FileSystemWatcher>(fileName, _watcher));
            }
        }
        public async Task <IEnumerable <Package> > GetInstalledPackages()
        {
            using (await Lock.ReadLockAsync())
            {
                var choco = Lets.GetChocolatey().SetCustomLogging(new SerilogLogger(Logger, _progressService));
                choco.Set(
                    config =>
                {
                    config.CommandName           = CommandNameType.list.ToString();
                    config.ListCommand.LocalOnly = true;
                });

                return((await choco.ListAsync <PackageResult>())
                       .Select(package => GetMappedPackage(choco, package, _mapper, true))
                       .ToArray());
            }
        }
        private static async Task LockAsync(
            AsyncReaderWriterLock readWriteLock,
            Random random,
            LockStatistics lockStatistics,
            System.Action checkLockAction,
            Func <bool> canContinue, CancellationToken cancellationToken = default(CancellationToken))
        {
            while (canContinue())
            {
                var isRead   = random.Next(100) < 80;
                var releaser = isRead ? await(readWriteLock.ReadLockAsync()) : await(readWriteLock.WriteLockAsync());
                lock (readWriteLock)
                {
                    if (isRead)
                    {
                        lockStatistics.ReadLockCount++;
                    }
                    else
                    {
                        lockStatistics.WriteLockCount++;
                    }

                    checkLockAction();
                }

                await(Task.Delay(10, cancellationToken));

                lock (readWriteLock)
                {
                    releaser.Dispose();
                    if (isRead)
                    {
                        lockStatistics.ReadLockCount--;
                    }
                    else
                    {
                        lockStatistics.WriteLockCount--;
                    }

                    checkLockAction();
                }
            }
        }
        public async Task AttachFileObserver(string fileName, string bundleFile, Func <string, bool, Task> updateBundle)
        {
            fileName = Path.GetFullPath(fileName);

            if (!File.Exists(fileName))
            {
                return;
            }

            _watcher        = new FileSystemWatcher();
            _watcher.Path   = Path.GetDirectoryName(fileName);
            _watcher.Filter = Path.GetFileName(fileName);
            //_watcher.NotifyFilter = NotifyFilters.Attributes | NotifyFilters.LastWrite | NotifyFilters.Size;
            _watcher.NotifyFilter = NotifyFilters.Attributes |
                                    NotifyFilters.CreationTime |
                                    NotifyFilters.FileName |
                                    NotifyFilters.LastAccess |
                                    NotifyFilters.LastWrite |
                                    NotifyFilters.Size;

            using (await rwLock.ReadLockAsync())
            {
                if (_watchedFiles.ContainsKey(bundleFile) && _watchedFiles[bundleFile].Contains(fileName))
                {
                    return;
                }
            }

            using (await rwLock.WriteLockAsync())
            {
                if (!_watchedFiles.ContainsKey(bundleFile))
                {
                    _watchedFiles.Add(bundleFile, new HashSet <string>());
                }

                _watchedFiles[bundleFile].Add(fileName);
            }

            _watcher.Changed += async(s, e) => await updateBundle(bundleFile, false);

            _watcher.EnableRaisingEvents = true;
        }
        public static async Task RunAsync(int id)
        {
            Console.WriteLine($"Run {id}");
            await Task.Delay(1000);

            for (var i = 0; i < id * 2; i++)
            {
                using (await locker.ReadLockAsync())
                {
                    using (await consoleLock.EnterAsync())
                    {
                        Interlocked.Increment(ref readers);
                        Console.WriteLine($"Begin Read Loop {i + 1} Id {id} number of readers {readers}");
                    }

                    await Task.Delay(1000);

                    using (await consoleLock.EnterAsync())
                    {
                        Interlocked.Decrement(ref readers);
                        Console.WriteLine($"End Read Loop {i + 1} Id {id} number of readers {readers}");
                    }
                }
            }

            using (await locker.UpgradeableReadLockAsync())
            {
                using (await consoleLock.EnterAsync())
                {
                    Interlocked.Increment(ref upgradeables);
                    Console.WriteLine($"Begin Upgradeable Id {id} number of upgradeables {upgradeables}");
                }

                await Task.Delay(1000);

                using (await consoleLock.EnterAsync())
                {
                    Console.WriteLine($"Wait Upgarde Id {id} number of upgradeables {upgradeables}");
                }

                using (await locker.WriteLockAsync())
                {
                    using (await consoleLock.EnterAsync())
                    {
                        Interlocked.Increment(ref writers);
                        Console.WriteLine($"Begin Write Id {id} number of writers {writers}");
                    }

                    await Task.Delay(1000);

                    using (await consoleLock.EnterAsync())
                    {
                        Interlocked.Decrement(ref writers);
                        Console.WriteLine($"End Write ID {id} number of writers {writers}");
                    }
                }

                using (await consoleLock.EnterAsync())
                {
                    Interlocked.Decrement(ref upgradeables);
                    Console.WriteLine($"End Upgradeable Id {id} number of upgradeables {upgradeables}");
                }
            }
        }
Esempio n. 16
0
        public async Task <JoinRoomResult> JoinRoomAsync(string peerId, string connectionId, JoinRoomRequest joinRoomRequest)
        {
            using (await _peersLock.ReadLockAsync())
            {
                if (!_peers.TryGetValue(peerId, out var peer))
                {
                    throw new PeerNotExistsException("JoinRoomAsync()", peerId);
                }

                CheckConnection(peer, connectionId);

                await _roomsLock.WaitAsync();

                try
                {
                    // Room 如果不存在则创建
                    if (!_rooms.TryGetValue(joinRoomRequest.RoomId, out var room))
                    {
                        // Router media codecs.
                        var mediaCodecs = _mediasoupOptions.MediasoupSettings.RouterSettings.RtpCodecCapabilities;

                        // Create a mediasoup Router.
                        var worker = _mediasoupServer.GetWorker();
                        var router = await worker.CreateRouterAsync(new RouterOptions
                        {
                            MediaCodecs = mediaCodecs
                        });

                        if (router == null)
                        {
                            throw new Exception($"PeerJoinAsync() | Worker maybe closed.");
                        }

                        room = new Room(_loggerFactory, router, joinRoomRequest.RoomId, "Default");
                        _rooms[room.RoomId] = room;
                    }

                    var result = await peer.JoinRoomAsync(room);

                    await peer.SetPeerInternalDataAsync(new SetPeerInternalDataRequest
                    {
                        InternalData = new Dictionary <string, object>
                        {
                            { Peer.RoleKey, joinRoomRequest.Role }
                        }
                    });

                    return(result);
                }
                catch (Exception ex)
                {
                    _logger.LogError(ex, "JoinRoomAsync()");
                    throw;
                }
                finally
                {
                    _roomsLock.Set();
                }
            }
        }
Esempio n. 17
0
 public static AsyncReaderWriterLock.Awaitable ReadOnMainAsync()
 {
     return(_cs_main_async.ReadLockAsync());
 }
Esempio n. 18
0
        public void Should_allow_multiple_read_locks_immediately_when_unlocked()
        {
            var readerTask1 = locker.ReadLockAsync();
            var readerTask2 = locker.ReadLockAsync();
            var readerTask3 = locker.ReadLockAsync();

            readerTask1.IsCompleted.Should().BeTrue();
            readerTask2.IsCompleted.Should().BeTrue();
            readerTask3.IsCompleted.Should().BeTrue();
        }
        public async Task TestConcurrentReadWriteAsync()
        {
            var l = new AsyncReaderWriterLock();

            for (var i = 0; i < 2; i++)
            {
                var writeReleaser = await(l.WriteLockAsync());
                Assert.That(l.Writing, Is.True);

                var secondWriteSemaphore = new SemaphoreSlim(0);
                var secondWriteReleaser  = default(AsyncReaderWriterLock.Releaser);
                var secondWriteThread    = new Thread(
                    () =>
                {
                    secondWriteSemaphore.Wait();
                    secondWriteReleaser = l.WriteLock();
                });
                secondWriteThread.Priority = ThreadPriority.Highest;
                secondWriteThread.Start();
                await(AssertEqualValueAsync(() => secondWriteThread.ThreadState == ThreadState.WaitSleepJoin, true));

                var secondReadThreads   = new Thread[20];
                var secondReadReleasers = new AsyncReaderWriterLock.Releaser[secondReadThreads.Length];
                var secondReadSemaphore = new SemaphoreSlim(0);
                for (var j = 0; j < secondReadReleasers.Length; j++)
                {
                    var index  = j;
                    var thread = new Thread(
                        () =>
                    {
                        secondReadSemaphore.Wait();
                        secondReadReleasers[index] = l.ReadLock();
                    });
                    thread.Priority      = ThreadPriority.Highest;
                    secondReadThreads[j] = thread;
                    thread.Start();
                }

                await(AssertEqualValueAsync(() => secondReadThreads.All(o => o.ThreadState == ThreadState.WaitSleepJoin), true));

                var firstReadReleaserTasks = new Task[30];
                var firstReadStopSemaphore = new SemaphoreSlim(0);
                for (var j = 0; j < firstReadReleaserTasks.Length; j++)
                {
                    firstReadReleaserTasks[j] = Task.Run(async() =>
                    {
                        var releaser = await(l.ReadLockAsync());
                        await(firstReadStopSemaphore.WaitAsync());
                        releaser.Dispose();
                    });
                }

                await(AssertEqualValueAsync(() => l.ReadersWaiting, firstReadReleaserTasks.Length, waitDelay: 60000));

                writeReleaser.Dispose();
                secondWriteSemaphore.Release();
                secondReadSemaphore.Release(secondReadThreads.Length);
                await(Task.Delay(1000));
                firstReadStopSemaphore.Release(firstReadReleaserTasks.Length);

                await(AssertEqualValueAsync(() => firstReadReleaserTasks.All(o => o.IsCompleted), true));
                Assert.That(l.ReadersWaiting, Is.EqualTo(secondReadThreads.Length));
                Assert.That(l.CurrentReaders, Is.EqualTo(0));
                await(AssertEqualValueAsync(() => secondWriteThread.IsAlive, false));
                await(AssertEqualValueAsync(() => secondReadThreads.All(o => o.IsAlive), true));

                secondWriteReleaser.Dispose();
                await(AssertEqualValueAsync(() => secondReadThreads.All(o => !o.IsAlive), true));

                Assert.That(l.ReadersWaiting, Is.EqualTo(0));
                Assert.That(l.CurrentReaders, Is.EqualTo(secondReadThreads.Length));

                foreach (var secondReadReleaser in secondReadReleasers)
                {
                    secondReadReleaser.Dispose();
                }

                Assert.That(l.ReadersWaiting, Is.EqualTo(0));
                Assert.That(l.CurrentReaders, Is.EqualTo(0));
            }
        }
Esempio n. 20
0
        public async Task <PeerAppDataResult> SetPeerAppDataAsync(string peerId, string connectionId, SetPeerAppDataRequest setPeerAppDataRequest)
        {
            using (await _peersLock.ReadLockAsync())
            {
                if (!_peers.TryGetValue(peerId, out var peer))
                {
                    throw new Exception($"SetPeerAppDataAsync() | Peer:{peerId} is not exists.");
                }

                CheckConnection(peer, connectionId);

                return(await peer.SetPeerAppDataAsync(setPeerAppDataRequest));
            }
        }