From 0915e13e8fbecca3d50271489e424d609ac07abe Mon Sep 17 00:00:00 2001 From: Leon <147289645+LeoninCS@users.noreply.github.com> Date: Tue, 16 Dec 2025 14:02:17 +0800 Subject: [PATCH] =?UTF-8?q?feat:=E6=B7=BB=E5=8A=A0=E6=8C=89=E7=85=A7?= =?UTF-8?q?=E7=82=B9=E8=B5=9E=E6=95=B0=E7=9A=84feed=E6=B5=81?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- internal/feed/entity.go | 11 +++++++++++ internal/feed/handler.go | 17 +++++++++++++++++ internal/feed/repo.go | 13 +++++++++++++ internal/feed/service.go | 32 ++++++++++++++++++++++++++++++++ internal/http/router.go | 1 + test/feed.json | 21 +++++++++++++++++++-- 6 files changed, 93 insertions(+), 2 deletions(-) diff --git a/internal/feed/entity.go b/internal/feed/entity.go index 83a258b..35ea613 100644 --- a/internal/feed/entity.go +++ b/internal/feed/entity.go @@ -27,3 +27,14 @@ type ListLatestResponse struct { NextTime int64 `json:"next_time"` HasMore bool `json:"has_more"` } + +type ListLikesCountRequest struct { + Limit int `json:"limit"` + LikesCount int64 `json:"likes_count"` +} + +type ListLikesCountResponse struct { + VideoList []FeedVideoItem `json:"video_list"` + NextLikesCountBefore int64 `json:"next_likes_count_before"` + HasMore bool `json:"has_more"` +} diff --git a/internal/feed/handler.go b/internal/feed/handler.go index 4b51b95..47e2f3f 100644 --- a/internal/feed/handler.go +++ b/internal/feed/handler.go @@ -34,3 +34,20 @@ func (f *FeedHandler) ListLatest(c *gin.Context) { } c.JSON(200, feedItems) } + +func (f *FeedHandler) ListLikesCount(c *gin.Context) { + var req ListLikesCountRequest + if err := c.ShouldBindJSON(&req); err != nil { + c.JSON(400, gin.H{"error": err.Error()}) + return + } + if req.Limit <= 0 || req.Limit > 50 { + req.Limit = 10 + } + feedItems, err := f.service.ListLikesCount(c.Request.Context(), req.Limit, req.LikesCount) + if err != nil { + c.JSON(500, gin.H{"error": err.Error()}) + return + } + c.JSON(200, feedItems) +} diff --git a/internal/feed/repo.go b/internal/feed/repo.go index c27b11b..8ab7544 100644 --- a/internal/feed/repo.go +++ b/internal/feed/repo.go @@ -28,3 +28,16 @@ func (repo *FeedRepository) ListLatest(ctx context.Context, limit int, latestBef } return videos, nil } + +func (repo *FeedRepository) ListLikesCount(ctx context.Context, limit int, likesCountBefore int64) ([]video.Video, error) { + var videos []video.Video + query := repo.db.WithContext(ctx).Model(&video.Video{}). + Order("like_count DESC") + if likesCountBefore > 0 { + query = query.Where("like_count < ?", likesCountBefore) + } + if err := query.Limit(limit).Find(&videos).Error; err != nil { + return nil, err + } + return videos, nil +} diff --git a/internal/feed/service.go b/internal/feed/service.go index 3045c78..6dacb54 100644 --- a/internal/feed/service.go +++ b/internal/feed/service.go @@ -52,3 +52,35 @@ func (f *FeedService) ListLatest(ctx context.Context, limit int, latestBefore ti } return resp, nil } + +func (f *FeedService) ListLikesCount(ctx context.Context, limit int, likesCountBefore int64) (ListLikesCountResponse, error) { + videos, err := f.repo.ListLikesCount(ctx, limit, likesCountBefore) + if err != nil { + return ListLikesCountResponse{}, err + } + var nextLikesCountBefore int64 + if len(videos) > 0 { + nextLikesCountBefore = videos[len(videos)-1].LikesCount + } else { + nextLikesCountBefore = 0 + } + hasMore := len(videos) == limit + feedVideos := make([]FeedVideoItem, 0, len(videos)) + for _, video := range videos { + feedVideos = append(feedVideos, FeedVideoItem{ + ID: video.ID, + Author: FeedAuthor{ID: video.AuthorID, Username: video.Username}, + Title: video.Title, + Description: video.Description, + PlayURL: video.PlayURL, + CoverURL: video.CoverURL, + LikesCount: video.LikesCount, + }) + } + resp := ListLikesCountResponse{ + VideoList: feedVideos, + NextLikesCountBefore: nextLikesCountBefore, + HasMore: hasMore, + } + return resp, nil +} diff --git a/internal/http/router.go b/internal/http/router.go index 8c5d0a4..499b8d3 100644 --- a/internal/http/router.go +++ b/internal/http/router.go @@ -67,6 +67,7 @@ func SetRouter(db *gorm.DB) *gin.Engine { feedGroup := r.Group("/feed") { feedGroup.POST("/listLatest", feedHandler.ListLatest) + feedGroup.POST("/listLikesCount", feedHandler.ListLikesCount) } return r } diff --git a/test/feed.json b/test/feed.json index 797274c..ccbb93e 100644 --- a/test/feed.json +++ b/test/feed.json @@ -2,7 +2,7 @@ "info": { "name": "FeedSystem Feed API", "_postman_id": "4c2fd555-b880-4b14-8023-55a944936352", - "description": "Feed endpoints without embedded scripts.", + "description": "Feed endpoints.\n\nPagination:\n- /feed/listLatest: copy response.next_time into feedLatestTime\n- /feed/listLikesCount: copy response.next_likes_count_before into feedLikesCountBefore", "schema": "https://schema.getpostman.com/json/collection/v2.1.0/collection.json" }, "item": [ @@ -21,11 +21,28 @@ "path": ["feed", "listLatest"] } } + }, + { + "name": "List Feed By Likes Count", + "request": { + "method": "POST", + "header": [{ "key": "Content-Type", "value": "application/json" }], + "body": { + "mode": "raw", + "raw": "{\n \"limit\": {{feedLimit}},\n \"likes_count\": {{feedLikesCountBefore}}\n}" + }, + "url": { + "raw": "{{host}}/feed/listLikesCount", + "host": ["{{host}}"], + "path": ["feed", "listLikesCount"] + } + } } ], "variable": [ { "key": "host", "value": "http://localhost:8080" }, { "key": "feedLimit", "value": "10" }, - { "key": "feedLatestTime", "value": "0" } + { "key": "feedLatestTime", "value": "0" }, + { "key": "feedLikesCountBefore", "value": "0" } ] }