using FreeSql; using LiveForum.Code.Base; using LiveForum.Code.JwtInfrastructure; using LiveForum.IService.Users; using LiveForum.Model; using LiveForum.Model.Dto.UserFollow; using System; using System.Collections.Generic; using System.Linq; using System.Threading.Tasks; namespace LiveForum.Service.Users { public class UserFollowService : IUserFollowService { private readonly JwtUserInfoModel _userInfoModel; private readonly IBaseRepository _followsRepository; private readonly IBaseRepository _usersRepository; /// /// 构造函数 /// /// JWT用户信息模型 /// 关注仓储 /// 用户仓储 public UserFollowService( JwtUserInfoModel userInfoModel, IBaseRepository followsRepository, IBaseRepository usersRepository) { _userInfoModel = userInfoModel; _followsRepository = followsRepository; _usersRepository = usersRepository; } /// /// 关注/取消关注用户 /// /// 请求参数 /// public async Task> FollowUser(FollowUserReq request) { var currentUserId = (long)_userInfoModel.UserId; // 1. 不能关注自己 if (request.UserId == currentUserId) { return new BaseResponse(ResponseCode.Error, "不能关注自己"); } // 2. 检查目标用户是否存在 var targetUser = await _usersRepository.Select .Where(x => x.Id == request.UserId) .FirstAsync(); if (targetUser == null) { return new BaseResponse(ResponseCode.Error, "用户不存在"); } // 3. 查找是否已关注 var existingFollow = await _followsRepository.Select .Where(x => x.FollowerId == currentUserId && x.FollowedUserId == request.UserId) .FirstAsync(); bool isFollowed = false; var followerCount = await _followsRepository.Select .Where(x => x.FollowedUserId == request.UserId) .CountAsync(); if (request.Action == 1) // 关注 { if (existingFollow != null) { return new BaseResponse(ResponseCode.Error, "已关注该用户"); } // 创建关注关系 var follow = new T_Follows { FollowerId = currentUserId, FollowedUserId = request.UserId, CreatedAt = DateTime.Now }; await _followsRepository.InsertAsync(follow); isFollowed = true; followerCount++; } else if (request.Action == 2) // 取消关注 { if (existingFollow == null) { return new BaseResponse(ResponseCode.Error, "未关注该用户"); } // 删除关注关系 await _followsRepository.DeleteAsync(existingFollow); isFollowed = false; followerCount = Math.Max(0, followerCount - 1); } else { return new BaseResponse(ResponseCode.Error, "无效的操作类型"); } // 4. 构建返回数据 var result = new FollowUserRespDto { UserId = request.UserId, IsFollowed = isFollowed, FollowerCount = (int)followerCount }; return new BaseResponse(result); } /// /// 获取关注列表 /// /// 请求参数 /// public async Task> GetUserFollowing(GetUserFollowingReq request) { var currentUserId = (long)_userInfoModel.UserId; // 构建查询条件 - 获取该用户关注的人 var query = _followsRepository.Select .Where(x => x.FollowerId == request.UserId) .OrderByDescending(x => x.CreatedAt); // 获取总数 var total = await query.CountAsync(); // 分页 var follows = await query .Skip((request.PageIndex - 1) * request.PageSize) .Take(request.PageSize) .ToListAsync(); if (!follows.Any()) { return new BaseResponse(new GetUserFollowingRespDto { PageIndex = request.PageIndex, PageSize = request.PageSize, Total = (int)total, TotalPages = (int)Math.Ceiling((double)total / request.PageSize), Items = new List() }); } // 获取被关注的用户ID列表 var followedUserIds = follows.Select(x => x.FollowedUserId).ToList(); // 获取用户信息 var users = await _usersRepository.Select .Where(x => followedUserIds.Contains(x.Id)) .ToListAsync(); // 构建用户ID字典 var userDict = users.ToDictionary(x => x.Id, x => x); // 检查当前用户是否已关注这些用户(互相关注状态) var currentUserFollowedIds = new HashSet(); if (request.UserId != currentUserId) { var myFollows = await _followsRepository.Select .Where(x => x.FollowerId == currentUserId && followedUserIds.Contains(x.FollowedUserId)) .ToListAsync(); foreach (var follow in myFollows) { currentUserFollowedIds.Add(follow.FollowedUserId); } } // 构建返回数据 var items = follows.Select(follow => { var user = userDict.ContainsKey(follow.FollowedUserId) ? userDict[follow.FollowedUserId] : null; if (user == null) { return null; } return new FollowingUserDto { UserId = user.Id, UserName = user.NickName, NickName = user.NickName, Avatar = user.Avatar ?? "", IsVip = user.IsVip, IsCertified = user.IsCertified, Signature = user.Signature ?? "", FollowedAt = follow.CreatedAt, IsFollowed = request.UserId == currentUserId || currentUserFollowedIds.Contains(follow.FollowedUserId) }; }).Where(x => x != null).ToList(); return new BaseResponse(new GetUserFollowingRespDto { PageIndex = request.PageIndex, PageSize = request.PageSize, Total = (int)total, TotalPages = (int)Math.Ceiling((double)total / request.PageSize), Items = items }); } /// /// 获取粉丝列表 /// /// 请求参数 /// public async Task> GetUserFollowers(GetUserFollowersReq request) { var currentUserId = (long)_userInfoModel.UserId; // 构建查询条件 - 获取关注该用户的人 var query = _followsRepository.Select .Where(x => x.FollowedUserId == request.UserId) .OrderByDescending(x => x.CreatedAt); // 获取总数 var total = await query.CountAsync(); // 分页 var follows = await query .Skip((request.PageIndex - 1) * request.PageSize) .Take(request.PageSize) .ToListAsync(); if (!follows.Any()) { return new BaseResponse(new GetUserFollowersRespDto { PageIndex = request.PageIndex, PageSize = request.PageSize, Total = (int)total, TotalPages = (int)Math.Ceiling((double)total / request.PageSize), Items = new List() }); } // 获取粉丝用户ID列表 var followerUserIds = follows.Select(x => x.FollowerId).ToList(); // 获取用户信息 var users = await _usersRepository.Select .Where(x => followerUserIds.Contains(x.Id)) .ToListAsync(); // 构建用户ID字典 var userDict = users.ToDictionary(x => x.Id, x => x); // 检查当前用户是否已关注这些粉丝(互相关注状态) var currentUserFollowedIds = new HashSet(); if (request.UserId != currentUserId) { var myFollows = await _followsRepository.Select .Where(x => x.FollowerId == currentUserId && followerUserIds.Contains(x.FollowedUserId)) .ToListAsync(); foreach (var follow in myFollows) { currentUserFollowedIds.Add(follow.FollowedUserId); } } // 构建返回数据 var items = follows.Select(follow => { var user = userDict.ContainsKey(follow.FollowerId) ? userDict[follow.FollowerId] : null; if (user == null) { return null; } return new FollowerUserDto { UserId = user.Id, UserName = user.NickName, NickName = user.NickName, Avatar = user.Avatar ?? "", IsVip = user.IsVip, IsCertified = user.IsCertified, Signature = user.Signature ?? "", FollowedAt = follow.CreatedAt, IsFollowed = currentUserFollowedIds.Contains(follow.FollowerId) }; }).Where(x => x != null).ToList(); return new BaseResponse(new GetUserFollowersRespDto { PageIndex = request.PageIndex, PageSize = request.PageSize, Total = (int)total, TotalPages = (int)Math.Ceiling((double)total / request.PageSize), Items = items }); } } }