* Allow users to opt-in to proxies * Allow opting in to proxies on the WebSocketpull/821/merge
@@ -22,7 +22,7 @@ namespace Discord.Net.Rest | |||||
private CancellationToken _cancelToken; | private CancellationToken _cancelToken; | ||||
private bool _isDisposed; | private bool _isDisposed; | ||||
public DefaultRestClient(string baseUrl) | |||||
public DefaultRestClient(string baseUrl, bool useProxy = false) | |||||
{ | { | ||||
_baseUrl = baseUrl; | _baseUrl = baseUrl; | ||||
@@ -30,7 +30,7 @@ namespace Discord.Net.Rest | |||||
{ | { | ||||
AutomaticDecompression = DecompressionMethods.GZip | DecompressionMethods.Deflate, | AutomaticDecompression = DecompressionMethods.GZip | DecompressionMethods.Deflate, | ||||
UseCookies = false, | UseCookies = false, | ||||
UseProxy = false | |||||
UseProxy = useProxy, | |||||
}); | }); | ||||
SetHeader("accept-encoding", "gzip, deflate"); | SetHeader("accept-encoding", "gzip, deflate"); | ||||
@@ -4,16 +4,21 @@ namespace Discord.Net.Rest | |||||
{ | { | ||||
public static class DefaultRestClientProvider | public static class DefaultRestClientProvider | ||||
{ | { | ||||
public static readonly RestClientProvider Instance = url => | |||||
public static readonly RestClientProvider Instance = Create(); | |||||
public static RestClientProvider Create(bool useProxy = false) | |||||
{ | { | ||||
try | |||||
{ | |||||
return new DefaultRestClient(url); | |||||
} | |||||
catch (PlatformNotSupportedException ex) | |||||
return url => | |||||
{ | { | ||||
throw new PlatformNotSupportedException("The default RestClientProvider is not supported on this platform.", ex); | |||||
} | |||||
}; | |||||
try | |||||
{ | |||||
return new DefaultRestClient(url, useProxy); | |||||
} | |||||
catch (PlatformNotSupportedException ex) | |||||
{ | |||||
throw new PlatformNotSupportedException("The default RestClientProvider is not supported on this platform.", ex); | |||||
} | |||||
}; | |||||
} | |||||
} | } | ||||
} | } |
@@ -3,6 +3,7 @@ using System; | |||||
using System.Collections.Generic; | using System.Collections.Generic; | ||||
using System.ComponentModel; | using System.ComponentModel; | ||||
using System.IO; | using System.IO; | ||||
using System.Net; | |||||
using System.Net.WebSockets; | using System.Net.WebSockets; | ||||
using System.Text; | using System.Text; | ||||
using System.Threading; | using System.Threading; | ||||
@@ -23,18 +24,20 @@ namespace Discord.Net.WebSockets | |||||
private readonly SemaphoreSlim _lock; | private readonly SemaphoreSlim _lock; | ||||
private readonly Dictionary<string, string> _headers; | private readonly Dictionary<string, string> _headers; | ||||
private ClientWebSocket _client; | private ClientWebSocket _client; | ||||
private IWebProxy _proxy; | |||||
private Task _task; | private Task _task; | ||||
private CancellationTokenSource _cancelTokenSource; | private CancellationTokenSource _cancelTokenSource; | ||||
private CancellationToken _cancelToken, _parentToken; | private CancellationToken _cancelToken, _parentToken; | ||||
private bool _isDisposed, _isDisconnecting; | private bool _isDisposed, _isDisconnecting; | ||||
public DefaultWebSocketClient() | |||||
public DefaultWebSocketClient(IWebProxy proxy = null) | |||||
{ | { | ||||
_lock = new SemaphoreSlim(1, 1); | _lock = new SemaphoreSlim(1, 1); | ||||
_cancelTokenSource = new CancellationTokenSource(); | _cancelTokenSource = new CancellationTokenSource(); | ||||
_cancelToken = CancellationToken.None; | _cancelToken = CancellationToken.None; | ||||
_parentToken = CancellationToken.None; | _parentToken = CancellationToken.None; | ||||
_headers = new Dictionary<string, string>(); | _headers = new Dictionary<string, string>(); | ||||
_proxy = proxy; | |||||
} | } | ||||
private void Dispose(bool disposing) | private void Dispose(bool disposing) | ||||
{ | { | ||||
@@ -70,7 +73,7 @@ namespace Discord.Net.WebSockets | |||||
_cancelToken = CancellationTokenSource.CreateLinkedTokenSource(_parentToken, _cancelTokenSource.Token).Token; | _cancelToken = CancellationTokenSource.CreateLinkedTokenSource(_parentToken, _cancelTokenSource.Token).Token; | ||||
_client = new ClientWebSocket(); | _client = new ClientWebSocket(); | ||||
_client.Options.Proxy = null; | |||||
_client.Options.Proxy = _proxy; | |||||
_client.Options.KeepAliveInterval = TimeSpan.Zero; | _client.Options.KeepAliveInterval = TimeSpan.Zero; | ||||
foreach (var header in _headers) | foreach (var header in _headers) | ||||
{ | { | ||||
@@ -1,21 +1,27 @@ | |||||
using System; | using System; | ||||
using System.Net; | |||||
namespace Discord.Net.WebSockets | namespace Discord.Net.WebSockets | ||||
{ | { | ||||
public static class DefaultWebSocketProvider | public static class DefaultWebSocketProvider | ||||
{ | { | ||||
#if DEFAULTWEBSOCKET | #if DEFAULTWEBSOCKET | ||||
public static readonly WebSocketProvider Instance = () => | |||||
public static readonly WebSocketProvider Instance = Create(); | |||||
public static WebSocketProvider Create(IWebProxy proxy = null) | |||||
{ | { | ||||
try | |||||
{ | |||||
return new DefaultWebSocketClient(); | |||||
} | |||||
catch (PlatformNotSupportedException ex) | |||||
return () => | |||||
{ | { | ||||
throw new PlatformNotSupportedException("The default WebSocketProvider is not supported on this platform.", ex); | |||||
} | |||||
}; | |||||
try | |||||
{ | |||||
return new DefaultWebSocketClient(proxy); | |||||
} | |||||
catch (PlatformNotSupportedException ex) | |||||
{ | |||||
throw new PlatformNotSupportedException("The default WebSocketProvider is not supported on this platform.", ex); | |||||
} | |||||
}; | |||||
} | |||||
#else | #else | ||||
public static readonly WebSocketProvider Instance = () => | public static readonly WebSocketProvider Instance = () => | ||||
{ | { | ||||