接口修改

This commit is contained in:
2026-07-06 14:26:16 +08:00
parent 7c53adc804
commit 91752baa3b
6 changed files with 472 additions and 79 deletions

View File

@ -62,4 +62,12 @@ public interface IUserAnswerTaskService : IBaseService<JournalPageTaskUserAnswer
/// <param name="userId">用户Id</param>
/// <returns>批量领取结果</returns>
Task<BatchClaimPointsOutput> BatchClaimPointsAsync(BatchClaimPointsInput input, long userId);
/// <summary>
/// 获取目录树形结构(一级目录和二级目录的完整树形结构,包含任务详情)
/// </summary>
/// <param name="journalId">期刊Id</param>
/// <param name="userId">用户Id</param>
/// <returns>目录树形结构数据</returns>
Task<CatalogTreeOutput> GetCatalogTreeAsync(long journalId, long userId);
}

View File

@ -0,0 +1,130 @@
namespace QYZH.InteractiveMagazine.Models.Dto.UserAnswerTaskService;
/// <summary>
/// 目录树形结构输出(包含一级目录列表)
/// </summary>
public class CatalogTreeOutput
{
/// <summary>
/// 一级目录列表
/// </summary>
public List<FirstLevelCatalogItem> FirstLevelCatalogs { get; set; } = [];
}
/// <summary>
/// 一级目录项输出
/// </summary>
public class FirstLevelCatalogItem
{
/// <summary>
/// 一级目录ID
/// </summary>
public long CatalogId { get; set; }
/// <summary>
/// 一级目录名称
/// </summary>
public string CatalogName { get; set; }
/// <summary>
/// 文章篇数(来自二级目录对应的所有有题目的页面数总和)
/// </summary>
public int ArticleCount { get; set; }
/// <summary>
/// 任务数量来自二级目录对应的所有任务按GroupId去重后的总和
/// </summary>
public int TaskCount { get; set; }
/// <summary>
/// 二级目录列表
/// </summary>
public List<SecondLevelCatalogItem> Children { get; set; } = [];
}
/// <summary>
/// 二级目录项输出(含页码范围、任务数量、状态、总成长值、总积分及任务列表)
/// </summary>
public class SecondLevelCatalogItem
{
/// <summary>
/// 二级目录ID
/// </summary>
public long CatalogId { get; set; }
/// <summary>
/// 二级目录名称
/// </summary>
public string CatalogName { get; set; }
/// <summary>
/// 起始页码
/// </summary>
public int StartPage { get; set; }
/// <summary>
/// 结束页码
/// </summary>
public int EndPage { get; set; }
/// <summary>
/// 任务数量按GroupId去重后的数量
/// </summary>
public int TaskCount { get; set; }
/// <summary>
/// 状态格式如1/2 进行中、0/2 未开始、2/2 已完成)
/// </summary>
public string Status { get; set; }
/// <summary>
/// 总成长值该二级目录下所有任务的成长值总和按GroupId去重
/// </summary>
public int TotalGrowthPoints { get; set; }
/// <summary>
/// 总积分该二级目录下所有任务的积分总和按GroupId去重
/// </summary>
public int TotalPoints { get; set; }
/// <summary>
/// 任务列表(每个任务的详细信息)
/// </summary>
public List<CatalogTaskItem> Tasks { get; set; } = [];
}
/// <summary>
/// 目录任务项输出(任务详情)
/// </summary>
public class CatalogTaskItem
{
/// <summary>
/// 任务分组IDGroupId
/// </summary>
public long GroupId { get; set; }
/// <summary>
/// 任务名称取主任务的Task字段
/// </summary>
public string TaskName { get; set; }
/// <summary>
/// 任务状态(未开始、进行中、已完成)
/// </summary>
public string Status { get; set; }
/// <summary>
/// 成长值取主任务的GrowthPoint
/// </summary>
public int GrowthPoints { get; set; }
/// <summary>
/// 积分值取主任务的Points
/// </summary>
public int Points { get; set; }
/// <summary>
/// 答题时长分钟该GroupId下所有任务的AnswerSeconds累加后转换为分钟
/// </summary>
public double AnswerMinutes { get; set; }
}

View File

@ -1,7 +1,10 @@
using QYZH.InteractiveMagazine.Models.Entity;
using Microsoft.AspNetCore.Http;
using QYZH.InteractiveMagazine.Infrastructure.Context;
using QYZH.InteractiveMagazine.Models.Entity;
using SqlSugar;
using System.Linq.Expressions;
using System.Reflection;
using System.Security.Claims;
using Yitter.IdGenerator;
@ -106,7 +109,7 @@ namespace QYZH.InteractiveMagazine.Repository.Core
return db;
}
/// <summary>
/// 添加创建人 创建时间 更新人 更新时间 默认值
/// </summary>
@ -117,14 +120,20 @@ namespace QYZH.InteractiveMagazine.Repository.Core
db.Aop.DataExecuting = (oldValue, entityInfo) =>
{
var entityValue = entityInfo.EntityColumnInfo.PropertyInfo.GetValue(entityInfo.EntityValue)?.ToString();
var currnetUserName = "";
//var currnetUserName = "";
//var currentNameIdentifier = ServiceContext.GetRequiredService<IHttpContextAccessor>().HttpContext?.User?.FindFirst(ClaimTypes.NameIdentifier)?.Value ?? "";
//var currentUserId = string.IsNullOrWhiteSpace(currentNameIdentifier) ? 0 : long.Parse(currentNameIdentifier);
var currentClaimName = ServiceContext.GetRequiredService<IHttpContextAccessor>().HttpContext?.User?.FindFirst(ClaimTypes.Name)?.Value;
/*** inset生效 ***/
if (entityInfo.OperationType == DataFilterType.InsertByObject)
{
if (entityInfo.PropertyName == "CreatedAt" && (string.IsNullOrWhiteSpace(entityValue) || entityValue == DateTime.MinValue.ToString()))
entityInfo.SetValue(DateTime.Now);//修改CreateTime字段
else if (entityInfo.PropertyName == "CreatedBy" && (string.IsNullOrWhiteSpace(entityValue)))
entityInfo.SetValue(currnetUserName);//修改创建人字段
entityInfo.SetValue(currentClaimName);//修改创建人字段
else if (entityInfo.PropertyName == "IsDeleted" && string.IsNullOrWhiteSpace(entityValue))
entityInfo.SetValue("0");//修改CreateTime字段
}
@ -135,7 +144,7 @@ namespace QYZH.InteractiveMagazine.Repository.Core
if (entityInfo.PropertyName == "UpdatedAt" && (string.IsNullOrWhiteSpace(entityValue) || entityValue == DateTime.MinValue.ToString()))
entityInfo.SetValue(DateTime.Now);//修改UpdatedTime字段
else if (entityInfo.PropertyName == "UpdatedBy" && (string.IsNullOrWhiteSpace(entityValue) || entityValue == "0"))
entityInfo.SetValue(currnetUserName);//修改更新人字段
entityInfo.SetValue(currentClaimName);//修改更新人字段
}
};
return db;

View File

@ -1314,9 +1314,7 @@ public class UserAnswerTaskService(
var newGrowthPointsBalance = user.GrowthPoints + totalGrowthPoints;
await answerRepository.Context.Updateable<Users>()
.SetColumns(u => u.Points == newPointsBalance)
.SetColumns(u => u.GrowthPoints == newGrowthPointsBalance)
.SetColumns(u => u.UpdatedBy == userId.ToString())
.SetColumns(u => u.UpdatedAt == DateTime.Now)
.SetColumns(u => u.GrowthPoints == newGrowthPointsBalance)
.Where(u => u.Id == userId)
.ExecuteCommandAsync();
@ -1326,16 +1324,12 @@ public class UserAnswerTaskService(
UserId = userId,
ChangeAmount = totalPoints,
BalanceAfter = newPointsBalance,
ChangeType = PointsChangeTypeEnum.TaskReward.ToString(),
ChangeType = nameof(PointsChangeTypeEnum.TaskReward),
RelatedId = groupId,
Description = $"完成任务奖励GroupId{mainTask.GroupId}",
Type = PointsFlowTypeEnum.Income,
Status = (int)PointsRecordStatusEnum.Success,
IsDeleted = false,
CreatedBy = "系统",
CreatedAt = DateTime.Now,
UpdatedBy = "系统",
UpdatedAt = DateTime.Now
Status = (int)PointsRecordStatusEnum.Success
};
await answerRepository.Context.Insertable(pointsRecord).ExecuteCommandAsync();
@ -1438,7 +1432,7 @@ public class UserAnswerTaskService(
// 3. 在内存中逐个校验每个 GroupId筛选可领取的任务
// 所有数据已在步骤2中一次性查询完成这里只做内存筛选
// ============================================
var claimableTasks = new List<(long GroupId, int Points, int GrowthPoints, float Score, string TaskNo)>();
var claimableTasks = new List<(long GroupId, int Points, int GrowthPoints, float Score)>();
foreach (var groupId in input.GroupIds)
{
@ -1449,8 +1443,7 @@ public class UserAnswerTaskService(
{
result.FailItems.Add(new BatchClaimFailItem
{
GroupId = groupId,
TaskNo = string.Empty,
GroupId = groupId,
Message = "任务不存在"
});
continue;
@ -1458,30 +1451,13 @@ public class UserAnswerTaskService(
// 3.2 判断是否跨页题目并找主任务
bool isCrossPage = relatedTasks.Count > 1;
var mainTask = relatedTasks.FirstOrDefault(t => t.Id == groupId);
// ============================================
// 【任务编号计算】
// 从 JournalPageTask.No 字段按 - 分割,取索引为 2 的部分,前面加"任务"
// 如果找不到主任务,尝试从子任务中计算
// ============================================
string taskNo = string.Empty;
var taskForNo = mainTask ?? relatedTasks.FirstOrDefault();
if (taskForNo != null && !string.IsNullOrEmpty(taskForNo.No))
{
var parts = taskForNo.No.Split('-');
if (parts.Length >= 3)
{
taskNo = $"任务{parts[2]}";
}
}
var mainTask = relatedTasks.FirstOrDefault(t => t.Id == groupId);
if (mainTask == null)
{
result.FailItems.Add(new BatchClaimFailItem
{
GroupId = groupId,
TaskNo = taskNo,
GroupId = groupId,
Message = "子题目无法单独领取积分,请从主任务入口领取"
});
continue;
@ -1492,8 +1468,7 @@ public class UserAnswerTaskService(
{
result.FailItems.Add(new BatchClaimFailItem
{
GroupId = groupId,
TaskNo = taskNo,
GroupId = groupId,
Message = "请先完成答题再领取积分"
});
continue;
@ -1505,8 +1480,7 @@ public class UserAnswerTaskService(
{
result.FailItems.Add(new BatchClaimFailItem
{
GroupId = groupId,
TaskNo = taskNo,
GroupId = groupId,
Message = "请先完成答题再领取积分"
});
continue;
@ -1524,8 +1498,7 @@ public class UserAnswerTaskService(
{
result.FailItems.Add(new BatchClaimFailItem
{
GroupId = groupId,
TaskNo = taskNo,
GroupId = groupId,
Message = "跨页题目需要完成所有任务才能领取积分"
});
continue;
@ -1537,8 +1510,7 @@ public class UserAnswerTaskService(
{
result.FailItems.Add(new BatchClaimFailItem
{
GroupId = groupId,
TaskNo = taskNo,
GroupId = groupId,
Message = "积分已领取,请勿重复领取"
});
continue;
@ -1553,36 +1525,20 @@ public class UserAnswerTaskService(
{
result.FailItems.Add(new BatchClaimFailItem
{
GroupId = groupId,
TaskNo = taskNo,
GroupId = groupId,
Message = "该任务无积分可领取"
});
continue;
}
// 添加到可领取列表
claimableTasks.Add((groupId, points, growthPoints, score, taskNo));
claimableTasks.Add((groupId, points, growthPoints, score));
}
catch (Exception ex)
{
// 异常情况下,尝试从已查询的数据中计算 taskNo
string taskNo = string.Empty;
if (tasksByGroupId.TryGetValue(groupId, out var tasks) && tasks.Count > 0)
{
var task = tasks.FirstOrDefault(t => t.Id == groupId) ?? tasks.FirstOrDefault();
if (task != null && !string.IsNullOrEmpty(task.No))
{
var parts = task.No.Split('-');
if (parts.Length >= 3)
{
taskNo = $"任务{parts[2]}";
}
}
}
result.FailItems.Add(new BatchClaimFailItem
{
GroupId = groupId,
TaskNo = taskNo,
GroupId = groupId,
Message = ex.Message
});
}
@ -1593,6 +1549,7 @@ public class UserAnswerTaskService(
// ============================================
// 4. 事务执行所有领取操作
// - 手动更新 Users.Points积分累加
// - 手动更新 Users.GrowthPoints成长值累加
// - 插入积分流水记录
// - 喂养宠物(如有活跃宠物,更新宠物成长值)
// ============================================
@ -1622,8 +1579,7 @@ public class UserAnswerTaskService(
// 添加成功详情
result.SuccessItems.Add(new BatchClaimSuccessItem
{
TaskNo = task.TaskNo,
{
Points = task.Points,
GrowthPoints = task.GrowthPoints,
Score = task.Score
@ -1637,31 +1593,27 @@ public class UserAnswerTaskService(
await answerRepository.Context.Updateable<Users>()
.SetColumns(u => u.Points == newPointsBalance)
.SetColumns(u => u.GrowthPoints == newGrowthPointsBalance)
.SetColumns(u => u.UpdatedBy == userId.ToString())
.SetColumns(u => u.UpdatedAt == DateTime.Now)
.SetColumns(u => u.GrowthPoints == newGrowthPointsBalance)
.Where(u => u.Id == userId)
.ExecuteCommandAsync();
// 4b. 批量插入积分流水记录
var records = new List<PointsRecord>();
var tempNewPointsBalance = user.Points;
foreach (var task in claimableTasks)
{
tempNewPointsBalance += task.Points;
// 计算每条记录的领取后余额
records.Add(new PointsRecord
{
UserId = userId,
ChangeAmount = task.Points,
BalanceAfter = newPointsBalance,
ChangeType = PointsChangeTypeEnum.TaskReward.ToString(),
BalanceAfter = tempNewPointsBalance,
ChangeType = nameof(PointsChangeTypeEnum.TaskReward),
RelatedId = task.GroupId,
Description = $"完成任务奖励GroupId{task.GroupId}",
Type = PointsFlowTypeEnum.Income,
Status = (int)PointsRecordStatusEnum.Success,
IsDeleted = false,
CreatedBy = "系统",
CreatedAt = DateTime.Now,
UpdatedBy = "系统",
UpdatedAt = DateTime.Now
});
}
await answerRepository.Context.Insertable(records).ExecuteCommandAsync();
@ -1683,8 +1635,270 @@ public class UserAnswerTaskService(
#region 5.
result.FailCount = result.FailItems.Count;
for (int i = 0; i < result.SuccessItems.Count; i++)
{
result.SuccessItems[i].TaskNo ="任务" + (i + 1);
}
for (int i = 0; i < result.FailItems.Count; i++)
{
result.FailItems[i].TaskNo ="任务" + (i + 1);
}
return result;
#endregion
}
/// <summary>
/// ============================================
/// 方法思路:获取目录树形结构(一级目录和二级目录的完整树形结构,包含任务详情)
/// 【核心逻辑】
/// 1. 用户绑定验证:查询 UserJournal 表验证用户是否绑定该杂志
/// 2. 批量预加载一次性加载目录、页面、任务、用户作答记录避免N+1查询
/// 3. 一级目录统计文章篇数二级目录有题目页面数总和、任务数GroupId去重总和
/// 4. 二级目录构建:页码范围、任务数、状态、总成长值、总积分、任务列表
/// 5. 任务详情任务名称取主任务Task字段、状态、成长值、积分值、答题时长
/// 【状态判定规则】
/// - 未开始:无任何任务作答记录
/// - 进行中:有作答记录但未全部完成
/// - 已完成所有任务都完成Status=1
/// 【跨页题目处理】
/// - 任务名称取主任务Id == GroupId的Task字段
/// - 成长值/积分取主任务数据按GroupId去重计算
/// - 答题时长该GroupId下所有任务的AnswerSeconds累加后转换为分钟
/// ============================================
/// </summary>
/// <param name="journalId">期刊Id</param>
/// <param name="userId">用户Id</param>
/// <returns>目录树形结构数据</returns>
public async Task<CatalogTreeOutput> GetCatalogTreeAsync(long journalId, long userId)
{
#region 0.
// 验证用户是否绑定该杂志,未绑定直接返回空结果
var isBound = await userJournalRepository.Context.Queryable<UserJournal>()
.Where(uj => uj.UserId == userId && uj.JournalId == journalId)
.AnyAsync();
if (!isBound)
{
return new CatalogTreeOutput();
}
#endregion
#region 1.
// 一次性加载所有关联数据避免N+1查询
var allCatalogs = await catalogRepository.Context.Queryable<JournalCatalog>()
.Where(c => c.JournalId == journalId)
.ToListAsync();
var allPages = await pageRepository.Context.Queryable<JournalPage>()
.Where(p => p.JournalId == journalId)
.ToListAsync();
var allTasks = await taskRepository.Context.Queryable<JournalPageTask>()
.Where(t => t.JournalId == journalId)
.ToListAsync();
var userAnswers = await answerRepository.Context.Queryable<JournalPageTaskUserAnswer>()
.Where(a => a.JournalId == journalId && a.UserId == userId)
.ToListAsync();
#endregion
#region 2.
// 用户已作答的任务ID集合包含进行中和已完成
var userAnsweredTaskIds = userAnswers.Select(a => a.JournalPageTaskId).ToHashSet();
// 用户已完成的任务ID集合Status=1表示已批阅完成
var userCompletedTaskIds = userAnswers
.Where(a => a.Status == (int)UserAnswerStatusEnum.Complete)
.Select(a => a.JournalPageTaskId)
.ToHashSet();
#endregion
#region 3.
// 获取一级目录ParentId=0按排序字段排序
var firstLevelCatalogs = allCatalogs.Where(c => c.ParentId == 0).OrderBy(c => c.Sort).ToList();
var result = new CatalogTreeOutput();
foreach (var firstCatalog in firstLevelCatalogs)
{
int articleCount = 0;
int taskCount = 0;
var children = new List<SecondLevelCatalogItem>();
// 获取该一级目录下的二级目录,按排序字段排序
var secondLevelCatalogs = allCatalogs
.Where(c => c.ParentId == firstCatalog.Id)
.OrderBy(c => c.Sort)
.ToList();
foreach (var secondCatalog in secondLevelCatalogs)
{
// 获取二级目录下的所有页面,按页码排序
var secondLevelPages = allPages
.Where(p => p.JournalCatalogId == secondCatalog.Id)
.OrderBy(p => p.PageNum)
.ToList();
var secondLevelPageIds = secondLevelPages.Select(p => p.Id).ToHashSet();
// 统计有题目的页面数(用于文章篇数计算)
var pagesWithTasks = allTasks
.Where(t => secondLevelPageIds.Contains(t.JournalPageId))
.Select(t => t.JournalPageId)
.Distinct()
.ToHashSet();
articleCount += pagesWithTasks.Count;
// 获取二级目录下的所有任务
var secondLevelTasks = allTasks.Where(t => secondLevelPageIds.Contains(t.JournalPageId)).ToList();
// 按GroupId分组跨页题目处理
var groupTasks = secondLevelTasks.GroupBy(t => t.GroupId).ToList();
var catalogTaskCount = groupTasks.Count;
// 如果二级目录没有任务,则跳过不显示
if (catalogTaskCount == 0)
{
continue;
}
taskCount += catalogTaskCount;
// 计算页码范围
var startPage = secondLevelPages.Count > 0 ? secondLevelPages.Min(p => p.PageNum) : 0;
var endPage = secondLevelPages.Count > 0 ? secondLevelPages.Max(p => p.PageNum) : 0;
// 计算二级目录状态
var status = CalculateCatalogStatus(groupTasks, userAnsweredTaskIds, userCompletedTaskIds);
// 计算总成长值和总积分按GroupId去重取主任务数据
var (totalGrowthPoints, totalPoints) = CalculateCatalogPoints(groupTasks);
// 构建任务列表
var taskItems = BuildTaskItems(groupTasks, userAnswers, userAnsweredTaskIds, userCompletedTaskIds);
// 添加二级目录项
children.Add(new SecondLevelCatalogItem
{
CatalogId = secondCatalog.Id,
CatalogName = secondCatalog.Name ?? string.Empty,
StartPage = startPage,
EndPage = endPage,
TaskCount = catalogTaskCount,
Status = status,
TotalGrowthPoints = totalGrowthPoints,
TotalPoints = totalPoints,
Tasks = taskItems
});
}
// 添加一级目录项
result.FirstLevelCatalogs.Add(new FirstLevelCatalogItem
{
CatalogId = firstCatalog.Id,
CatalogName = firstCatalog.Name ?? string.Empty,
ArticleCount = articleCount,
TaskCount = taskCount,
Children = children
});
}
#endregion
return result;
}
#region
/// <summary>
/// 计算目录状态(格式:已完成数/总数 状态描述)
/// </summary>
/// <param name="groupTasks">按GroupId分组的任务列表</param>
/// <param name="userAnsweredTaskIds">用户已作答任务ID集合</param>
/// <param name="userCompletedTaskIds">用户已完成任务ID集合</param>
/// <returns>状态描述格式1/2 进行中、0/2 未开始、2/2 已完成)</returns>
private static string CalculateCatalogStatus(List<IGrouping<long, JournalPageTask>> groupTasks, HashSet<long> userAnsweredTaskIds, HashSet<long> userCompletedTaskIds)
{
var catalogTaskCount = groupTasks.Count;
// 已完成的GroupId数量该GroupId下所有任务都完成
var completedGroupCount = groupTasks.Count(g => g.All(t => userCompletedTaskIds.Contains(t.Id)));
// 已作答的GroupId数量该GroupId下至少有一个任务被作答
var answeredGroupCount = groupTasks.Count(g => g.Any(t => userAnsweredTaskIds.Contains(t.Id)));
if (answeredGroupCount == 0)
return $"0/{catalogTaskCount} 未开始";
if (completedGroupCount == catalogTaskCount)
return $"{completedGroupCount}/{catalogTaskCount} 已完成";
return $"{completedGroupCount}/{catalogTaskCount} 进行中";
}
/// <summary>
/// 计算目录总成长值和总积分按GroupId去重
/// </summary>
/// <param name="groupTasks">按GroupId分组的任务列表</param>
/// <returns>总成长值和总积分</returns>
private static (int TotalGrowthPoints, int TotalPoints) CalculateCatalogPoints(List<IGrouping<long, JournalPageTask>> groupTasks)
{
// 取每个GroupId的主任务Id == GroupId若不存在则取第一个任务
var mainTasks = groupTasks.ConvertAll(g => g.FirstOrDefault(t => t.Id == g.Key) ?? g.First());
return (mainTasks.Sum(t => t.GrowthPoint), mainTasks.Sum(t => t.Points));
}
/// <summary>
/// 构建任务详情列表
/// </summary>
/// <param name="groupTasks">按GroupId分组的任务列表</param>
/// <param name="userAnswers">用户作答记录</param>
/// <param name="userAnsweredTaskIds">用户已作答任务ID集合</param>
/// <param name="userCompletedTaskIds">用户已完成任务ID集合</param>
/// <returns>任务详情列表</returns>
private static List<CatalogTaskItem> BuildTaskItems(List<IGrouping<long, JournalPageTask>> groupTasks, List<JournalPageTaskUserAnswer> userAnswers, HashSet<long> userAnsweredTaskIds, HashSet<long> userCompletedTaskIds)
{
var taskItems = new List<CatalogTaskItem>();
foreach (var group in groupTasks)
{
var groupId = group.Key;
// 取主任务Id == GroupId若不存在则取第一个任务
var mainTask = group.FirstOrDefault(t => t.Id == groupId) ?? group.First();
// 计算该GroupId下所有任务的答题时间秒 → 分钟)
var taskIds = group.Select(t => t.Id).ToHashSet();
var groupAnswerSeconds = userAnswers
.Where(a => taskIds.Contains(a.JournalPageTaskId))
.Sum(a => a.AnswerSeconds);
var groupAnswerMinutes = Math.Round(groupAnswerSeconds / 60.0, 2);
// 判断任务状态
bool hasAnswer = group.Any(t => userAnsweredTaskIds.Contains(t.Id));
bool isAllCompleted = group.All(t => userCompletedTaskIds.Contains(t.Id));
string taskStatus = !hasAnswer ? "未开始" : (isAllCompleted ? "已完成" : "进行中");
taskItems.Add(new CatalogTaskItem
{
GroupId = groupId,
TaskName = mainTask.Task ?? string.Empty,
Status = taskStatus,
GrowthPoints = mainTask.GrowthPoint,
Points = mainTask.Points,
AnswerMinutes = groupAnswerMinutes
});
}
return taskItems;
}
#endregion
}

View File

@ -238,8 +238,8 @@ public class UserAnswerTaskController : WeChatBaseController
public async Task<BaseResponse<BatchClaimPointsOutput>> BatchClaimPointsAsync([FromBody] BatchClaimPointsInput input)
{
try
{
var userId = ConstUserId;//GetCurrentUserId();
{
var userId = GetCurrentUserId();
if (userId == 0)
{
return BaseResponse<BatchClaimPointsOutput>.Fail(ResultCode.DENY, "未获取到用户信息");
@ -264,4 +264,35 @@ public class UserAnswerTaskController : WeChatBaseController
return BaseResponse<BatchClaimPointsOutput>.Fail("批量领取积分失败,请稍后重试");
}
}
/// <summary>
/// 获取目录树形结构(一级目录和二级目录的完整树形结构,包含任务详情)
/// </summary>
/// <param name="journalId">期刊Id</param>
/// <returns>目录树形结构数据</returns>
[HttpGet("catalog-tree/{journalId:long}")]
public async Task<BaseResponse<CatalogTreeOutput>> GetCatalogTreeAsync([Required(ErrorMessage = "参数错误")] long journalId)
{
try
{
var userId = ConstUserId;//GetCurrentUserId();
if (userId == 0)
{
return BaseResponse<CatalogTreeOutput>.Fail(ResultCode.DENY, "未获取到用户信息");
}
if (journalId <= 0)
{
return BaseResponse<CatalogTreeOutput>.Fail(ResultCode.PARAM_ERROR, "期刊Id不能为空");
}
var result = await _userAnswerTaskService.GetCatalogTreeAsync(journalId, userId);
return Success(result);
}
catch (Exception ex)
{
_logger.LogError(ex, "获取目录树形结构失败JournalId: {JournalId}, UserId: {UserId}", journalId, GetCurrentUserId());
return BaseResponse<CatalogTreeOutput>.Fail("获取目录树形结构失败,请稍后重试");
}
}
}

View File

@ -1,6 +1,7 @@
using Microsoft.AspNetCore.Authorization;
using Microsoft.AspNetCore.Mvc;
using QYZH.InteractiveMagazine.Infrastructure.Auth;
using QYZH.InteractiveMagazine.Infrastructure.Context;
using QYZH.InteractiveMagazine.Models.Dto;
using QYZH.InteractiveMagazine.Models.Enum;
using System.Security.Claims;