Compare commits
	
		
			2 Commits
		
	
	
		
			89406870bd
			...
			b3ed98322b
		
	
	| Author | SHA1 | Date | |
|---|---|---|---|
| b3ed98322b | |||
| 4cfd4387b6 | 
| @@ -47,6 +47,7 @@ public class Post : ModelBase, IIdentifiedResource, IActivity | ||||
|     public int Downvotes { get; set; } | ||||
|     [NotMapped] public Dictionary<string, int> ReactionsCount { get; set; } = new(); | ||||
|     [NotMapped] public int RepliesCount { get; set; } | ||||
|     [NotMapped] public Dictionary<string, bool>? ReactionsMade { get; set; } | ||||
|  | ||||
|     public Guid? RepliedPostId { get; set; } | ||||
|     public Post? RepliedPost { get; set; } | ||||
|   | ||||
| @@ -151,6 +151,30 @@ public class PostController( | ||||
|         return Ok(posts); | ||||
|     } | ||||
|  | ||||
|     [HttpGet("{id:guid}/reactions")] | ||||
|     public async Task<ActionResult<List<PostReaction>>> GetReactions( | ||||
|         Guid id, | ||||
|         [FromQuery] string? symbol = null, | ||||
|         [FromQuery] int offset = 0, | ||||
|         [FromQuery] int take = 20 | ||||
|     ) | ||||
|     { | ||||
|         var query = db.PostReactions | ||||
|             .Where(e => e.PostId == id); | ||||
|         if (symbol is not null) query = query.Where(e => e.Symbol == symbol); | ||||
|          | ||||
|         var totalCount = await query.CountAsync(); | ||||
|         Response.Headers.Append("X-Total", totalCount.ToString()); | ||||
|          | ||||
|         var reactions = await query | ||||
|             .OrderBy(r => r.Symbol) | ||||
|             .ThenByDescending(r => r.CreatedAt) | ||||
|             .Take(take) | ||||
|             .Skip(offset) | ||||
|             .ToListAsync(); | ||||
|         return Ok(reactions); | ||||
|     } | ||||
|  | ||||
|     [HttpGet("{id:guid}/replies/featured")] | ||||
|     public async Task<ActionResult<Post>> GetFeaturedReply(Guid id) | ||||
|     { | ||||
| @@ -165,7 +189,7 @@ public class PostController( | ||||
|         } | ||||
|  | ||||
|         var userPublishers = currentUser is null ? [] : await pub.GetUserPublishers(Guid.Parse(currentUser.Id)); | ||||
|          | ||||
|  | ||||
|         var now = SystemClock.Instance.GetCurrentInstant(); | ||||
|         var post = await db.Posts | ||||
|             .Where(e => e.RepliedPostId == id) | ||||
| @@ -181,7 +205,7 @@ public class PostController( | ||||
|  | ||||
|         // Track view - use the account ID as viewer ID if user is logged in | ||||
|         await ps.IncreaseViewCount(post.Id, currentUser?.Id); | ||||
|          | ||||
|  | ||||
|         return await ps.LoadPostInfo(post); | ||||
|     } | ||||
|  | ||||
|   | ||||
| @@ -182,7 +182,8 @@ public partial class PostService( | ||||
|                                     Title = localizer["PostReplyTitle", sender.Nick], | ||||
|                                     Body = string.IsNullOrWhiteSpace(post.Title) | ||||
|                                         ? localizer["PostReplyBody", sender.Nick, ChopPostForNotification(post).content] | ||||
|                                         : localizer["PostReplyContentBody", sender.Nick, post.Title, ChopPostForNotification(post).content], | ||||
|                                         : localizer["PostReplyContentBody", sender.Nick, post.Title, | ||||
|                                             ChopPostForNotification(post).content], | ||||
|                                     IsSavable = true, | ||||
|                                     ActionUri = $"/posts/{post.Id}" | ||||
|                                 } | ||||
| @@ -519,6 +520,24 @@ public partial class PostService( | ||||
|             ); | ||||
|     } | ||||
|  | ||||
|     public async Task<Dictionary<Guid, Dictionary<string, bool>>> GetPostReactionMadeMapBatch(List<Guid> postIds, Guid accountId) | ||||
|     { | ||||
|         var reactions = await db.Set<PostReaction>() | ||||
|             .Where(r => postIds.Contains(r.PostId) && r.AccountId == accountId) | ||||
|             .Select(r => new { r.PostId, r.Symbol }) | ||||
|             .ToListAsync(); | ||||
|  | ||||
|         return postIds.ToDictionary( | ||||
|             postId => postId, | ||||
|             postId => reactions | ||||
|                 .Where(r => r.PostId == postId) | ||||
|                 .ToDictionary( | ||||
|                     r => r.Symbol, | ||||
|                     _ => true | ||||
|                 ) | ||||
|         ); | ||||
|     } | ||||
|  | ||||
|     /// <summary> | ||||
|     /// Increases the view count for a post. | ||||
|     /// Uses the flush buffer service to batch database updates for better performance. | ||||
| @@ -595,20 +614,28 @@ public partial class PostService( | ||||
|         var postsId = posts.Select(e => e.Id).ToList(); | ||||
|  | ||||
|         var reactionMaps = await GetPostReactionMapBatch(postsId); | ||||
|         var reactionMadeMap = currentUser is not null | ||||
|             ? await GetPostReactionMadeMapBatch(postsId, Guid.Parse(currentUser.Id)) | ||||
|             : new Dictionary<Guid, Dictionary<string, bool>>(); | ||||
|         var repliesCountMap = await GetPostRepliesCountBatch(postsId); | ||||
|  | ||||
|         foreach (var post in posts) | ||||
|         { | ||||
|             // Set reactions count | ||||
|             // Set reaction count | ||||
|             post.ReactionsCount = reactionMaps.TryGetValue(post.Id, out var count) | ||||
|                 ? count | ||||
|                 : new Dictionary<string, int>(); | ||||
|  | ||||
|             // Set replies count | ||||
|             // Set reaction made status | ||||
|             post.ReactionsMade = reactionMadeMap.TryGetValue(post.Id, out var made) | ||||
|                 ? made | ||||
|                 : []; | ||||
|              | ||||
|             // Set reply count | ||||
|             post.RepliesCount = repliesCountMap.TryGetValue(post.Id, out var repliesCount) | ||||
|                 ? repliesCount | ||||
|                 : 0; | ||||
|  | ||||
|              | ||||
|             // Track view for each post in the list | ||||
|             if (currentUser != null) | ||||
|                 await IncreaseViewCount(post.Id, currentUser.Id); | ||||
| @@ -688,4 +715,4 @@ public static class PostQueryExtensions | ||||
|                         (e.Publisher.AccountId != null && userFriends.Contains(e.Publisher.AccountId.Value)) || | ||||
|                         publishersId.Contains(e.PublisherId)); | ||||
|     } | ||||
| } | ||||
| } | ||||
		Reference in New Issue
	
	Block a user