From 44f368cda05d6d26a605081230615ed739a7a7e4 Mon Sep 17 00:00:00 2001 From: zerosaturation Date: Mon, 1 Jun 2026 15:08:16 +0800 Subject: [PATCH] =?UTF-8?q?feat:=20=E4=BF=AE=E6=94=B9bug?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../repository/ranking_repository.go | 21 +++++++++++++------ 1 file changed, 15 insertions(+), 6 deletions(-) diff --git a/backend/services/assetService/repository/ranking_repository.go b/backend/services/assetService/repository/ranking_repository.go index b55b89d..ec0a189 100644 --- a/backend/services/assetService/repository/ranking_repository.go +++ b/backend/services/assetService/repository/ranking_repository.go @@ -99,12 +99,13 @@ func (r *rankingRepository) getHotRankingByDimension(starID int64, dimension str now := time.Now().UnixMilli() startOfMonth := time.Date(time.Now().Year(), time.Now().Month(), 1, 0, 0, 0, 0, time.Local).UnixMilli() - // 构建基础查询,JOIN 用户表和粉丝档案表获取昵称和头像 - // 使用 GROUP BY 去重,并用聚合函数获取 owner 信息 - // is_original 是布尔值,需要转为 int 再取 MAX + // 构建基础查询 + // fan_profiles JOIN 条件按维度区分: + // - displaying/month: 使用 exhibitions.occupier_uid(展位占用者必然是当前star的注册粉丝) + // - total: 使用 assets.owner_uid(无展览上下文时的全局拥有者) + // 之所以不能统一用 assets.owner_uid,是因为藏品拥有者不一定是当前star的粉丝。 db := r.db.Model(&models.Asset{}). Select("assets.id as asset_id, assets.name as asset_name, assets.cover_url, assets.owner_uid, MAX(assets.like_count) as like_count, MAX(assets.is_original::int) as is_original, MAX(fp.nickname) as owner_nickname, MAX(fp.avatar_url) as owner_avatar"). - Joins("LEFT JOIN fan_profiles fp ON fp.user_id = assets.owner_uid AND fp.star_id = ?", starID). Where("assets.star_id = ? AND assets.is_active = ? AND assets.status = ?", starID, true, models.AssetStatusActive) if isOriginalOnly { @@ -116,8 +117,10 @@ func (r *rankingRepository) getHotRankingByDimension(starID int64, dimension str case "displaying": // 展示中:关联 Exhibition 表,筛选未过期的、未删除的,且是当前star的展品 // occupier_star_id 表示展品所属的明星 + // 用展品的 occupier(展位占用者)去 JOIN fan_profiles,而不是 assets.owner_uid db = db.Select("assets.id as asset_id, assets.name as asset_name, assets.cover_url, assets.owner_uid, MAX(assets.like_count) as like_count, MAX(assets.is_original::int) as is_original, MAX(fp.nickname) as owner_nickname, MAX(fp.avatar_url) as owner_avatar, MAX(exhibitions.id) as exhibition_id"). Joins("INNER JOIN exhibitions ON exhibitions.asset_id = assets.id AND exhibitions.deleted_at IS NULL"). + Joins("LEFT JOIN fan_profiles fp ON fp.user_id = exhibitions.occupier_uid AND fp.star_id = exhibitions.occupier_star_id"). Where("exhibitions.expire_at > ?", now). Where("exhibitions.occupier_star_id = ?", starID). Group("assets.id, exhibitions.id") @@ -125,19 +128,21 @@ func (r *rankingRepository) getHotRankingByDimension(starID int64, dimension str // 本月:本月内展览过的藏品(包括已下架的,只要 expire_at 在本月内即可) db = db.Select("assets.id as asset_id, assets.name as asset_name, assets.cover_url, assets.owner_uid, MAX(assets.like_count) as like_count, MAX(assets.is_original::int) as is_original, MAX(fp.nickname) as owner_nickname, MAX(fp.avatar_url) as owner_avatar, MAX(exhibitions.id) as exhibition_id"). Joins("INNER JOIN exhibitions ON exhibitions.asset_id = assets.id"). + Joins("LEFT JOIN fan_profiles fp ON fp.user_id = exhibitions.occupier_uid AND fp.star_id = exhibitions.occupier_star_id"). Where("exhibitions.expire_at >= ?", startOfMonth). Where("exhibitions.occupier_star_id = ?", starID). Group("assets.id, exhibitions.id") case "total": // 全部:直接使用 assets 表的 like_count,无需额外条件 - db = db.Select("assets.id as asset_id, assets.name as asset_name, assets.cover_url, assets.owner_uid, MAX(assets.like_count) as like_count, MAX(assets.is_original::int) as is_original, MAX(fp.nickname) as owner_nickname, MAX(fp.avatar_url) as owner_avatar, 0 as exhibition_id") + // fan_profiles JOIN 使用藏品的拥有者(无展览上下文) + db = db.Select("assets.id as asset_id, assets.name as asset_name, assets.cover_url, assets.owner_uid, MAX(assets.like_count) as like_count, MAX(assets.is_original::int) as is_original, MAX(fp.nickname) as owner_nickname, MAX(fp.avatar_url) as owner_avatar, 0 as exhibition_id"). + Joins("LEFT JOIN fan_profiles fp ON fp.user_id = assets.owner_uid AND fp.star_id = ?", starID) } // 统计总数(先查询 ID 列表再 Count,避免 DISTINCT 干扰) var total int64 countDB := r.db.Model(&models.Asset{}). Select("assets.id"). - Joins("LEFT JOIN fan_profiles fp ON fp.user_id = assets.owner_uid AND fp.star_id = ?", starID). Where("assets.star_id = ? AND assets.is_active = ? AND assets.status = ?", starID, true, models.AssetStatusActive) if isOriginalOnly { countDB = countDB.Where("assets.is_original = ?", true) @@ -145,13 +150,17 @@ func (r *rankingRepository) getHotRankingByDimension(starID int64, dimension str switch dimension { case "displaying": countDB = countDB.Joins("INNER JOIN exhibitions ON exhibitions.asset_id = assets.id AND exhibitions.deleted_at IS NULL"). + Joins("LEFT JOIN fan_profiles fp ON fp.user_id = exhibitions.occupier_uid AND fp.star_id = exhibitions.occupier_star_id"). Where("exhibitions.expire_at > ?", now). Where("exhibitions.occupier_star_id = ?", starID) case "month": // 本月:本月内展览过的藏品(包括已下架的) countDB = countDB.Joins("INNER JOIN exhibitions ON exhibitions.asset_id = assets.id"). + Joins("LEFT JOIN fan_profiles fp ON fp.user_id = exhibitions.occupier_uid AND fp.star_id = exhibitions.occupier_star_id"). Where("exhibitions.expire_at >= ?", startOfMonth). Where("exhibitions.occupier_star_id = ?", starID) + case "total": + countDB = countDB.Joins("LEFT JOIN fan_profiles fp ON fp.user_id = assets.owner_uid AND fp.star_id = ?", starID) } if err := countDB.Count(&total).Error; err != nil { return nil, 0, err