diff options
Diffstat (limited to 'LibMatrix')
-rw-r--r-- | LibMatrix/Helpers/SyncHelper.cs | 28 | ||||
-rw-r--r-- | LibMatrix/Helpers/SyncStateResolver.cs | 2 | ||||
-rw-r--r-- | LibMatrix/RoomTypes/GenericRoom.cs | 3 | ||||
-rw-r--r-- | LibMatrix/StateEvent.cs | 42 |
4 files changed, 46 insertions, 29 deletions
diff --git a/LibMatrix/Helpers/SyncHelper.cs b/LibMatrix/Helpers/SyncHelper.cs index a05b915..334c288 100644 --- a/LibMatrix/Helpers/SyncHelper.cs +++ b/LibMatrix/Helpers/SyncHelper.cs @@ -1,4 +1,5 @@ using System.Diagnostics; +using System.Net.Http.Json; using ArcaneLibs.Extensions; using LibMatrix.Filters; using LibMatrix.Homeservers; @@ -12,23 +13,41 @@ public class SyncHelper(AuthenticatedHomeserverGeneric homeserver, ILogger? logg public int Timeout { get; set; } = 30000; public string? SetPresence { get; set; } = "online"; public SyncFilter? Filter { get; set; } - public bool FullState { get; set; } = false; + public bool FullState { get; set; } public bool IsInitialSync { get; set; } = true; + public TimeSpan MinimumDelay { get; set; } = new(0); + public async Task<SyncResponse?> SyncAsync(CancellationToken? cancellationToken = null) { if (homeserver is null) { Console.WriteLine("Null passed as homeserver for SyncHelper!"); - throw new ArgumentNullException("Null passed as homeserver for SyncHelper!"); + throw new ArgumentNullException(nameof(homeserver), "Null passed as homeserver for SyncHelper!"); + } + if (homeserver.ClientHttpClient is null) { + Console.WriteLine("Homeserver for SyncHelper is not properly configured!"); + throw new ArgumentNullException(nameof(homeserver.ClientHttpClient), "Null passed as homeserver for SyncHelper!"); } + + var sw = Stopwatch.StartNew(); + var url = $"/_matrix/client/v3/sync?timeout={Timeout}&set_presence={SetPresence}&full_state={(FullState ? "true" : "false")}"; if (!string.IsNullOrWhiteSpace(Since)) url += $"&since={Since}"; if (Filter is not null) url += $"&filter={Filter.ToJson(ignoreNull: true, indent: false)}"; // Console.WriteLine("Calling: " + url); logger?.LogInformation("SyncHelper: Calling: {}", url); try { - return await homeserver?.ClientHttpClient?.GetFromJsonAsync<SyncResponse>(url, cancellationToken: cancellationToken ?? CancellationToken.None)!; + var httpResp = await homeserver.ClientHttpClient.GetAsync(url, cancellationToken: cancellationToken ?? CancellationToken.None)!; + if (httpResp is null) throw new NullReferenceException("Failed to send HTTP request"); + logger?.LogInformation("Got sync response: {} bytes, {} elapsed", httpResp?.Content.Headers.ContentLength ?? -1, sw.Elapsed); + var deserializeSw = Stopwatch.StartNew(); + var resp = await httpResp.Content.ReadFromJsonAsync<SyncResponse>(cancellationToken: cancellationToken ?? CancellationToken.None)!; + logger?.LogInformation("Deserialized sync response: {} bytes, {} elapsed, {} total", httpResp?.Content.Headers.ContentLength ?? -1, deserializeSw.Elapsed, sw.Elapsed); + var timeToWait = MinimumDelay.Subtract(sw.Elapsed); + if (timeToWait.TotalMilliseconds > 0) + await Task.Delay(timeToWait); + return resp; } catch (TaskCanceledException) { Console.WriteLine("Sync cancelled!"); @@ -57,7 +76,6 @@ public class SyncHelper(AuthenticatedHomeserverGeneric homeserver, ILogger? logg var oldTimeout = Timeout; Timeout = 0; await foreach (var sync in EnumerateSyncAsync(cancellationToken)) { - logger?.LogInformation("Got sync response: {} bytes, {} elapsed", sync?.ToJson(ignoreNull: true, indent: false).Length ?? -1, sw.Elapsed); if (sync?.ToJson(ignoreNull: true, indent: false).Length < 250) { emptyInitialSyncCount++; if (emptyInitialSyncCount > 5) { @@ -125,4 +143,4 @@ public class SyncHelper(AuthenticatedHomeserverGeneric homeserver, ILogger? logg /// Event fired when an account data event is received /// </summary> public List<Func<StateEventResponse, Task>> AccountDataReceivedHandlers { get; } = new(); -} +} \ No newline at end of file diff --git a/LibMatrix/Helpers/SyncStateResolver.cs b/LibMatrix/Helpers/SyncStateResolver.cs index 3482be3..f40fa22 100644 --- a/LibMatrix/Helpers/SyncStateResolver.cs +++ b/LibMatrix/Helpers/SyncStateResolver.cs @@ -13,7 +13,7 @@ public class SyncStateResolver(AuthenticatedHomeserverGeneric homeserver, ILogge public SyncFilter? Filter { get; set; } public bool FullState { get; set; } = false; - public SyncResponse? MergedState { get; set; } = null!; + public SyncResponse? MergedState { get; set; } private SyncHelper _syncHelper = new SyncHelper(homeserver, logger); diff --git a/LibMatrix/RoomTypes/GenericRoom.cs b/LibMatrix/RoomTypes/GenericRoom.cs index a64e167..9804e78 100644 --- a/LibMatrix/RoomTypes/GenericRoom.cs +++ b/LibMatrix/RoomTypes/GenericRoom.cs @@ -173,7 +173,8 @@ public class GenericRoom { var resText = await res.Content.ReadAsStringAsync(); Console.WriteLine($"Members call response read in {sw.GetElapsedAndRestart()}"); var result = await JsonSerializer.DeserializeAsync<ChunkedStateEventResponse>(await res.Content.ReadAsStreamAsync(), new JsonSerializerOptions() { - TypeInfoResolver = ChunkedStateEventResponseSerializerContext.Default + TypeInfoResolver = ChunkedStateEventResponseSerializerContext.Default, + }); Console.WriteLine($"Members call deserialised in {sw.GetElapsedAndRestart()}"); foreach (var resp in result.Chunk) { diff --git a/LibMatrix/StateEvent.cs b/LibMatrix/StateEvent.cs index 6d69820..6ca82f4 100644 --- a/LibMatrix/StateEvent.cs +++ b/LibMatrix/StateEvent.cs @@ -1,3 +1,4 @@ +using System.Diagnostics.CodeAnalysis; using System.Reflection; using System.Text.Json; using System.Text.Json.Nodes; @@ -29,26 +30,26 @@ public class StateEvent { return typeof(Dictionary<string, JsonObject>); } - // var eventType = KnownStateEventTypes.FirstOrDefault(x => - // x.GetCustomAttributes<MatrixEventAttribute>()?.Any(y => y.EventName == type) ?? false); - var eventType = KnownStateEventTypesByName.GetValueOrDefault(type); - - return eventType ?? typeof(UnknownEventContent); + return KnownStateEventTypesByName.GetValueOrDefault(type) ?? typeof(UnknownEventContent); } + private static readonly JsonSerializerOptions TypedContentSerializerOptions = new JsonSerializerOptions() { + Converters = { + new JsonFloatStringConverter(), + new JsonDoubleStringConverter(), + new JsonDecimalStringConverter() + } + }; + [JsonIgnore] - public EventContent TypedContent { + [SuppressMessage("ReSharper", "PropertyCanBeMadeInitOnly.Global")] + public EventContent? TypedContent { get { - if (Type == "m.receipt") { - return null!; - } + // if (Type == "m.receipt") { + // return null; + // } try { - var jse = new JsonSerializerOptions(); - jse ??= new JsonSerializerOptions(); - jse.Converters.Add(new JsonFloatStringConverter()); - jse.Converters.Add(new JsonDoubleStringConverter()); - jse.Converters.Add(new JsonDecimalStringConverter()); - return (EventContent)RawContent.Deserialize(GetType, jse)!; + return (EventContent)RawContent.Deserialize(GetType, TypedContentSerializerOptions)!; } catch (JsonException e) { Console.WriteLine(e); @@ -59,7 +60,7 @@ public class StateEvent { } set { if (value is null) { - RawContent = null; + RawContent?.Clear(); } else RawContent = JsonSerializer.Deserialize<JsonObject>(JsonSerializer.Serialize(value, value.GetType())); } @@ -69,7 +70,7 @@ public class StateEvent { public string StateKey { get; set; } = ""; [JsonPropertyName("type")] - public string Type { get; set; } + public required string Type { get; set; } [JsonPropertyName("replaces_state")] public string? ReplacesState { get; set; } @@ -121,7 +122,7 @@ public class StateEvent { //debug [JsonIgnore] - public string dtype { + public string InternalSelfTypeName { get { var res = GetType().Name switch { "StateEvent`1" => "StateEvent", @@ -132,7 +133,7 @@ public class StateEvent { } [JsonIgnore] - public string cdtype => TypedContent.GetType().Name; + public string InternalContentTypeName => TypedContent?.GetType().Name ?? "null"; } @@ -152,9 +153,6 @@ public class StateEventResponse : StateEvent { [JsonPropertyName("event_id")] public string EventId { get; set; } - // [JsonPropertyName("user_id")] - // public string UserId { get; set; } - [JsonPropertyName("replaces_state")] public new string ReplacesState { get; set; } |