diff options
Diffstat (limited to 'MatrixRoomUtils.Core/RoomTypes/GenericRoom.cs')
-rw-r--r-- | MatrixRoomUtils.Core/RoomTypes/GenericRoom.cs | 226 |
1 files changed, 71 insertions, 155 deletions
diff --git a/MatrixRoomUtils.Core/RoomTypes/GenericRoom.cs b/MatrixRoomUtils.Core/RoomTypes/GenericRoom.cs index 8dc30d1..f57c855 100644 --- a/MatrixRoomUtils.Core/RoomTypes/GenericRoom.cs +++ b/MatrixRoomUtils.Core/RoomTypes/GenericRoom.cs @@ -1,15 +1,17 @@ using System.Net.Http.Json; -using System.Text; using System.Text.Json; using System.Web; using MatrixRoomUtils.Core.Extensions; +using MatrixRoomUtils.Core.Responses; using MatrixRoomUtils.Core.RoomTypes; +using MatrixRoomUtils.Core.StateEventTypes; +using Microsoft.Extensions.Logging; namespace MatrixRoomUtils.Core; public class GenericRoom { internal readonly AuthenticatedHomeServer _homeServer; - internal readonly HttpClient _httpClient; + internal readonly MatrixHttpClient _httpClient; public GenericRoom(AuthenticatedHomeServer homeServer, string roomId) { _homeServer = homeServer; @@ -21,51 +23,41 @@ public class GenericRoom { public string RoomId { get; set; } - public async Task<JsonElement?> GetStateAsync(string type, string stateKey = "", bool logOnFailure = true) { + [Obsolete("", true)] + public async Task<JsonElement?> GetStateAsync(string type, string stateKey = "") { var url = $"/_matrix/client/v3/rooms/{RoomId}/state"; if (!string.IsNullOrEmpty(type)) url += $"/{type}"; if (!string.IsNullOrEmpty(stateKey)) url += $"/{stateKey}"; + return await _httpClient.GetFromJsonAsync<JsonElement>(url); + } - var res = await _httpClient.GetAsync(url); - if (!res.IsSuccessStatusCode) { - if (logOnFailure) Console.WriteLine($"{RoomId}/{stateKey}/{type} - got status: {res.StatusCode}"); - return null; + public async IAsyncEnumerable<StateEventResponse?> GetFullStateAsync() { + var res = await _httpClient.GetAsync($"/_matrix/client/v3/rooms/{RoomId}/state"); + var result = + JsonSerializer.DeserializeAsyncEnumerable<StateEventResponse>(await res.Content.ReadAsStreamAsync()); + await foreach (var resp in result) { + yield return resp; } - - var result = await res.Content.ReadFromJsonAsync<JsonElement>(); - return result; } - public async Task<T?> GetStateAsync<T>(string type, string stateKey = "", bool logOnFailure = false) { - var res = await GetStateAsync(type, stateKey, logOnFailure); - if (res == null) return default; - return res.Value.Deserialize<T>(); + public async Task<T?> GetStateAsync<T>(string type, string stateKey = "") { + var url = $"/_matrix/client/v3/rooms/{RoomId}/state"; + if (!string.IsNullOrEmpty(type)) url += $"/{type}"; + if (!string.IsNullOrEmpty(stateKey)) url += $"/{stateKey}"; + return await _httpClient.GetFromJsonAsync<T>(url); } public async Task<MessagesResponse> GetMessagesAsync(string from = "", int limit = 10, string dir = "b", string filter = "") { var url = $"/_matrix/client/v3/rooms/{RoomId}/messages?from={from}&limit={limit}&dir={dir}"; if (!string.IsNullOrEmpty(filter)) url += $"&filter={filter}"; - var res = await _httpClient.GetAsync(url); - if (!res.IsSuccessStatusCode) { - Console.WriteLine($"Failed to get messages for {RoomId} - got status: {res.StatusCode}"); - throw new Exception($"Failed to get messages for {RoomId} - got status: {res.StatusCode}"); - } - - var result = await res.Content.ReadFromJsonAsync<MessagesResponse>(); - return result ?? new MessagesResponse(); + var res = await _httpClient.GetFromJsonAsync<MessagesResponse>(url); + return res ?? new MessagesResponse(); } public async Task<string> GetNameAsync() { - var res = await GetStateAsync("m.room.name"); - if (!res.HasValue) { - Console.WriteLine($"Room {RoomId} has no name!"); - return RoomId; - } - - var resn = res?.TryGetProperty("name", out var name) ?? false ? name.GetString() ?? RoomId : RoomId; - //Console.WriteLine($"Got name: {resn}"); - return resn; + var res = await GetStateAsync<RoomNameEventData>("m.room.name"); + return res.Name ?? RoomId; } public async Task JoinAsync(string[]? homeservers = null, string? reason = null) { @@ -78,165 +70,89 @@ public class GenericRoom { }); } - public async Task<List<string>> GetMembersAsync(bool joinedOnly = true) { - var res = await GetStateAsync(""); - if (!res.HasValue) return new List<string>(); - var members = new List<string>(); - foreach (var member in res.Value.EnumerateArray()) { - if (member.GetProperty("type").GetString() != "m.room.member") continue; - if (joinedOnly && member.GetProperty("content").GetProperty("membership").GetString() != "join") continue; - var memberId = member.GetProperty("state_key").GetString(); - members.Add( - memberId ?? throw new InvalidOperationException("Event type was member but state key was null!")); + public async IAsyncEnumerable<StateEventResponse> GetMembersAsync(bool joinedOnly = true) { + var res = GetFullStateAsync(); + await foreach (var member in res) { + if (member.Type != "m.room.member") continue; + if (joinedOnly && (member.TypedContent as RoomMemberEventData).Membership is not "join") continue; + yield return member; } - - return members; } public async Task<List<string>> GetAliasesAsync() { - var res = await GetStateAsync("m.room.aliases"); - if (!res.HasValue) return new List<string>(); - var aliases = new List<string>(); - foreach (var alias in res.Value.GetProperty("aliases").EnumerateArray()) aliases.Add(alias.GetString() ?? ""); - - return aliases; + var res = await GetStateAsync<RoomAliasEventData>("m.room.aliases"); + return res.Aliases; } - public async Task<string> GetCanonicalAliasAsync() { - var res = await GetStateAsync("m.room.canonical_alias"); - if (!res.HasValue) return ""; - return res.Value.GetProperty("alias").GetString() ?? ""; - } - - public async Task<string> GetTopicAsync() { - var res = await GetStateAsync("m.room.topic"); - if (!res.HasValue) return ""; - return res.Value.GetProperty("topic").GetString() ?? ""; - } - - public async Task<string> GetAvatarUrlAsync() { - var res = await GetStateAsync("m.room.avatar"); - if (!res.HasValue) return ""; - return res.Value.GetProperty("url").GetString() ?? ""; - } + public async Task<CanonicalAliasEventData?> GetCanonicalAliasAsync() => + await GetStateAsync<CanonicalAliasEventData>("m.room.canonical_alias"); - public async Task<JoinRulesEventData> GetJoinRuleAsync() { - var res = await GetStateAsync("m.room.join_rules"); - if (!res.HasValue) return new JoinRulesEventData(); - return res.Value.Deserialize<JoinRulesEventData>() ?? new JoinRulesEventData(); - } + public async Task<RoomTopicEventData?> GetTopicAsync() => + await GetStateAsync<RoomTopicEventData>("m.room.topic"); - public async Task<string> GetHistoryVisibilityAsync() { - var res = await GetStateAsync("m.room.history_visibility"); - if (!res.HasValue) return ""; - return res.Value.GetProperty("history_visibility").GetString() ?? ""; - } + public async Task<RoomAvatarEventData?> GetAvatarUrlAsync() => + await GetStateAsync<RoomAvatarEventData>("m.room.avatar"); - public async Task<string> GetGuestAccessAsync() { - var res = await GetStateAsync("m.room.guest_access"); - if (!res.HasValue) return ""; - return res.Value.GetProperty("guest_access").GetString() ?? ""; - } + public async Task<JoinRulesEventData> GetJoinRuleAsync() => + await GetStateAsync<JoinRulesEventData>("m.room.join_rules"); - public async Task<CreateEvent> GetCreateEventAsync() { - var res = await GetStateAsync("m.room.create"); - if (!res.HasValue) return new CreateEvent(); + public async Task<HistoryVisibilityData?> GetHistoryVisibilityAsync() => + await GetStateAsync<HistoryVisibilityData>("m.room.history_visibility"); - res.FindExtraJsonElementFields(typeof(CreateEvent)); + public async Task<GuestAccessData?> GetGuestAccessAsync() => + await GetStateAsync<GuestAccessData>("m.room.guest_access"); - return res.Value.Deserialize<CreateEvent>() ?? new CreateEvent(); - } + public async Task<CreateEvent> GetCreateEventAsync() => + await GetStateAsync<CreateEvent>("m.room.create"); public async Task<string?> GetRoomType() { - var res = await GetStateAsync("m.room.create"); - if (!res.HasValue) return null; - if (res.Value.TryGetProperty("type", out var type)) return type.GetString(); - return null; + var res = await GetStateAsync<RoomCreateEventData>("m.room.create"); + return res.Type; } - public async Task ForgetAsync() { - var res = await _httpClient.PostAsync($"/_matrix/client/v3/rooms/{RoomId}/forget", null); - if (!res.IsSuccessStatusCode) { - Console.WriteLine($"Failed to forget room {RoomId} - got status: {res.StatusCode}"); - throw new Exception($"Failed to forget room {RoomId} - got status: {res.StatusCode}"); - } - } + public async Task ForgetAsync() => + await _httpClient.PostAsync($"/_matrix/client/v3/rooms/{RoomId}/forget", null); - public async Task LeaveAsync(string? reason = null) { - var res = await _httpClient.PostAsJsonAsync($"/_matrix/client/v3/rooms/{RoomId}/leave", new { + public async Task LeaveAsync(string? reason = null) => + await _httpClient.PostAsJsonAsync($"/_matrix/client/v3/rooms/{RoomId}/leave", new { reason }); - if (!res.IsSuccessStatusCode) { - Console.WriteLine($"Failed to leave room {RoomId} - got status: {res.StatusCode}"); - throw new Exception($"Failed to leave room {RoomId} - got status: {res.StatusCode}"); - } - } - public async Task KickAsync(string userId, string? reason = null) { - var res = await _httpClient.PostAsJsonAsync($"/_matrix/client/v3/rooms/{RoomId}/kick", + public async Task KickAsync(string userId, string? reason = null) => + await _httpClient.PostAsJsonAsync($"/_matrix/client/v3/rooms/{RoomId}/kick", new UserIdAndReason() { UserId = userId, Reason = reason }); - if (!res.IsSuccessStatusCode) { - Console.WriteLine($"Failed to kick {userId} from room {RoomId} - got status: {res.StatusCode}"); - throw new Exception($"Failed to kick {userId} from room {RoomId} - got status: {res.StatusCode}"); - } - } - public async Task BanAsync(string userId, string? reason = null) { - var res = await _httpClient.PostAsJsonAsync($"/_matrix/client/v3/rooms/{RoomId}/ban", + public async Task BanAsync(string userId, string? reason = null) => + await _httpClient.PostAsJsonAsync($"/_matrix/client/v3/rooms/{RoomId}/ban", new UserIdAndReason() { UserId = userId, Reason = reason }); - if (!res.IsSuccessStatusCode) { - Console.WriteLine($"Failed to ban {userId} from room {RoomId} - got status: {res.StatusCode}"); - throw new Exception($"Failed to ban {userId} from room {RoomId} - got status: {res.StatusCode}"); - } - } - public async Task UnbanAsync(string userId) { - var res = await _httpClient.PostAsJsonAsync($"/_matrix/client/v3/rooms/{RoomId}/unban", + public async Task UnbanAsync(string userId) => + await _httpClient.PostAsJsonAsync($"/_matrix/client/v3/rooms/{RoomId}/unban", new UserIdAndReason() { UserId = userId }); - if (!res.IsSuccessStatusCode) { - Console.WriteLine($"Failed to unban {userId} from room {RoomId} - got status: {res.StatusCode}"); - throw new Exception($"Failed to unban {userId} from room {RoomId} - got status: {res.StatusCode}"); - } - } - - public async Task<EventIdResponse> SendStateEventAsync(string eventType, object content) { - var res = await _httpClient.PostAsJsonAsync($"/_matrix/client/v3/rooms/{RoomId}/state/{eventType}", content); - if (!res.IsSuccessStatusCode) { - Console.WriteLine( - $"Failed to send state event {eventType} to room {RoomId} - got status: {res.StatusCode}"); - throw new Exception( - $"Failed to send state event {eventType} to room {RoomId} - got status: {res.StatusCode}"); - } - return await res.Content.ReadFromJsonAsync<EventIdResponse>(); - } + public async Task<EventIdResponse> SendStateEventAsync(string eventType, object content) => + await (await _httpClient.PostAsJsonAsync($"/_matrix/client/v3/rooms/{RoomId}/state/{eventType}", content)) + .Content.ReadFromJsonAsync<EventIdResponse>(); public async Task<EventIdResponse> SendMessageEventAsync(string eventType, MessageEventData content) { - var url = $"/_matrix/client/v3/rooms/{RoomId}/send/{eventType}/" + Guid.NewGuid(); - var res = await _httpClient.PutAsJsonAsync(url, content); - if (!res.IsSuccessStatusCode) { - Console.WriteLine($"Failed to send event {eventType} to room {RoomId} - got status: {res.StatusCode}"); - throw new Exception($"Failed to send event {eventType} to room {RoomId} - got status: {res.StatusCode}"); - } - + var res = await _httpClient.PutAsJsonAsync( + $"/_matrix/client/v3/rooms/{RoomId}/send/{eventType}/" + Guid.NewGuid(), content); var resu = await res.Content.ReadFromJsonAsync<EventIdResponse>(); - return resu; } public async Task<EventIdResponse> SendFileAsync(string eventType, string fileName, Stream fileStream) { - var url = $"/_matrix/client/v3/rooms/{RoomId}/send/{eventType}/" + Guid.NewGuid(); var content = new MultipartFormDataContent(); content.Add(new StreamContent(fileStream), "file", fileName); - var res = await _httpClient.PutAsync(url, content); - if (!res.IsSuccessStatusCode) { - Console.WriteLine($"Failed to send event {eventType} to room {RoomId} - got status: {res.StatusCode}"); - throw new Exception($"Failed to send event {eventType} to room {RoomId} - got status: {res.StatusCode}"); - } - - var resu = await res.Content.ReadFromJsonAsync<EventIdResponse>(); - - return resu; + var res = await + ( + await _httpClient.PutAsync( + $"/_matrix/client/v3/rooms/{RoomId}/send/{eventType}/" + Guid.NewGuid(), + content + ) + ) + .Content.ReadFromJsonAsync<EventIdResponse>(); + return res; } public readonly SpaceRoom AsSpace; |