diff --git a/src/modules/nostr-feed/services/FeedService.ts b/src/modules/nostr-feed/services/FeedService.ts index c15bd04..e607cd2 100644 --- a/src/modules/nostr-feed/services/FeedService.ts +++ b/src/modules/nostr-feed/services/FeedService.ts @@ -46,6 +46,7 @@ export class FeedService extends BaseService { protected relayHub: any = null protected visibilityService: any = null + protected reactionService: any = null // Event ID tracking for deduplication private seenEventIds = new Set() @@ -70,9 +71,11 @@ export class FeedService extends BaseService { this.relayHub = injectService(SERVICE_TOKENS.RELAY_HUB) this.visibilityService = injectService(SERVICE_TOKENS.VISIBILITY_SERVICE) + this.reactionService = injectService(SERVICE_TOKENS.REACTION_SERVICE) console.log('FeedService: RelayHub injected:', !!this.relayHub) console.log('FeedService: VisibilityService injected:', !!this.visibilityService) + console.log('FeedService: ReactionService injected:', !!this.reactionService) if (!this.relayHub) { throw new Error('RelayHub service not available') @@ -437,8 +440,6 @@ export class FeedService extends BaseService { currentPost.depth = (parentPost.depth || 0) + 1 parentPost.replies = parentPost.replies || [] parentPost.replies.push(currentPost) - // Sort replies by timestamp (oldest first for better reading flow) - parentPost.replies.sort((a, b) => a.created_at - b.created_at) } else { // Parent not found, treat as root post rootPosts.push(currentPost) @@ -449,12 +450,63 @@ export class FeedService extends BaseService { } }) - // Sort root posts by newest first - rootPosts.sort((a, b) => b.created_at - a.created_at) + // Sort posts using like count and timestamp + this.sortPostsByLikesAndTime(rootPosts) + + // Sort all reply threads recursively + rootPosts.forEach(post => this.sortRepliesRecursively(post)) return rootPosts } + /** + * Sort posts by likes first, then by time (newest first) + */ + private sortPostsByLikesAndTime(posts: FeedPost[]): void { + posts.sort((a, b) => { + // Get like counts from reaction service if available + const aLikes = this.getLikeCount(a.id) + const bLikes = this.getLikeCount(b.id) + + // Sort by likes first (descending) + if (aLikes !== bLikes) { + return bLikes - aLikes + } + + // If likes are equal, sort by time (newest first) + return b.created_at - a.created_at + }) + } + + /** + * Recursively sort replies within each thread + */ + private sortRepliesRecursively(post: FeedPost): void { + if (post.replies && post.replies.length > 0) { + // Sort replies by likes first, then time + this.sortPostsByLikesAndTime(post.replies) + + // Recursively sort nested replies + post.replies.forEach(reply => this.sortRepliesRecursively(reply)) + } + } + + /** + * Get like count for a post from ReactionService + */ + private getLikeCount(postId: string): number { + try { + if (this.reactionService && typeof this.reactionService.getEventReactions === 'function') { + const reactions = this.reactionService.getEventReactions(postId) + return reactions?.likes || 0 + } + } catch (error) { + // Silently fail if reaction service is not available + console.debug('FeedService: Could not get like count for post', postId, error) + } + return 0 + } + /** * Get filtered posts for specific feed type */