[backend/core] Improve FastFallback handler in CustomHttpClient

This commit is contained in:
Laura Hausmann 2024-03-25 17:32:08 +01:00
parent 8ff938639b
commit f2d8bda393
No known key found for this signature in database
GPG key ID: D044E84C5BE01605

View file

@ -29,7 +29,7 @@ public class CustomHttpClient : HttpClient
var sortedRecords = await GetSortedAddresses(context.DnsEndPoint.Host, token); var sortedRecords = await GetSortedAddresses(context.DnsEndPoint.Host, token);
var linkedToken = CancellationTokenSource.CreateLinkedTokenSource(token); var linkedToken = CancellationTokenSource.CreateLinkedTokenSource(token);
var tasks = new List<Task<NetworkStream>>(); var tasks = new List<Task<(NetworkStream? stream, Exception? exception)>>();
var delayCts = CancellationTokenSource.CreateLinkedTokenSource(linkedToken.Token); var delayCts = CancellationTokenSource.CreateLinkedTokenSource(linkedToken.Token);
for (var i = 0; i < sortedRecords.Count; i++) for (var i = 0; i < sortedRecords.Count; i++)
@ -46,14 +46,31 @@ public class CustomHttpClient : HttpClient
delayCts = nextDelayCts; delayCts = nextDelayCts;
} }
var stream = await await Task.WhenAny(tasks).ConfigureAwait(false); NetworkStream? stream = null;
Exception? lastException = null;
while (tasks.Count > 0 && stream == null)
{
var task = await Task.WhenAny(tasks).ConfigureAwait(false);
var res = await task;
tasks.Remove(task);
stream = res.stream;
lastException = res.exception;
}
if (stream == null)
{
throw lastException ??
new Exception("An unknown exception occured during fast fallback connection attempt");
}
await linkedToken.CancelAsync(); await linkedToken.CancelAsync();
tasks.ForEach(task => { task.ContinueWith(_ => Task.CompletedTask, CancellationToken.None); }); tasks.ForEach(task => { task.ContinueWith(_ => Task.CompletedTask, CancellationToken.None); });
return stream; return stream;
} }
private static async Task<NetworkStream> AttemptConnection( private static async Task<(NetworkStream? stream, Exception? exception)> AttemptConnection(
IPAddress address, int port, CancellationToken token, CancellationToken delayToken IPAddress address, int port, CancellationToken token, CancellationToken delayToken
) )
{ {
@ -70,12 +87,12 @@ public class CustomHttpClient : HttpClient
try try
{ {
await socket.ConnectAsync(address, port, token).ConfigureAwait(false); await socket.ConnectAsync(address, port, token).ConfigureAwait(false);
return new NetworkStream(socket, true); return (new NetworkStream(socket, true), null);
} }
catch catch (Exception e)
{ {
socket.Dispose(); socket.Dispose();
throw; return (null, e);
} }
} }