From c0e8a6d680f356acb6afbfeb75ca5bc85cc4baaa Mon Sep 17 00:00:00 2001 From: Laura Hausmann Date: Wed, 20 Nov 2024 02:15:16 +0100 Subject: [PATCH] [backend/streaming] Fix streaming updates not containing html markup if supported --- .../Streaming/Channels/DirectChannel.cs | 6 +++--- .../Streaming/Channels/HashtagChannel.cs | 4 ++-- .../Streaming/Channels/ListChannel.cs | 8 ++++---- .../Streaming/Channels/PublicChannel.cs | 4 ++-- .../Streaming/Channels/UserChannel.cs | 8 ++++---- .../Mastodon/Streaming/WebSocketConnection.cs | 19 +++++++++++++++++-- 6 files changed, 32 insertions(+), 17 deletions(-) diff --git a/Iceshrimp.Backend/Controllers/Mastodon/Streaming/Channels/DirectChannel.cs b/Iceshrimp.Backend/Controllers/Mastodon/Streaming/Channels/DirectChannel.cs index 42bf3460..ea9c9dab 100644 --- a/Iceshrimp.Backend/Controllers/Mastodon/Streaming/Channels/DirectChannel.cs +++ b/Iceshrimp.Backend/Controllers/Mastodon/Streaming/Channels/DirectChannel.cs @@ -23,7 +23,7 @@ public class DirectChannel(WebSocketConnection connection) : IChannel if (IsSubscribed) return; IsSubscribed = true; - await using var scope = connection.ScopeFactory.CreateAsyncScope(); + await using var scope = connection.GetAsyncServiceScope(); await using var db = scope.ServiceProvider.GetRequiredService(); connection.EventService.NotePublished += OnNotePublished; @@ -106,7 +106,7 @@ public class DirectChannel(WebSocketConnection connection) : IChannel if (connection.IsFiltered(note)) return; if (note.CreatedAt < DateTime.UtcNow - TimeSpan.FromMinutes(5)) return; - await using var scope = connection.ScopeFactory.CreateAsyncScope(); + await using var scope = connection.GetAsyncServiceScope(); if (await connection.IsMutedThreadAsync(note, scope)) return; var message = new StreamingUpdateMessage @@ -132,7 +132,7 @@ public class DirectChannel(WebSocketConnection connection) : IChannel if (wrapped == null) return; if (connection.IsFiltered(note)) return; - await using var scope = connection.ScopeFactory.CreateAsyncScope(); + await using var scope = connection.GetAsyncServiceScope(); var message = new StreamingUpdateMessage { Stream = [Name], diff --git a/Iceshrimp.Backend/Controllers/Mastodon/Streaming/Channels/HashtagChannel.cs b/Iceshrimp.Backend/Controllers/Mastodon/Streaming/Channels/HashtagChannel.cs index 4cde53b9..5993692e 100644 --- a/Iceshrimp.Backend/Controllers/Mastodon/Streaming/Channels/HashtagChannel.cs +++ b/Iceshrimp.Backend/Controllers/Mastodon/Streaming/Channels/HashtagChannel.cs @@ -105,7 +105,7 @@ public class HashtagChannel(WebSocketConnection connection, bool local) : IChann var wrapped = IsApplicable(note); if (wrapped == null) return; if (connection.IsFiltered(note)) return; - await using var scope = connection.ScopeFactory.CreateAsyncScope(); + await using var scope = connection.GetAsyncServiceScope(); if (await connection.IsMutedThreadAsync(note, scope)) return; var renderer = scope.ServiceProvider.GetRequiredService(); @@ -130,7 +130,7 @@ public class HashtagChannel(WebSocketConnection connection, bool local) : IChann var wrapped = IsApplicable(note); if (wrapped == null) return; if (connection.IsFiltered(note)) return; - await using var scope = connection.ScopeFactory.CreateAsyncScope(); + await using var scope = connection.GetAsyncServiceScope(); var renderer = scope.ServiceProvider.GetRequiredService(); var data = new NoteRenderer.NoteRendererDto { Filters = connection.Filters.ToList() }; diff --git a/Iceshrimp.Backend/Controllers/Mastodon/Streaming/Channels/ListChannel.cs b/Iceshrimp.Backend/Controllers/Mastodon/Streaming/Channels/ListChannel.cs index 9bee9145..9b71a614 100644 --- a/Iceshrimp.Backend/Controllers/Mastodon/Streaming/Channels/ListChannel.cs +++ b/Iceshrimp.Backend/Controllers/Mastodon/Streaming/Channels/ListChannel.cs @@ -43,7 +43,7 @@ public class ListChannel(WebSocketConnection connection) : IChannel if (_lists.AddIfMissing(msg.List)) { - await using var scope = connection.ScopeFactory.CreateAsyncScope(); + await using var scope = connection.GetAsyncServiceScope(); var db = scope.ServiceProvider.GetRequiredService(); var list = await db.UserLists.FirstOrDefaultAsync(p => p.UserId == connection.Token.User.Id && @@ -128,7 +128,7 @@ public class ListChannel(WebSocketConnection connection) : IChannel var wrapped = IsApplicable(note); if (wrapped == null) return; if (connection.IsFiltered(note)) return; - await using var scope = connection.ScopeFactory.CreateAsyncScope(); + await using var scope = connection.GetAsyncServiceScope(); if (await connection.IsMutedThreadAsync(note, scope)) return; var renderer = scope.ServiceProvider.GetRequiredService(); @@ -154,7 +154,7 @@ public class ListChannel(WebSocketConnection connection) : IChannel var wrapped = IsApplicable(note); if (wrapped == null) return; if (connection.IsFiltered(note)) return; - await using var scope = connection.ScopeFactory.CreateAsyncScope(); + await using var scope = connection.GetAsyncServiceScope(); var renderer = scope.ServiceProvider.GetRequiredService(); var data = new NoteRenderer.NoteRendererDto { Filters = connection.Filters.ToList() }; @@ -197,7 +197,7 @@ public class ListChannel(WebSocketConnection connection) : IChannel if (list.UserId != connection.Token.User.Id) return; if (!_lists.Contains(list.Id)) return; - await using var scope = connection.ScopeFactory.CreateAsyncScope(); + await using var scope = connection.GetAsyncServiceScope(); var db = scope.ServiceProvider.GetRequiredService(); var members = await db.UserListMembers.Where(p => p.UserListId == list.Id) diff --git a/Iceshrimp.Backend/Controllers/Mastodon/Streaming/Channels/PublicChannel.cs b/Iceshrimp.Backend/Controllers/Mastodon/Streaming/Channels/PublicChannel.cs index d01345b5..3df57d9b 100644 --- a/Iceshrimp.Backend/Controllers/Mastodon/Streaming/Channels/PublicChannel.cs +++ b/Iceshrimp.Backend/Controllers/Mastodon/Streaming/Channels/PublicChannel.cs @@ -88,7 +88,7 @@ public class PublicChannel( var wrapped = IsApplicable(note); if (wrapped == null) return; if (connection.IsFiltered(note)) return; - await using var scope = connection.ScopeFactory.CreateAsyncScope(); + await using var scope = connection.GetAsyncServiceScope(); if (await connection.IsMutedThreadAsync(note, scope)) return; var renderer = scope.ServiceProvider.GetRequiredService(); @@ -116,7 +116,7 @@ public class PublicChannel( var wrapped = IsApplicable(note); if (wrapped == null) return; if (connection.IsFiltered(note)) return; - await using var scope = connection.ScopeFactory.CreateAsyncScope(); + await using var scope = connection.GetAsyncServiceScope(); var renderer = scope.ServiceProvider.GetRequiredService(); var data = new NoteRenderer.NoteRendererDto { Filters = connection.Filters.ToList() }; diff --git a/Iceshrimp.Backend/Controllers/Mastodon/Streaming/Channels/UserChannel.cs b/Iceshrimp.Backend/Controllers/Mastodon/Streaming/Channels/UserChannel.cs index 742347d1..f3849290 100644 --- a/Iceshrimp.Backend/Controllers/Mastodon/Streaming/Channels/UserChannel.cs +++ b/Iceshrimp.Backend/Controllers/Mastodon/Streaming/Channels/UserChannel.cs @@ -22,7 +22,7 @@ public class UserChannel(WebSocketConnection connection, bool notificationsOnly) if (IsSubscribed) return; IsSubscribed = true; - await using var scope = connection.ScopeFactory.CreateAsyncScope(); + await using var scope = connection.GetAsyncServiceScope(); await using var db = scope.ServiceProvider.GetRequiredService(); if (!notificationsOnly) @@ -101,7 +101,7 @@ public class UserChannel(WebSocketConnection connection, bool notificationsOnly) if (wrapped == null) return; if (connection.IsFiltered(note)) return; if (note.CreatedAt < DateTime.UtcNow - TimeSpan.FromMinutes(5)) return; - await using var scope = connection.ScopeFactory.CreateAsyncScope(); + await using var scope = connection.GetAsyncServiceScope(); if (await connection.IsMutedThreadAsync(note, scope)) return; var renderer = scope.ServiceProvider.GetRequiredService(); @@ -128,7 +128,7 @@ public class UserChannel(WebSocketConnection connection, bool notificationsOnly) var wrapped = IsApplicable(note); if (wrapped == null) return; if (connection.IsFiltered(note)) return; - await using var scope = connection.ScopeFactory.CreateAsyncScope(); + await using var scope = connection.GetAsyncServiceScope(); var renderer = scope.ServiceProvider.GetRequiredService(); var intermediate = await renderer.RenderAsync(note, connection.Token.User); @@ -174,7 +174,7 @@ public class UserChannel(WebSocketConnection connection, bool notificationsOnly) if (!IsApplicable(notification)) return; if (IsFiltered(notification)) return; - await using var scope = connection.ScopeFactory.CreateAsyncScope(); + await using var scope = connection.GetAsyncServiceScope(); if (notification.Note != null && await connection.IsMutedThreadAsync(notification.Note, scope, true)) return; diff --git a/Iceshrimp.Backend/Controllers/Mastodon/Streaming/WebSocketConnection.cs b/Iceshrimp.Backend/Controllers/Mastodon/Streaming/WebSocketConnection.cs index e1581270..e2a800d5 100644 --- a/Iceshrimp.Backend/Controllers/Mastodon/Streaming/WebSocketConnection.cs +++ b/Iceshrimp.Backend/Controllers/Mastodon/Streaming/WebSocketConnection.cs @@ -8,6 +8,7 @@ using Iceshrimp.Backend.Core.Database.Tables; using Iceshrimp.Backend.Core.Events; using Iceshrimp.Backend.Core.Extensions; using Iceshrimp.Backend.Core.Helpers; +using Iceshrimp.Backend.Core.Helpers.LibMfm.Conversion; using Iceshrimp.Backend.Core.Services; using JetBrains.Annotations; using Microsoft.EntityFrameworkCore; @@ -32,7 +33,6 @@ public sealed class WebSocketConnection( public readonly WriteLockingList Filters = []; public readonly EventService EventService = eventSvc; public readonly IServiceScope Scope = scopeFactory.CreateScope(); - public readonly IServiceScopeFactory ScopeFactory = scopeFactory; public readonly OauthToken Token = token; public HashSet HiddenFromHome = []; @@ -57,6 +57,8 @@ public sealed class WebSocketConnection( public void InitializeStreamingWorker() { + InitializeScopeLocalParameters(Scope); + _channels.Add(new ListChannel(this)); _channels.Add(new DirectChannel(this)); _channels.Add(new UserChannel(this, true)); @@ -343,7 +345,7 @@ public sealed class WebSocketConnection( if (list.UserId != Token.User.Id) return; if (!list.HideFromHomeTl) return; - await using var scope = ScopeFactory.CreateAsyncScope(); + await using var scope = GetAsyncServiceScope(); var db = scope.ServiceProvider.GetRequiredService(); HiddenFromHome = await db.UserListMembers @@ -383,6 +385,19 @@ public sealed class WebSocketConnection( return await db.NoteThreadMutings.AnyAsync(p => p.UserId == Token.UserId && p.ThreadId == note.ThreadId); } + public AsyncServiceScope GetAsyncServiceScope() + { + var scope = scopeFactory.CreateAsyncScope(); + InitializeScopeLocalParameters(scope); + return scope; + } + + private void InitializeScopeLocalParameters(IServiceScope scope) + { + var mfmConverter = scope.ServiceProvider.GetRequiredService(); + mfmConverter.SupportsHtmlFormatting.Value = Token.SupportsHtmlFormatting; + } + public async Task CloseAsync(WebSocketCloseStatus status) { Dispose();