From 91319ba62de889bde645b6f1df4dd6a960ee7de4 Mon Sep 17 00:00:00 2001 From: Rory& Date: Sun, 21 Sep 2025 15:49:54 +0200 Subject: Dependency updates, some fixes, partial msc2545 support --- LibMatrix/Extensions/MatrixHttpClient.Single.cs | 48 ++++++++++++++++++++++--- LibMatrix/Helpers/RoomBuilder.cs | 10 +++++- LibMatrix/LibMatrix.csproj | 4 +-- LibMatrix/RoomTypes/GenericRoom.cs | 12 +++++++ LibMatrix/Services/HomeserverProviderService.cs | 2 +- LibMatrix/Services/HomeserverResolverService.cs | 4 ++- 6 files changed, 70 insertions(+), 10 deletions(-) (limited to 'LibMatrix') diff --git a/LibMatrix/Extensions/MatrixHttpClient.Single.cs b/LibMatrix/Extensions/MatrixHttpClient.Single.cs index 26fb31f..aa188dd 100644 --- a/LibMatrix/Extensions/MatrixHttpClient.Single.cs +++ b/LibMatrix/Extensions/MatrixHttpClient.Single.cs @@ -55,6 +55,10 @@ public class MatrixHttpClient { public Dictionary AdditionalQueryParameters { get; set; } = new(); public Uri? BaseAddress { get; set; } + public bool RetryOnNetworkError { get; set; } = true; + public bool RetryOnMatrixError { get; set; } = true; + + private Dictionary _retries = []; // default headers, not bound to client public HttpRequestHeaders DefaultRequestHeaders { get; set; } = @@ -151,8 +155,37 @@ public class MatrixHttpClient { } public async Task SendAsync(HttpRequestMessage request, CancellationToken cancellationToken = default) { - var responseMessage = await SendUnhandledAsync(request, cancellationToken); - if (responseMessage.IsSuccessStatusCode) return responseMessage; + _retries.TryAdd(request, 10); + HttpResponseMessage responseMessage; + try { + responseMessage = await SendUnhandledAsync(request, cancellationToken); + } + catch (HttpRequestException ex) { + if (RetryOnNetworkError) { + if (_retries[request]-- <= 0) throw; + if (ex.InnerException?.GetType().FullName == "System.Runtime.InteropServices.JavaScript.JSException") + Console.WriteLine("Got JSException, likely a CORS error due to a reverse proxy misconfiguration and error, retrying..."); + else + Console.WriteLine(new { + ex.HttpRequestError, + ex.StatusCode, + ex.Data, + ex.Message, + InnerException = ex.InnerException?.ToString(), + InnerExceptionType = ex.InnerException?.GetType().FullName + }.ToJson()); + + await Task.Delay(Random.Shared.Next(1000, 2000), cancellationToken); + request.ResetSendStatus(); + return await SendAsync(request, cancellationToken); + } + throw; + } + + if (responseMessage.IsSuccessStatusCode) { + _retries.Remove(request); + return responseMessage; + } //retry on gateway timeout // if (responseMessage.StatusCode == HttpStatusCode.GatewayTimeout) { @@ -192,14 +225,19 @@ public class MatrixHttpClient { request.ResetSendStatus(); return await SendAsync(request, cancellationToken); } + throw ex; } if (responseMessage.StatusCode == HttpStatusCode.BadGateway) { // spread out retries - await Task.Delay(Random.Shared.Next(1000, 2000), cancellationToken); - request.ResetSendStatus(); - return await SendAsync(request, cancellationToken); + if (RetryOnNetworkError) { + if (_retries[request]-- <= 0) throw new InvalidDataException("Encountered invalid data:\n" + content); + Console.WriteLine("Got 502 Bad Gateway, retrying..."); + await Task.Delay(Random.Shared.Next(1000, 2000), cancellationToken); + request.ResetSendStatus(); + return await SendAsync(request, cancellationToken); + } } responseMessage.EnsureSuccessStatusCode(); diff --git a/LibMatrix/Helpers/RoomBuilder.cs b/LibMatrix/Helpers/RoomBuilder.cs index 0b0b5f8..6e24103 100644 --- a/LibMatrix/Helpers/RoomBuilder.cs +++ b/LibMatrix/Helpers/RoomBuilder.cs @@ -83,7 +83,15 @@ public class RoomBuilder { { RoomPowerLevelEventContent.EventId, 100 }, { RoomServerAclEventContent.EventId, 100 }, { RoomTombstoneEventContent.EventId, 150 }, - { RoomPolicyServerEventContent.EventId, 100 } + { RoomPolicyServerEventContent.EventId, 100 }, + { RoomPinnedEventContent.EventId, 50 }, + // recommended extensions + { "im.vector.modular.widgets", 50}, + // { "m.reaction", 0 }, // we probably don't want these to end up as room state + // - prevent calls + { "io.element.voice_broadcast_info", 50 }, + { "org.matrix.msc3401.call", 50 }, + { "org.matrix.msc3401.call.member", 50 }, } }; diff --git a/LibMatrix/LibMatrix.csproj b/LibMatrix/LibMatrix.csproj index c1049b5..c6c1dce 100644 --- a/LibMatrix/LibMatrix.csproj +++ b/LibMatrix/LibMatrix.csproj @@ -12,8 +12,8 @@ - - + + diff --git a/LibMatrix/RoomTypes/GenericRoom.cs b/LibMatrix/RoomTypes/GenericRoom.cs index 0077acb..58e5434 100644 --- a/LibMatrix/RoomTypes/GenericRoom.cs +++ b/LibMatrix/RoomTypes/GenericRoom.cs @@ -704,6 +704,18 @@ public class GenericRoom { } public async Task> GetHomeserversInRoom() => (await GetMemberIdsListAsync("join")).Select(x => x.Split(':', 2)[1]).Distinct().ToList(); + + public async Task IsJoinedAsync() { + try { + var member = await GetStateOrNullAsync(RoomMemberEventContent.EventId, Homeserver.UserId); + return member?.Membership == "join"; + } + catch (MatrixException e) { + if (e.ErrorCode == "M_NOT_FOUND") return false; + if (e.ErrorCode == "M_FORBIDDEN") return false; + throw; + } + } } public class RoomIdResponse { diff --git a/LibMatrix/Services/HomeserverProviderService.cs b/LibMatrix/Services/HomeserverProviderService.cs index c984c34..52aadd2 100644 --- a/LibMatrix/Services/HomeserverProviderService.cs +++ b/LibMatrix/Services/HomeserverProviderService.cs @@ -17,7 +17,7 @@ public class HomeserverProviderService(ILogger logger if (!enableClient && !enableServer) throw new ArgumentException("At least one of enableClient or enableServer must be true"); - return await AuthenticatedHomeserverCache.GetOrAdd($"{homeserver}{accessToken}{proxy}{impersonatedMxid}", async () => { + return await AuthenticatedHomeserverCache.GetOrAdd($"{homeserver}{accessToken}{proxy}{impersonatedMxid}{useGeneric}{enableClient}{enableServer}", async () => { var wellKnownUris = await hsResolver.ResolveHomeserverFromWellKnown(homeserver, enableClient, enableServer); var rhs = new RemoteHomeserver(homeserver, wellKnownUris, proxy); diff --git a/LibMatrix/Services/HomeserverResolverService.cs b/LibMatrix/Services/HomeserverResolverService.cs index 94a3826..7d30b7b 100644 --- a/LibMatrix/Services/HomeserverResolverService.cs +++ b/LibMatrix/Services/HomeserverResolverService.cs @@ -9,7 +9,9 @@ using Microsoft.Extensions.Logging.Abstractions; namespace LibMatrix.Services; public class HomeserverResolverService { - private readonly MatrixHttpClient _httpClient = new(); + private readonly MatrixHttpClient _httpClient = new() { + RetryOnNetworkError = false + }; private static readonly SemaphoreCache WellKnownCache = new(); -- cgit 1.5.1