using AutoMapper; using Microsoft.EntityFrameworkCore; using Microsoft.IdentityModel.Tokens; using Newtonsoft.Json; using Newtonsoft.Json.Linq; using System.Collections; using System.Collections.Generic; using System.Globalization; using System.Text.RegularExpressions; using VOL.Entity.DomainModels; using YD_WeChatApplet.Api.Entitys; using YD_WeChatApplet.Api.SmartSportsEntitys; using YD_WeChatApplet.Api.Utilities; using YD_WeChatApplet.Commons.Dto; using YD_WeChatApplet.Commons.Dto.ClientSide; using YD_WeChatApplet.Commons.Dto.HomeWork; using YD_WeChatApplet.Commons.Dto.Patriarch; using YD_WeChatApplet.Commons.Dto.Resource; using YD_WeChatApplet.Commons.Dto.School; using YD_WeChatApplet.Commons.Dto.SportsTest; using YD_WeChatApplet.Commons.Dto.Teacher; using YD_WeChatApplet.Commons.Enum; using YD_WeChatApplet.Commons.Utils; using YD_WeChatApplet.Context; using YD_WeChatApplet.Services; using static Microsoft.EntityFrameworkCore.DbLoggerCategory; namespace YD_WeChatApplet.Api.Services.Impl { /// /// 用户端 /// public class ClientSideService : IClientSideService { public UserContext _userContext; public SmartSportsContext _sportsContext; private readonly IMapper _mapper; public ClientSideService(UserContext userContext, SmartSportsContext sportsContext, IMapper mapper) { _userContext = userContext; _sportsContext = sportsContext; _mapper = mapper; } /// /// 获取场馆列表 /// /// /// /// public async Task> StadiumList(GetStadiumListDto dto) { //double centerLat = dto.Latitude; //double centerLng = dto.Longitude; //double radiusInKm = 10.0; var query = _sportsContext.Stadium; //.Where(x => // 6371 * 2 * Math.Asin(Math.Sqrt( // Math.Pow(Math.Sin((x.Latitude - centerLat) * Math.PI / 180 / 2), 2) + // Math.Cos(centerLat * Math.PI / 180) * // Math.Cos(x.Latitude * Math.PI / 180) * // Math.Pow(Math.Sin((x.Longitude - centerLng) * Math.PI / 180 / 2), 2) // )) <= radiusInKm //); var totalCount = await query.CountAsync(); var list = await query .Select(x => new StadiumListDto { Id = x.Id, StadiumName = x.StadiumName, Address = x.Address, CoverImage = x.StadiumResourceList.Select(x => x.Url).FirstOrDefault(), Latitude = x.Latitude, Longitude = x.Longitude }) .Skip((dto.PageIndex - 1) * dto.PageSize) .Take(dto.PageSize) .ToListAsync(); return new PageDataDto { Total = totalCount, Datas = list }; } /// /// 场馆详情 /// /// /// public async Task StadiumDetails(int stadiumId) { var res = await _sportsContext.Stadium.Where(x => x.Id == stadiumId).Select(x => new StadiumDetailsDto() { Id = x.Id, StadiumName = x.StadiumName, Address = x.Address, CoverImage = x.CoverImage, Intro = x.Intro, Latitude = x.Latitude, Longitude = x.Longitude, PhoneNo = x.PhoneNo, StadiumResourceList = x.StadiumResourceList.Select(x => new StadiumResourceDto() { Id = x.Id, Type = x.Type, Url = x.Url }).ToList() }).FirstOrDefaultAsync(); return res; } /// /// 教学类别 /// /// public async Task> CurricularTaxonomyList() { var res = await _sportsContext.CurricularTaxonomy.Select(x => new ComboBoxDto() { Id = x.Id, Name = x.TaxonomyName }).ToListAsync(); return res; } /// /// 教学列表 /// /// /// public async Task> CurricularList(CurricularDto dto) { var query = _sportsContext.Curricular; var totalCount = await query.CountAsync(); var list = await query .Select(x => new CurricularListDto() { Id = x.Id, TaxonomyId = x.TaxonomyId, CurricularName = x.CurricularName, CoverImage = x.CoverImage, Hits = x.Hits, Url = x.Url }).Where(x => x.TaxonomyId == dto.TaxonomyId) .Skip((dto.PageIndex - 1) * dto.PageSize) .Take(dto.PageSize) .ToListAsync(); return new PageDataDto { Total = totalCount, Datas = list }; } /// /// 热门视频 /// /// public async Task> PopularCurricularList() { var res = await _sportsContext.PopularCurricular .Join(_sportsContext.Curricular, a => a.CurricularId, s => s.Id, (a, s) => new CurricularListDto() { Id = a.Id, CurricularName = s.CurricularName, CoverImage = s.CoverImage, Url = s.Url, Hits = s.Hits }).ToListAsync(); return res; } /// /// 视频播放 /// /// /// public async Task VideoPlay(int curricularId) { var entity = await _sportsContext.Curricular.Where(x => x.Id == curricularId).FirstAsync(); entity.Hits = entity.Hits + 1; _sportsContext.Curricular.Update(entity); await _sportsContext.SaveChangesAsync(); } /// /// 场馆预约 /// /// /// public async Task StadiumVisiting(int stadiumId) { if (stadiumId == 0) throw new Exception("场馆信息有误"); var userId = UserLoginContext.Current.UserId; var user = await _userContext.Users.FirstAsync(x => x.User_Id == userId); var stadiumVisiting = await _sportsContext.StadiumVisiting.FirstOrDefaultAsync(x => x.PhoneNo == user.PhoneNo && x.StadiumId == stadiumId); if (stadiumVisiting == null) { var entity = new Y_StadiumVisiting() { StadiumId = stadiumId, Status = 1, PhoneNo = user.PhoneNo, UserName = user.UserTrueName, VisitingTime = DateTime.Now }; await _sportsContext.StadiumVisiting.AddAsync(entity); await _sportsContext.SaveChangesAsync(); } } /// /// 各项目排行 /// /// /// public async Task> Ranking(int categoryId) { var res = await _userContext.ExerciseData .Where(x => x.WorkType == categoryId) .GroupBy(x => x.UserId) .Select(g => new RankingDto() { UserId = g.Key, UserName = g.FirstOrDefault().UserName, Value = g.Sum(x => x.Amount ?? 0) }) .OrderByDescending(x => x.Value) .ToListAsync(); return res; } /// /// 文章列表 /// /// /// public async Task> Articles(PageDto dto) { //try //{ // // 获取 access_token // var accessToken = await GetAccessTokenAsync(); // int offset = dto.PageIndex - 1 == 0 ? 0 : (dto.PageIndex - 1) * dto.PageSize - 1; // // 获取文章列表 // var articles = await GetArticlesAsync(accessToken, offset, dto.PageSize); // // 返回文章列表数据 // return new { articles }; //} //catch (Exception ex) //{ // return new { message = "Error retrieving articles", error = ex.Message }; //} var res = new PageDataDto(); res.Total = await _sportsContext.Article.CountAsync(); var data = await _sportsContext.Article.Select(x => new ArticlesDto() { Id = x.Id, Abstract = x.Abstract, ArticleUrl = x.ArticleUrl, CoverImage = x.CoverImage, Title = x.Title, UpdateDate = x.UpdateDate }) .OrderByDescending(x => x.UpdateDate) .Skip((dto.PageIndex - 1) * dto.PageSize) .Take(dto.PageSize) .ToListAsync(); res.Datas = data; return res; } /// /// 创建群组 /// /// /// public async Task CreateUserGruop(CreateUserGruopDto dto) { using var transaction = await _userContext.Database.BeginTransactionAsync(); try { var userId = UserLoginContext.Current.UserId; var entity = new WCA_UserGroup() { GroupName = dto.GroupName, UserId = userId, CreaterId = userId, CreateTime = DateTime.Now }; await _userContext.UserGroup.AddAsync(entity); await _userContext.SaveChangesAsync(); //var user = await _userContext.Users.FirstAsync(x => x.User_Id == userId); var member = new WCA_GroupMembers() { UserId = userId, //HeadImageUrl = user.HeadImageUrl, //NickName = user.UserTrueName ?? "", UserGroupId = entity.Id, //PhoneNo = user.PhoneNo, CreateTime = DateTime.Now, }; await _userContext.GroupMembers.AddAsync(member); await _userContext.SaveChangesAsync(); await transaction.CommitAsync(); } catch { await transaction.RollbackAsync(); throw; } } /// /// 获取群组列表 /// /// /// public async Task> GetUserGruop(GetUserGruopDto dto) { var userId = UserLoginContext.Current.UserId; var res = new PageDataDto(); IQueryable query; if (dto.IsCreated) { // 查询我创建的群组 query = _userContext.UserGroup.Where(x => x.UserId == userId); } else { // 1. 先查询我加入的所有群组ID var joinedGroupIds = await _userContext.GroupMembers .Where(x => x.UserId == userId) .Select(x => x.UserGroupId) .ToListAsync(); if (!joinedGroupIds.Any()) return new PageDataDto(); // 2. 再查询我创建的群组ID var createdGroupIds = await _userContext.UserGroup .Where(x => x.UserId == userId) .Select(x => x.Id) .ToListAsync(); // 3. 使用Except排除我创建的群组 var filteredGroupIds = joinedGroupIds.Except(createdGroupIds).ToList(); if (!filteredGroupIds.Any()) return new PageDataDto(); // 4. 最终查询:我加入但不是我创建的群组 query = _userContext.UserGroup.Where(x => filteredGroupIds.Contains(x.Id)); } // 分页逻辑保持不变 res.Total = await query.CountAsync(); res.Datas = await query .Select(x => new UserGruopDto { GroupId = x.Id, GroupName = x.GroupName, MemberCount = _userContext.GroupMembers.Count(gm => gm.UserGroupId == x.Id) }) .OrderByDescending(x => x.GroupId) .Skip((dto.PageIndex - 1) * dto.PageSize) .Take(dto.PageSize) .ToListAsync(); return res; } /// /// 是否再群组中 /// /// /// public async Task IsInGroup(int groupId) { var userId = UserLoginContext.Current.UserId; var any = await _userContext.GroupMembers.AnyAsync(x => x.UserId == userId && x.UserGroupId == groupId); return any; } /// /// 加入群组 /// /// /// public async Task JoinGroup(int groupId) { var userId = UserLoginContext.Current.UserId; var any = await _userContext.GroupMembers.AnyAsync(x => x.UserId == userId && x.UserGroupId == groupId); if (any) { return; } if (groupId == 0) throw new Exception("未找到组Id"); //var user = await _userContext.Users.FirstAsync(x => x.User_Id == userId); var entity = new WCA_GroupMembers() { UserId = userId, //HeadImageUrl = user.HeadImageUrl, //NickName = user.UserTrueName ?? "", UserGroupId = groupId, //PhoneNo = user.PhoneNo, CreateTime = DateTime.Now, }; await _userContext.GroupMembers.AddAsync(entity); await _userContext.SaveChangesAsync(); } /// /// 群成员列表 /// /// /// public async Task> GetMembers(GetMembersDto dto) { var res = new PageDataDto(); var nowTime = DateTime.Now; var group = await _userContext.UserGroup.FirstAsync(gm => gm.Id == dto.GroupId); var query = _userContext.GroupMembers.Join(_userContext.Users, x => x.UserId, u => u.User_Id, (x, u) => new MembersDto { GroupName = group.GroupName, UserId = x.UserId, UserGroupId = x.UserGroupId, HeadImageUrl = u.HeadImageUrl, NickName = u.UserTrueName, PhoneNo = u.PhoneNo, CreateTime = x.CreateTime }).Where(x => x.UserGroupId == dto.GroupId); res.Total = await query.CountAsync(); res.Datas = await query .OrderByDescending(x => x.CreateTime) .Skip((dto.PageIndex - 1) * dto.PageSize) .Take(dto.PageSize) .ToListAsync(); return res; } /// /// 创建群组任务 /// /// /// public async Task CreateGroupTask(CreateGroupTaskDto dto) { List taskEntities = new List(); DateTime startDate = dto.StartTime; DateTime endDate = dto.EndTime; var weekList = dto.WeekList; if (dto.IsRepeat) { for (var currentDate = startDate; currentDate <= endDate; currentDate = currentDate.AddDays(1)) { if (weekList.Contains(((int)currentDate.DayOfWeek == 0 ? 7 : (int)currentDate.DayOfWeek))) { var taskEntity = _mapper.Map(dto); taskEntity.CreateTime = DateTime.Now; taskEntity.WorkText = ""; taskEntity.CreateTime = DateTime.Now; taskEntity.StartTime = currentDate.Date; taskEntity.RepetitionPeriod = string.Join(',', weekList); taskEntity.EndTime = currentDate.Date.AddDays(1).AddSeconds(-1); taskEntities.Add(taskEntity); } } } else { var taskEntity = _mapper.Map(dto); taskEntity.CreateTime = DateTime.Now; taskEntity.WorkText = ""; taskEntity.StartTime = startDate; taskEntity.RepetitionPeriod = "1"; taskEntity.EndTime = endDate; taskEntities.Add(taskEntity); } await _userContext.GroupTask.AddRangeAsync(taskEntities); await _userContext.SaveChangesAsync(); } /// /// 删除群组任务 /// /// /// public async Task DeleteGroupTask(int groupTaskId) { var nowTime = DateTime.Now; var model = await _userContext.GroupTask.Where(x => x.Id == groupTaskId).FirstOrDefaultAsync(); if (model == null) throw new Exception("未找到符合条件的群任务!"); _userContext.GroupTask.Remove(model); await _userContext.SaveChangesAsync(); } /// /// 获取群任务列表 /// /// /// public async Task> GetGroupTasks(GetGroupTaskDto dto) { var res = new PageDataDto(); var nowTime = DateTime.Now; var query = _userContext.GroupTask.Where(x => x.UserGroupId == dto.GroupId) .Select(x => new GroupTaskDto { Id = x.Id, Amount = x.Amount, Duration = x.Duration, StartTime = x.StartTime, EndTime = x.EndTime, GroupTaskName = x.GroupTaskName, IsRepeat = x.IsRepeat, RepetitionPeriod = x.RepetitionPeriod, WorkModeType = x.WorkModeType, WorkModeTypeName = x.WorkModeTypeName, Status = dto.Status }); switch (dto.Status) { case 1: query = query.Where(x => x.StartTime < nowTime && x.EndTime > nowTime); break; case 2: query = query.Where(x => x.StartTime > nowTime); break; case 3: query = query.Where(x => x.EndTime < nowTime); break; } res.Total = await query.CountAsync(); res.Datas = await query .OrderByDescending(x => x.Id) .Skip((dto.PageIndex - 1) * dto.PageSize) .Take(dto.PageSize) .ToListAsync(); return res; } /// /// 获取群任务详情 /// /// /// public async Task GetGroupTaskDetails(int groupTaskId) { var res = _userContext.GroupTask.Where(x => x.Id == groupTaskId).Select(x => new GroupTaskDetailsDto() { Id = x.Id, Amount = x.Amount, CreateTime = x.CreateTime, Duration = x.Duration, EndTime = x.EndTime, GroupNumber = x.GroupNumber, GroupTaskName = x.GroupTaskName, IsRepeat = x.IsRepeat, RepetitionPeriod = x.RepetitionPeriod, StartTime = x.StartTime, WorkModeType = x.WorkModeType, WorkModeTypeName = x.WorkModeTypeName, WorkText = x.WorkText, WorkTypeName = x.WorkTypeName }).FirstOrDefault(); return res; } /// /// 添加团队运动成绩 /// /// /// public async Task AddGroupTaskResult(AddGroupTaskResultDto dto) { var userId = UserLoginContext.Current.UserId; var user = await _userContext.Users.Where(x => x.User_Id == userId).Select(x => new { x.User_Id, x.UserTrueName, x.HeadImageUrl }).FirstAsync(); if (dto.WorkModeType == WorkModeType.CountTimer || dto.WorkModeType == WorkModeType.TimerCount) { var entity = new WCA_GroupTaskResult() { UserId = userId, DataSource = dto.DataSource, Amount = dto.Amount, Duration = dto.Duration, GroupTaskId = dto.GroupTaskId, WorkModeType = dto.WorkModeType, WorkModeTypeName = dto.WorkModeTypeName, //NickName = user.UserTrueName, //HeadImageUrl = user.HeadImageUrl, CreateTime = DateTime.Now }; await _userContext.AddAsync(entity); await _userContext.SaveChangesAsync(); return new TaskResultDto() { TaskResultId = entity.Id }; } else { var taskResult = await _userContext.GroupTaskResult.Where(x => x.UserId == userId && x.GroupTaskId == dto.GroupTaskId).FirstOrDefaultAsync(); if (taskResult == null) { var entity = new WCA_GroupTaskResult() { UserId = userId, Amount = dto.Amount, Duration = dto.Duration, GroupTaskId = dto.GroupTaskId, WorkModeType = dto.WorkModeType, WorkModeTypeName = dto.WorkModeTypeName, CreateTime = DateTime.Now }; await _userContext.AddAsync(entity); await _userContext.SaveChangesAsync(); return new TaskResultDto() { TaskResultId = entity.Id }; } else { taskResult.Duration += dto.Duration; taskResult.Amount += dto.Amount; _userContext.GroupTaskResult.Update(taskResult); await _userContext.SaveChangesAsync(); return new TaskResultDto() { TaskResultId = taskResult.Id }; } } } /// /// 获取成绩列表 /// /// /// public async Task GetGroupTaskResult(GetGroupTaskResultDto dto) { var userId = UserLoginContext.Current.UserId; var res = new GroupTaskResultDto(); // 获取组任务基本信息 var groupTask = await _userContext.GroupTask .Where(x => x.Id == dto.GroupTaskId) .Select(x => new { x.WorkModeType, x.Amount, x.Duration }) .FirstAsync(); res.TeamGoal = groupTask.WorkModeType == WorkModeType.TimerCount || groupTask.WorkModeType == WorkModeType.GroupCount ? groupTask.Amount : groupTask.Duration; // 获取结果列表 var resultList = await _userContext.GroupTaskResult .Where(x => x.GroupTaskId == dto.GroupTaskId) .Join(_userContext.Users, x => x.UserId, u => u.User_Id, (x, u) => new TaskResultListDto { UserId = x.UserId, HeadImageUrl = u.HeadImageUrl, NickName = u.UserTrueName, Amount = x.Amount, Duration = x.Duration }) .ToListAsync(); if (!resultList.Any()) { return res; } // 根据工作模式排序并计算排名 var isAmountBased = groupTask.WorkModeType == WorkModeType.TimerCount || groupTask.WorkModeType == WorkModeType.GroupCount; var sortedQuery = isAmountBased ? resultList.OrderByDescending(x => x.Amount).ToList() : resultList.OrderByDescending(x => x.Duration).ToList(); // 分配排名 for (int i = 0; i < sortedQuery.Count; i++) { sortedQuery[i].Ranking = i + 1; } // 设置用户特定信息 var userResult = sortedQuery.FirstOrDefault(x => x.UserId == userId); res.CurrentRanking = sortedQuery .FindIndex(x => x.UserId == userId) + 1; res.NickName = userResult?.NickName ?? ""; res.HeadImageUrl = userResult?.HeadImageUrl ?? ""; // 计算完成度和贡献值 res.Complete = isAmountBased ? sortedQuery.Sum(x => x.Amount) : sortedQuery.Sum(x => x.Duration); res.Contribute = isAmountBased ? userResult?.Amount ?? 0 : userResult?.Duration ?? 0; res.TaskResults = sortedQuery; return res; } /// /// 统计汇总 /// /// /// public async Task AggregateStatistics(GetAggregateStatisticsDto dto) { var userId = UserLoginContext.Current.UserId; var res = new AggregateStatisticsDto(); var groupResults = await _userContext.GroupTaskResult.Where(x => x.UserId == userId).Select(x => new { x.Duration, x.Amount, x.CreateTime }).ToListAsync(); var personalResults = await _userContext.PersonalGoalResult.Where(x => x.UserId == userId).Select(x => new { x.Duration, x.Amount, x.CreateTime }).ToListAsync(); var results = groupResults.Concat(personalResults); res.AccumulatedDuration = results.Sum(x => x.Duration); res.AccumulatedCount = results.Sum(x => x.Amount); res.AccumulatedConsume = res.AccumulatedCount / 10; // 根据周期类型确定时间范围 var now = DateTime.Now; var culture = CultureInfo.CurrentCulture; DateTime startDate; // 结束时间设为明天零点 DateTime endDate = now.Date.AddDays(1); switch (dto.CycleType) { case CycleType.Day: // 日 startDate = now.Date; break; case CycleType.Week: // 周 startDate = now.Date.AddDays(-(int)now.DayOfWeek + 1); // 本周一(调整为周一到周日) break; case CycleType.Month: // 月 startDate = new DateTime(now.Year, now.Month, 1); break; case CycleType.Year: // 年 startDate = new DateTime(now.Year, 1, 1); break; default: startDate = DateTime.MinValue; break; } results = results.Where(x => x.CreateTime >= startDate && x.CreateTime <= endDate).ToList(); // 根据周期类型进行分组并优化显示格式 var groupedData = dto.CycleType switch { // 日:按小时分组 (0-23),格式:2024-03-16/1 CycleType.Day => results.GroupBy(x => x.CreateTime.Hour) .OrderBy(g => g.Key) .Select(g => new { //TimePeriod = $"{now:yyyy-MM-dd}/{g.Key}", TimePeriod = $"{g.Key}:00", Count = g.Sum(x => x.Amount), Duration = g.Sum(x => x.Duration), }).ToList(), // 周:按星期几分组 (1-7 对应周一到周日),显示本地化星期名称 CycleType.Week => Enumerable.Range(1, 7) // 确保显示完整的周一到周日 .Select(day => new { DayOfWeek = day, DayName = culture.DateTimeFormat.GetDayName((DayOfWeek)(day % 7)), Data = results.Where(x => (int)x.CreateTime.DayOfWeek == day % 7) }) .Select(g => new { TimePeriod = g.DayName, Count = g.Data.Sum(x => x.Amount), Duration = g.Data.Sum(x => x.Duration), }).ToList(), // 月:按日分组,格式:2025-03-06 CycleType.Month => results.GroupBy(x => x.CreateTime.Day) .OrderBy(g => g.Key) .Select(g => new { TimePeriod = $"{now:yyyy-MM}-{g.Key:D2}", Count = g.Sum(x => x.Amount), Duration = g.Sum(x => x.Duration), }).ToList(), // 年:按月分组,显示本地化月份名称(一月、二月...) CycleType.Year => Enumerable.Range(1, 12) // 确保显示完整的12个月 .Select(month => new { Month = month, MonthName = culture.DateTimeFormat.GetMonthName(month), Data = results.Where(x => x.CreateTime.Month == month) }) .Select(g => new { TimePeriod = g.MonthName, Count = g.Data.Sum(x => x.Amount), Duration = g.Data.Sum(x => x.Duration), }).ToList() }; res.ChartDataByCount = new ChartDataDto { AxisX = groupedData.Select(x => x.TimePeriod).ToList(), AxisY = groupedData.Select(x => x.Count).ToList() }; res.ChartDataByDuration = new ChartDataDto { AxisX = groupedData.Select(x => x.TimePeriod).ToList(), AxisY = groupedData.Select(x => x.Duration).ToList() }; res.ChartDataByConsume = new ChartDataDto { AxisX = groupedData.Select(x => x.TimePeriod).ToList(), AxisY = groupedData.Select(x => x.Count / 10).ToList() }; res.TotalCount = results.Sum(x => x.Amount); res.BestResult = results.Select(x => x.Amount).DefaultIfEmpty(0).Max(); return res; } /// /// 运动记录 /// /// /// public async Task> SportsRecord(PageDto dto) { var userId = UserLoginContext.Current.UserId; //var groupList = await _userContext.GroupTaskResult // .Join(_userContext.GroupTask, r => r.GroupTaskId, t => t.Id, (r, t) => new SportsRecordDto // { // UserId = r.UserId, // Count = r.Amount, // CreateTime = r.CreateTime, // Duration = r.Duration, // Consume = r.Amount / 10, // GroupTaskName = t.GroupTaskName, // }) // .Where(x => x.UserId == userId).ToListAsync(); var groupQueryss = await _userContext.GroupTaskResult.Where(x => x.UserId == userId).Select(x => new SportsRecordDto { UserId = x.UserId, Count = x.Amount, CreateTime = x.CreateTime, Duration = x.Duration, Consume = x.Amount / 10, GroupTaskName = "团队训练" }).ToListAsync(); var personalQuerysss = await _userContext.PersonalGoalResult.Where(x => x.UserId == userId).Select(x => new SportsRecordDto { UserId = x.UserId, Count = x.Amount, CreateTime = x.CreateTime, Duration = x.Duration, Consume = x.Amount / 10, GroupTaskName = x.PersonalGoalName }).ToListAsync(); var combinedData = groupQueryss.Concat(personalQuerysss); return new PageDataDto { Total = combinedData.Count(), Datas = combinedData .OrderByDescending(x => x.CreateTime) .Skip((dto.PageIndex - 1) * dto.PageSize) .Take(dto.PageSize) .ToList() }; //var totalCounts = combinedQuerys.Count(); //var groupQuery = _userContext.GroupTaskResult.Where(x => x.UserId == userId).Select(x => new SportsRecordDto //{ // UserId = x.UserId, // Count = x.Amount, // CreateTime = x.CreateTime, // Duration = x.Duration, // Consume = x.Amount / 10, // GroupTaskName = "团队训练" //}); //var personalQuery = _userContext.PersonalGoalResult.Where(x => x.UserId == userId).Select(x => new SportsRecordDto //{ // UserId = x.UserId, // Count = x.Amount, // CreateTime = x.CreateTime, // Duration = x.Duration, // Consume = x.Amount / 10, // GroupTaskName = x.PersonalGoalName //}); //var combinedQuery = groupQuery.Concat(personalQuery); //var totalCount = await combinedQuery.CountAsync(); //var list = await combinedQuery // .OrderByDescending(x => x.CreateTime) // .Skip((dto.PageIndex - 1) * dto.PageSize) // .Take(dto.PageSize) // .ToListAsync(); //return new PageDataDto //{ // Total = totalCount, // Datas = list //}; } /// /// 创建个人目标 /// /// /// public async Task CreatePersonalGoal(CreatePersonalGoalDto dto) { var userId = UserLoginContext.Current.UserId; var today = DateTime.Now.Date; var personalGoal = await _userContext.PersonalGoal .FirstOrDefaultAsync(x => x.GoalDate.Date == today && x.UserId == userId); if (personalGoal == null) { var entity = new WCA_PersonalGoal() { UserId = userId, GoalDuration = dto.GoalDuration, GoalAmount = dto.GoalAmount, GoalDate = dto.GoalDate.Date, }; await _userContext.AddAsync(entity); } else { personalGoal.GoalDuration = dto.GoalDuration; personalGoal.GoalAmount = dto.GoalAmount; _userContext.Update(personalGoal); } await _userContext.SaveChangesAsync(); } /// /// 获取个人目标 /// /// public async Task CetPersonalGoal() { var res = new CetPersonalGoalDto(); var userId = UserLoginContext.Current.UserId; var today = DateTime.Now.Date; var personalGoals = await _userContext.PersonalGoal .Join(_userContext.PersonalGoalResult, a => a.Id, s => s.PersonalGoalId, (a, s) => new { a.GoalAmount, a.GoalDate, a.GoalDuration, s.PersonalGoalName, s.PersonalGoalType, s.Amount, s.PersonalGoalId, s.Duration, s.CreateTime, s.WorkModeType, s.UserId }).Where(x => x.UserId == userId).ToListAsync(); var personalGoal = await _userContext.PersonalGoal.Where(x => x.GoalDate.Date == today && x.UserId == userId).FirstOrDefaultAsync(); var teamData = await _userContext.GroupTaskResult.Where(x => x.UserId == userId).Select(x => new { x.CreateTime, x.Amount }).ToListAsync(); var personData = await _userContext.PersonalGoalResult.Where(x => x.UserId == userId).Select(x => new { x.CreateTime, x.Amount }).ToListAsync(); if (personalGoal != null) { res.GoalAmount = personalGoal.GoalAmount; res.CompletedCount = teamData.Where(x => x.CreateTime.Date == today).Sum(x => x.Amount) + personData.Where(x => x.CreateTime.Date == today).Sum(x => x.Amount); res.CompletionRate = res.GoalAmount > 0 ? $"{(decimal)res.CompletedCount / res.GoalAmount * 100:F0}%" : "0%"; } // 取最新的一条 var concatData = teamData.Concat(personData).OrderByDescending(x => x.CreateTime).ToList(); res.LastCount = concatData.FirstOrDefault()?.Amount ?? 0; res.AccumulatedCount = concatData.Sum(x => x.Amount); var userGoals = personalGoals .OrderBy(x => x.GoalDate) .GroupBy(x => x.GoalDate.Date) .Select(g => new { Date = g.Key, TotalAmount = g.Sum(x => x.Amount), GoalAmount = g.First().GoalAmount, Achieved = g.Sum(x => x.Amount) >= g.First().GoalAmount }) .OrderBy(d => d.Date) .ToList(); int currentStreak = 0; DateTime? prevDay = null; foreach (var day in userGoals.OrderByDescending(d => d.Date)) { if (prevDay == null && !day.Achieved) { currentStreak = 0; break; } if (day.Achieved) { if (prevDay == null) { currentStreak = 1; } else if ((prevDay.Value - day.Date).Days == 1) { currentStreak++; } else { break; } } else { currentStreak = 0; break; } prevDay = day.Date; } res.ContinuousDays = currentStreak; return res; } /// /// 添加个人目标数据 /// /// /// public async Task AddPersonalGoalResult(AddPersonalGoalResultDto dto) { var userId = UserLoginContext.Current.UserId; var today = DateTime.Now.Date; var personalGoal = await _userContext.PersonalGoal .FirstOrDefaultAsync(x => x.GoalDate.Date == today && x.UserId == userId); var entity = new WCA_PersonalGoalResult() { UserId = userId, DataSource = dto.DataSource, Amount = dto.Amount, Score = dto.Score, PersonalGoalType = dto.PersonalGoalType, Duration = dto.Duration, PersonalGoalName = dto.PersonalGoalName, PersonalGoalId = personalGoal?.Id ?? 0, WorkModeType = dto.WorkModeType, WorkModeTypeName = dto.WorkModeTypeName, CreateTime = DateTime.Now }; await _userContext.AddAsync(entity); await _userContext.SaveChangesAsync(); return new TaskResultDto() { TaskResultId = entity.Id }; } /// /// 获取得分和等级 /// /// /// public async Task CetPersonalScoreRank(CetPersonalScoreRankDto dto) { var healthStandard = await _sportsContext.HealthStandards.Where(x => x.CategoryEnum == "OneMinuteJumpRope" && x.GradeId == dto.GradeId && x.Sex == dto.Sex && dto.Amount >= x.MinValue && dto.Amount < x.MaxValue ).FirstOrDefaultAsync(); return new PersonalScoreRankDto() { Score = healthStandard?.Score ?? 0, Rank = healthStandard?.Rank ?? "" }; } /// /// 获取地区项目时长 /// /// public async Task> CetAreaCategory() { var healthStandard = await _sportsContext.AreaCategory.Select(x => new AreaCategoryDto() { Id = x.Id, Area = x.Area, Duration = x.Duration }).ToListAsync(); return healthStandard; } /// /// 获取中考得分 /// /// /// public async Task CetAreaCategoryScoreRank(CetAreaCategoryScoreRankDto dto) { var healthStandard = await _sportsContext.AreaStandards.Where(x => x.AreaCategoryId == dto.AreaId && x.Sex == dto.Sex && dto.Amount >= x.MinValue && dto.Amount < x.MaxValue ).FirstOrDefaultAsync(); return new PersonalScoreRankDto() { Score = healthStandard?.Score ?? 0, Rank = healthStandard?.Rank ?? "" }; } /// /// 获取打卡记录 /// /// /// public async Task> CetCheckInRecord(CetCheckInRecordDto dto) { var userId = UserLoginContext.Current.UserId; var dailyGoals = await _userContext.PersonalGoal .Where(g => g.UserId == userId && g.GoalDate >= dto.StartTime && g.GoalDate <= dto.EndTime) .GroupBy(g => g.GoalDate.Day) .Select(g => new { Day = g.Key, Goal = g.First(), HasGoal = true }) .ToListAsync(); var results = await _userContext.PersonalGoalResult .Where(r => r.UserId == userId && r.CreateTime >= dto.StartTime && r.CreateTime <= dto.EndTime) .ToListAsync(); var dailyRecords = dailyGoals.Select(g => new CheckInRecordDto { Day = g.Day, GoalAmount = g.Goal.GoalAmount, CompletedCount = results .Where(r => r.PersonalGoalId == g.Goal.Id) .Sum(r => r.Amount) }) .OrderBy(x => x.Day) .ToList(); return dailyRecords; } /// /// 学校账号预约 /// /// /// public async Task SchoolAccountApplication(SchoolAccountApplicationDto dto) { var timeNow = DateTime.Now; var entity = new Y_SchoolAccountApplication() { SchoolName = dto.SchoolName, SchoolAddress = dto.SchoolAddress, PhoneNo = dto.PhoneNo, UserName = dto.UserName, Remarks = dto.Remarks, Status = 1, VisitingTime = timeNow, UpdateTime = timeNow }; await _sportsContext.SchoolAccountApplication.AddAsync(entity); await _sportsContext.SaveChangesAsync(); } } }