From 508c694c3d551cddb3b15c1b0d4787dae3c00530 Mon Sep 17 00:00:00 2001 From: Rory& Date: Thu, 2 May 2024 07:20:13 +0200 Subject: HomeserverEmulator work --- LibMatrix/Extensions/HttpClientExtensions.cs | 34 ++++++++++++++++++++++++---- LibMatrix/RoomTypes/GenericRoom.cs | 6 +++-- 2 files changed, 34 insertions(+), 6 deletions(-) (limited to 'LibMatrix') diff --git a/LibMatrix/Extensions/HttpClientExtensions.cs b/LibMatrix/Extensions/HttpClientExtensions.cs index 01ce6ea..64b4f6a 100644 --- a/LibMatrix/Extensions/HttpClientExtensions.cs +++ b/LibMatrix/Extensions/HttpClientExtensions.cs @@ -29,6 +29,10 @@ public class MatrixHttpClient : HttpClient { public Dictionary AdditionalQueryParameters { get; set; } = new(); internal string? AssertedUserId { get; set; } + internal SemaphoreSlim _rateLimitSemaphore { get; } = new(1, 1); + + internal const bool debug = false; + private JsonSerializerOptions GetJsonSerializerOptions(JsonSerializerOptions? options = null) { options ??= new JsonSerializerOptions(); options.Converters.Add(new JsonFloatStringConverter()); @@ -39,7 +43,8 @@ public class MatrixHttpClient : HttpClient { } public async Task SendUnhandledAsync(HttpRequestMessage request, CancellationToken cancellationToken) { - Console.WriteLine($"Sending {request.Method} {BaseAddress}{request.RequestUri} ({Util.BytesToString(request.Content?.Headers.ContentLength ?? 0)})"); + if(debug) await _rateLimitSemaphore.WaitAsync(cancellationToken); + // Console.WriteLine($"Sending {request.Method} {BaseAddress}{request.RequestUri} ({Util.BytesToString(request.Content?.Headers.ContentLength ?? 0)})"); if (request.RequestUri is null) throw new NullReferenceException("RequestUri is null"); if (!request.RequestUri.IsAbsoluteUri) request.RequestUri = new Uri(BaseAddress, request.RequestUri); // if (AssertedUserId is not null) request.RequestUri = request.RequestUri.AddQuery("user_id", AssertedUserId); @@ -57,7 +62,17 @@ public class MatrixHttpClient : HttpClient { Console.WriteLine(e); } - var responseMessage = await base.SendAsync(request, HttpCompletionOption.ResponseHeadersRead, cancellationToken); + HttpResponseMessage? responseMessage; + try { + responseMessage = await base.SendAsync(request, HttpCompletionOption.ResponseHeadersRead, cancellationToken); + } + catch (Exception e) { + Console.WriteLine($"Failed to send request {request.Method} {BaseAddress}{request.RequestUri} ({Util.BytesToString(request.Content?.Headers.ContentLength ?? 0)}):\n{e}"); + throw; + } + finally { + if(debug) _rateLimitSemaphore.Release(); + } return responseMessage; } @@ -75,7 +90,18 @@ public class MatrixHttpClient : HttpClient { }; if (!content.StartsWith('{')) throw new InvalidDataException("Encountered invalid data:\n" + content); //we have a matrix error - var ex = JsonSerializer.Deserialize(content); + + MatrixException? ex = null; + try { + ex = JsonSerializer.Deserialize(content); + } + catch (JsonException e) { + throw new LibMatrixException() { + ErrorCode = "M_INVALID_JSON", + Error = e.Message + "\nBody:\n" + await responseMessage.Content.ReadAsStringAsync(cancellationToken) + }; + } + Debug.Assert(ex != null, nameof(ex) + " != null"); ex.RawContent = content; // Console.WriteLine($"Failed to send request: {ex}"); @@ -136,7 +162,7 @@ public class MatrixHttpClient : HttpClient { options = GetJsonSerializerOptions(options); var request = new HttpRequestMessage(HttpMethod.Put, requestUri); request.Headers.Accept.Add(new MediaTypeWithQualityHeaderValue("application/json")); - Console.WriteLine($"Sending PUT {requestUri}"); + // Console.WriteLine($"Sending PUT {requestUri}"); // Console.WriteLine($"Content: {JsonSerializer.Serialize(value, value.GetType(), options)}"); // Console.WriteLine($"Type: {value.GetType().FullName}"); request.Content = new StringContent(JsonSerializer.Serialize(value, value.GetType(), options), diff --git a/LibMatrix/RoomTypes/GenericRoom.cs b/LibMatrix/RoomTypes/GenericRoom.cs index 43f3acc..742f5d9 100644 --- a/LibMatrix/RoomTypes/GenericRoom.cs +++ b/LibMatrix/RoomTypes/GenericRoom.cs @@ -517,18 +517,20 @@ public class GenericRoom { #endregion public async IAsyncEnumerable GetRelatedEventsAsync(string eventId, string? relationType = null, string? eventType = null, string? dir = "f", - string? from = null, int? chunkLimit = 100, bool? recurse = false, string? to = null) { - var path = $"/_matrix/client/v3/rooms/{RoomId}/relations/{eventId}"; + string? from = null, int? chunkLimit = 100, bool? recurse = null, string? to = null) { + var path = $"/_matrix/client/v1/rooms/{RoomId}/relations/{HttpUtility.UrlEncode(eventId)}"; if (!string.IsNullOrEmpty(relationType)) path += $"/{relationType}"; if (!string.IsNullOrEmpty(eventType)) path += $"/{eventType}"; var uri = new Uri(path, UriKind.Relative); if (dir == "b" || dir == "f") uri = uri.AddQuery("dir", dir); + else if(!string.IsNullOrWhiteSpace(dir)) throw new ArgumentException("Invalid direction", nameof(dir)); if (!string.IsNullOrEmpty(from)) uri = uri.AddQuery("from", from); if (chunkLimit is not null) uri = uri.AddQuery("limit", chunkLimit.Value.ToString()); if (recurse is not null) uri = uri.AddQuery("recurse", recurse.Value.ToString()); if (!string.IsNullOrEmpty(to)) uri = uri.AddQuery("to", to); + // Console.WriteLine($"Getting related events from {uri}"); var result = await Homeserver.ClientHttpClient.GetFromJsonAsync(uri); while (result!.Chunk.Count > 0) { foreach (var resp in result.Chunk) { -- cgit 1.4.1