feature: Implement Dispose for types which have disposable data (#1171)

* Initial set of dispose implementations

Not handled yet:
- Discord.Net.Websocket/Entities/SocketGuild
- Discord.Net.Tests

* Refactor DiscordSocketClient init into ctor

This way we remove an IDisposableAnalyzer warning for not disposing
the client when we set the client variable.

* Dispose of clients when disposing sharded client

* Finish implementing IDisposable where appropriate

I opted to use NoWarn in the Tests project as it wasn't really necessary
considering that our tests only run once

* Tweak samples after feedback
This commit is contained in:
Monica S
2018-11-29 01:18:16 +00:00
committed by Christopher F
parent dca6c33da3
commit 7366cd4361
31 changed files with 406 additions and 154 deletions

View File

@@ -19,6 +19,7 @@ namespace Discord.Net.Providers.WS4Net
private readonly SemaphoreSlim _lock;
private readonly Dictionary<string, string> _headers;
private WS4NetSocket _client;
private CancellationTokenSource _disconnectCancelTokenSource;
private CancellationTokenSource _cancelTokenSource;
private CancellationToken _cancelToken, _parentToken;
private ManualResetEventSlim _waitUntilConnect;
@@ -28,7 +29,7 @@ namespace Discord.Net.Providers.WS4Net
{
_headers = new Dictionary<string, string>();
_lock = new SemaphoreSlim(1, 1);
_cancelTokenSource = new CancellationTokenSource();
_disconnectCancelTokenSource = new CancellationTokenSource();
_cancelToken = CancellationToken.None;
_parentToken = CancellationToken.None;
_waitUntilConnect = new ManualResetEventSlim();
@@ -38,7 +39,11 @@ namespace Discord.Net.Providers.WS4Net
if (!_isDisposed)
{
if (disposing)
{
DisconnectInternalAsync(true).GetAwaiter().GetResult();
_lock?.Dispose();
_cancelTokenSource?.Dispose();
}
_isDisposed = true;
}
}
@@ -63,8 +68,13 @@ namespace Discord.Net.Providers.WS4Net
{
await DisconnectInternalAsync().ConfigureAwait(false);
_cancelTokenSource = new CancellationTokenSource();
_cancelToken = CancellationTokenSource.CreateLinkedTokenSource(_parentToken, _cancelTokenSource.Token).Token;
_disconnectCancelTokenSource?.Dispose();
_cancelTokenSource?.Dispose();
_client?.Dispose();
_disconnectCancelTokenSource = new CancellationTokenSource();
_cancelTokenSource = CancellationTokenSource.CreateLinkedTokenSource(_parentToken, _disconnectCancelTokenSource.Token);
_cancelToken = _cancelTokenSource.Token;
_client = new WS4NetSocket(host, "", customHeaderItems: _headers.ToList())
{
@@ -96,7 +106,7 @@ namespace Discord.Net.Providers.WS4Net
}
private Task DisconnectInternalAsync(bool isDisposing = false)
{
_cancelTokenSource.Cancel();
_disconnectCancelTokenSource.Cancel();
if (_client == null)
return Task.Delay(0);
@@ -125,8 +135,10 @@ namespace Discord.Net.Providers.WS4Net
}
public void SetCancelToken(CancellationToken cancelToken)
{
_cancelTokenSource?.Dispose();
_parentToken = cancelToken;
_cancelToken = CancellationTokenSource.CreateLinkedTokenSource(_parentToken, _cancelTokenSource.Token).Token;
_cancelTokenSource = CancellationTokenSource.CreateLinkedTokenSource(_parentToken, _disconnectCancelTokenSource.Token);
_cancelToken = _cancelTokenSource.Token;
}
public async Task SendAsync(byte[] data, int index, int count, bool isText)