修复报名后修改项目的问题

This commit is contained in:
马梓彭 2026-06-08 12:19:33 +08:00
parent 682c9580eb
commit 3619b4b260

View File

@ -525,6 +525,16 @@ public class EventService : BaseService<EventInfo>, ITransient
var eventInfo = await _repository.GetByIdAsync(input.Id);
if (eventInfo == null) throw new InvalidOperationException("赛事不存在");
// 检查赛事状态:如果是报名状态,检查是否修改了项目和组别
if (eventInfo.EventStatus == EventStatus.Enrolling)
{
var hasProjectOrGroupChange = await CheckIfProjectsOrGroupsChanged(input, eventInfo.Id);
if (hasProjectOrGroupChange)
{
throw Oops.Bah("当前赛事正在报名中,不允许修改项目信息");
}
}
// 将前端传过来的Code转换为对应的Id
var provinceId = eventInfo.ProvinceId;
var cityId = eventInfo.CityId;
@ -585,75 +595,209 @@ public class EventService : BaseService<EventInfo>, ITransient
var projectFees = new List<ProjectFeeInput>();
// 3. 更新项目信息 - 使用软删避免丢失历史报名关联数据
var oldEventProjects = await _eventProjectRepository.GetListAsync(x => x.EventId == input.Id && !x.DeleteMark);
var oldEventProjectIds = oldEventProjects.Select(x => x.Id).ToList();
if (oldEventProjectIds.Any())
// 3. 更新项目信息
if (eventInfo.EventStatus == EventStatus.Enrolling)
{
// 软删旧的 EventProjectGroup(按框架模式:直接 UPDATE)
await _eventProjectGroupRepository.SoftDeleteAsync(x => oldEventProjectIds.Contains(x.EventProjectId));
// 报名状态下,只允许修改项目价格和限报
var oldEventProjects = await _eventProjectRepository.GetListAsync(x => x.EventId == input.Id && !x.DeleteMark);
var oldProjectDict = oldEventProjects.ToDictionary(x => x.ProjectId);
// 软删旧的 EventProjectRegistrationLimit
await _projectLimitRepository.SoftDeleteAsync(x => oldEventProjectIds.Contains(x.ProjectId));
// 软删旧的 EventProject
await _eventProjectRepository.SoftDeleteAsync(x => oldEventProjectIds.Contains(x.Id));
}
if (input.Projects != null && input.Projects.Any())
{
foreach (var projInput in input.Projects)
if (input.Projects != null && input.Projects.Any())
{
var eventProject = new EventProject
foreach (var projInput in input.Projects)
{
Id = _idGenerator.NewLong(),
EventId = eventInfo.Id,
ProjectId = projInput.ProjectId,
GenderType = projInput.GenderType,
Price = projInput.Fee,
CreatedUserId = _authManager.UserId,
CreatedTime = DateTime.Now
};
await _eventProjectRepository.InsertAsync(eventProject);
projectFees.Add(new ProjectFeeInput { ProjectId = eventProject.Id, Fee = projInput.Fee });
if (projInput.Groups != null && projInput.Groups.Any())
{
var groups = projInput.Groups.Select(g =>
if (oldProjectDict.ContainsKey(projInput.ProjectId))
{
var group = new EventProjectGroup
var eventProject = oldProjectDict[projInput.ProjectId];
// 只更新项目价格
eventProject.Price = projInput.Fee;
eventProject.UpdatedTime = DateTime.Now;
await _eventProjectRepository.UpdateAsync(eventProject);
projectFees.Add(new ProjectFeeInput { ProjectId = eventProject.Id, Fee = projInput.Fee });
// 更新项目限报
var oldLimit = await _projectLimitRepository.GetFirstAsync(x => x.ProjectId == eventProject.Id && !x.DeleteMark);
if (projInput.LimitCount.HasValue)
{
if (oldLimit != null)
{
oldLimit.LimitCount = projInput.LimitCount.Value;
oldLimit.UpdatedTime = DateTime.Now;
await _projectLimitRepository.UpdateAsync(oldLimit);
}
else
{
var projLimit = new EventProjectRegistrationLimit
{
Id = _idGenerator.NewLong(),
EventId = eventInfo.Id,
ProjectId = eventProject.Id,
LimitCount = projInput.LimitCount.Value,
CreatedUserId = _authManager.UserId,
CreatedTime = DateTime.Now
};
await _projectLimitRepository.InsertAsync(projLimit);
}
}
else if (oldLimit != null)
{
await _projectLimitRepository.SoftDeleteAsync(x => x.Id == oldLimit.Id);
}
}
}
}
}
else
{
// 非报名状态下,全量更新项目信息
var oldEventProjects = await _eventProjectRepository.GetListAsync(x => x.EventId == input.Id && !x.DeleteMark);
var oldProjectDict = oldEventProjects.ToDictionary(x => x.ProjectId);
var oldEventProjectIds = oldEventProjects.Select(x => x.Id).ToList();
if (input.Projects != null && input.Projects.Any())
{
var newProjectIds = new List<long>();
foreach (var projInput in input.Projects)
{
EventProject eventProject;
if (oldProjectDict.ContainsKey(projInput.ProjectId))
{
// 更新现有项目
eventProject = oldProjectDict[projInput.ProjectId];
eventProject.GenderType = projInput.GenderType;
eventProject.Price = projInput.Fee;
eventProject.UpdatedTime = DateTime.Now;
await _eventProjectRepository.UpdateAsync(eventProject);
newProjectIds.Add(eventProject.Id);
}
else
{
// 新增项目
eventProject = new EventProject
{
Id = _idGenerator.NewLong(),
EventId = eventInfo.Id,
EventProjectId = eventProject.Id,
ProjectId = projInput.ProjectId,
ProjectGroupId = g.ProjectGroupId,
GroupName = g.GroupName ?? "",
BirthDateStart = g.BirthDateStart ?? DateTime.MinValue,
BirthDateEnd = g.BirthDateEnd ?? DateTime.MinValue,
Gender = g.Gender ?? Gender.All,
GenderType = projInput.GenderType,
Price = projInput.Fee,
CreatedUserId = _authManager.UserId,
CreatedTime = DateTime.Now
};
return group;
}).ToList();
await _eventProjectGroupRepository.InsertRangeAsync(groups);
await _eventProjectRepository.InsertAsync(eventProject);
newProjectIds.Add(eventProject.Id);
}
projectFees.Add(new ProjectFeeInput { ProjectId = eventProject.Id, Fee = projInput.Fee });
// 处理项目分组
var oldGroups = await _eventProjectGroupRepository.GetListAsync(x => x.EventProjectId == eventProject.Id && !x.DeleteMark);
var oldGroupDict = oldGroups.ToDictionary(x => x.ProjectGroupId);
var newGroupIds = new List<long>();
if (projInput.Groups != null && projInput.Groups.Any())
{
foreach (var groupInput in projInput.Groups)
{
EventProjectGroup group;
if (oldGroupDict.ContainsKey(groupInput.ProjectGroupId))
{
// 更新现有分组
group = oldGroupDict[groupInput.ProjectGroupId];
group.GroupName = groupInput.GroupName ?? "";
group.BirthDateStart = groupInput.BirthDateStart ?? DateTime.MinValue;
group.BirthDateEnd = groupInput.BirthDateEnd ?? DateTime.MinValue;
group.Gender = groupInput.Gender ?? Gender.All;
group.UpdatedTime = DateTime.Now;
await _eventProjectGroupRepository.UpdateAsync(group);
newGroupIds.Add(group.Id);
}
else
{
// 新增分组
group = new EventProjectGroup
{
Id = _idGenerator.NewLong(),
EventId = eventInfo.Id,
EventProjectId = eventProject.Id,
ProjectId = projInput.ProjectId,
ProjectGroupId = groupInput.ProjectGroupId,
GroupName = groupInput.GroupName ?? "",
BirthDateStart = groupInput.BirthDateStart ?? DateTime.MinValue,
BirthDateEnd = groupInput.BirthDateEnd ?? DateTime.MinValue,
Gender = groupInput.Gender ?? Gender.All,
CreatedUserId = _authManager.UserId,
CreatedTime = DateTime.Now
};
await _eventProjectGroupRepository.InsertAsync(group);
newGroupIds.Add(group.Id);
}
}
}
// 软删除不再存在的分组
var groupsToDelete = oldGroups.Where(g => !newGroupIds.Contains(g.Id)).Select(g => g.Id).ToList();
if (groupsToDelete.Any())
{
await _eventProjectGroupRepository.SoftDeleteAsync(x => groupsToDelete.Contains(x.Id));
}
// 处理项目限制
var oldLimit = await _projectLimitRepository.GetFirstAsync(x => x.ProjectId == eventProject.Id && !x.DeleteMark);
if (projInput.LimitCount.HasValue)
{
if (oldLimit != null)
{
// 更新现有限制
oldLimit.LimitCount = projInput.LimitCount.Value;
oldLimit.UpdatedTime = DateTime.Now;
await _projectLimitRepository.UpdateAsync(oldLimit);
}
else
{
// 新增限制
var projLimit = new EventProjectRegistrationLimit
{
Id = _idGenerator.NewLong(),
EventId = eventInfo.Id,
ProjectId = eventProject.Id,
LimitCount = projInput.LimitCount.Value,
CreatedUserId = _authManager.UserId,
CreatedTime = DateTime.Now
};
await _projectLimitRepository.InsertAsync(projLimit);
}
}
else if (oldLimit != null)
{
// 删除限制
await _projectLimitRepository.SoftDeleteAsync(x => x.Id == oldLimit.Id);
}
}
if (projInput.LimitCount.HasValue)
// 软删除不再存在的项目
var projectsToDelete = oldEventProjects.Where(ep => !newProjectIds.Contains(ep.Id)).Select(ep => ep.Id).ToList();
if (projectsToDelete.Any())
{
var projLimit = new EventProjectRegistrationLimit
{
Id = _idGenerator.NewLong(),
EventId = eventInfo.Id,
ProjectId = eventProject.Id,
LimitCount = projInput.LimitCount.Value,
CreatedUserId = _authManager.UserId,
CreatedTime = DateTime.Now
};
await _projectLimitRepository.InsertAsync(projLimit);
await _eventProjectGroupRepository.SoftDeleteAsync(x => projectsToDelete.Contains(x.EventProjectId));
await _projectLimitRepository.SoftDeleteAsync(x => projectsToDelete.Contains(x.ProjectId));
await _eventProjectRepository.SoftDeleteAsync(x => projectsToDelete.Contains(x.Id));
}
}
else
{
// 删除所有项目
if (oldEventProjectIds.Any())
{
await _eventProjectGroupRepository.SoftDeleteAsync(x => oldEventProjectIds.Contains(x.EventProjectId));
await _projectLimitRepository.SoftDeleteAsync(x => oldEventProjectIds.Contains(x.ProjectId));
await _eventProjectRepository.SoftDeleteAsync(x => oldEventProjectIds.Contains(x.Id));
}
}
}
@ -689,6 +833,88 @@ public class EventService : BaseService<EventInfo>, ITransient
}
}
/// <summary>
/// 检查项目或组别是否有变化
/// </summary>
private async Task<bool> CheckIfProjectsOrGroupsChanged(UpdateEventInput input, long eventId)
{
var oldEventProjects = await _eventProjectRepository.GetListAsync(x => x.EventId == eventId && !x.DeleteMark);
// 检查项目数量是否变化
if ((input.Projects == null || !input.Projects.Any()) && oldEventProjects.Any())
{
return true; // 删除了所有项目
}
if (input.Projects != null && input.Projects.Count() != oldEventProjects.Count)
{
return true; // 项目数量有变化
}
// 如果都有项目,继续比较每个项目
if (input.Projects != null && input.Projects.Any())
{
var oldProjectDict = oldEventProjects.ToDictionary(x => x.ProjectId);
foreach (var inputProj in input.Projects)
{
// 检查是否有新的项目
if (!oldProjectDict.ContainsKey(inputProj.ProjectId))
{
return true;
}
var oldProj = oldProjectDict[inputProj.ProjectId];
// 检查项目的基本信息是否变化
if (oldProj.GenderType != inputProj.GenderType)
{
return true;
}
// 检查组别是否变化
var oldGroups = await _eventProjectGroupRepository.GetListAsync(x => x.EventProjectId == oldProj.Id && !x.DeleteMark);
if ((inputProj.Groups == null || !inputProj.Groups.Any()) && oldGroups.Any())
{
return true; // 删除了所有组别
}
if (inputProj.Groups != null && inputProj.Groups.Count() != oldGroups.Count)
{
return true; // 组别数量有变化
}
if (inputProj.Groups != null && inputProj.Groups.Any())
{
var oldGroupDict = oldGroups.ToDictionary(x => x.ProjectGroupId);
foreach (var inputGroup in inputProj.Groups)
{
// 检查是否有新的组别
if (!oldGroupDict.ContainsKey(inputGroup.ProjectGroupId))
{
return true;
}
var oldGroup = oldGroupDict[inputGroup.ProjectGroupId];
// 检查组别的基本信息是否变化
if (oldGroup.GroupName != inputGroup.GroupName ||
oldGroup.BirthDateStart != (inputGroup.BirthDateStart ?? DateTime.MinValue) ||
oldGroup.BirthDateEnd != (inputGroup.BirthDateEnd ?? DateTime.MinValue) ||
oldGroup.Gender != (inputGroup.Gender ?? Gender.All))
{
return true;
}
}
}
}
}
return false;
}
/// <summary>
/// 导出赛事
/// </summary>
@ -961,74 +1187,151 @@ public class EventService : BaseService<EventInfo>, ITransient
throw new InvalidOperationException("请先完成参与单位配置");
}
// 1. 更新项目信息 (全量替换) - 使用软删避免丢失历史报名关联数据
// 1. 更新项目信息 - 优先修改现有数据,仅对新增数据执行添加操作
var oldEventProjects = await _eventProjectRepository.GetListAsync(x => x.EventId == input.EventId && !x.DeleteMark);
var oldProjectDict = oldEventProjects.ToDictionary(x => x.ProjectId);
var oldEventProjectIds = oldEventProjects.Select(x => x.Id).ToList();
if (oldEventProjectIds.Any())
{
// 软删旧的 EventProjectGroup(按框架模式:直接 UPDATE)
await _eventProjectGroupRepository.SoftDeleteAsync(x => oldEventProjectIds.Contains(x.EventProjectId));
// 软删旧的 EventProjectRegistrationLimit
await _projectLimitRepository.SoftDeleteAsync(x => oldEventProjectIds.Contains(x.ProjectId));
// 软删旧的 EventProject
await _eventProjectRepository.SoftDeleteAsync(x => oldEventProjectIds.Contains(x.Id));
}
// 处理输入的项目
if (input.Projects != null && input.Projects.Any())
{
var newProjectIds = new List<long>();
foreach (var projInput in input.Projects)
{
var eventProject = new EventProject
{
Id = _idGenerator.NewLong(),
EventId = input.EventId,
ProjectId = projInput.ProjectId,
GenderType = projInput.GenderType,
Price = projInput.Fee,
CreatedUserId = _authManager.UserId,
CreatedTime = DateTime.Now
};
await _eventProjectRepository.InsertAsync(eventProject);
EventProject eventProject;
if (projInput.Groups != null && projInput.Groups.Any())
if (oldProjectDict.ContainsKey(projInput.ProjectId))
{
var groups = projInput.Groups.Select(g =>
{
var group = new EventProjectGroup
{
Id = _idGenerator.NewLong(),
EventId = input.EventId,
EventProjectId = eventProject.Id,
ProjectId = projInput.ProjectId,
ProjectGroupId = g.ProjectGroupId,
GroupName = g.GroupName ?? "",
BirthDateStart = g.BirthDateStart ?? DateTime.MinValue,
BirthDateEnd = g.BirthDateEnd ?? DateTime.MinValue,
Gender = g.Gender ?? Gender.All,
CreatedUserId = _authManager.UserId,
CreatedTime = DateTime.Now
};
return group;
}).ToList();
await _eventProjectGroupRepository.InsertRangeAsync(groups);
// 更新现有项目
eventProject = oldProjectDict[projInput.ProjectId];
eventProject.GenderType = projInput.GenderType;
eventProject.Price = projInput.Fee;
eventProject.UpdatedTime = DateTime.Now;
await _eventProjectRepository.UpdateAsync(eventProject);
newProjectIds.Add(eventProject.Id);
}
if (projInput.LimitCount.HasValue)
else
{
var projLimit = new EventProjectRegistrationLimit
// 新增项目
eventProject = new EventProject
{
Id = _idGenerator.NewLong(),
EventId = input.EventId,
ProjectId = eventProject.Id,
LimitCount = projInput.LimitCount.Value,
ProjectId = projInput.ProjectId,
GenderType = projInput.GenderType,
Price = projInput.Fee,
CreatedUserId = _authManager.UserId,
CreatedTime = DateTime.Now
};
await _projectLimitRepository.InsertAsync(projLimit);
await _eventProjectRepository.InsertAsync(eventProject);
newProjectIds.Add(eventProject.Id);
}
// 处理项目分组
var oldGroups = await _eventProjectGroupRepository.GetListAsync(x => x.EventProjectId == eventProject.Id && !x.DeleteMark);
var oldGroupDict = oldGroups.ToDictionary(x => x.ProjectGroupId);
var newGroupIds = new List<long>();
if (projInput.Groups != null && projInput.Groups.Any())
{
foreach (var groupInput in projInput.Groups)
{
EventProjectGroup group;
if (oldGroupDict.ContainsKey(groupInput.ProjectGroupId))
{
// 更新现有分组
group = oldGroupDict[groupInput.ProjectGroupId];
group.GroupName = groupInput.GroupName ?? "";
group.BirthDateStart = groupInput.BirthDateStart ?? DateTime.MinValue;
group.BirthDateEnd = groupInput.BirthDateEnd ?? DateTime.MinValue;
group.Gender = groupInput.Gender ?? Gender.All;
group.UpdatedTime = DateTime.Now;
await _eventProjectGroupRepository.UpdateAsync(group);
newGroupIds.Add(group.Id);
}
else
{
// 新增分组
group = new EventProjectGroup
{
Id = _idGenerator.NewLong(),
EventId = input.EventId,
EventProjectId = eventProject.Id,
ProjectId = projInput.ProjectId,
ProjectGroupId = groupInput.ProjectGroupId,
GroupName = groupInput.GroupName ?? "",
BirthDateStart = groupInput.BirthDateStart ?? DateTime.MinValue,
BirthDateEnd = groupInput.BirthDateEnd ?? DateTime.MinValue,
Gender = groupInput.Gender ?? Gender.All,
CreatedUserId = _authManager.UserId,
CreatedTime = DateTime.Now
};
await _eventProjectGroupRepository.InsertAsync(group);
newGroupIds.Add(group.Id);
}
}
}
// 软删除不再存在的分组
var groupsToDelete = oldGroups.Where(g => !newGroupIds.Contains(g.Id)).Select(g => g.Id).ToList();
if (groupsToDelete.Any())
{
await _eventProjectGroupRepository.SoftDeleteAsync(x => groupsToDelete.Contains(x.Id));
}
// 处理项目限制
var oldLimit = await _projectLimitRepository.GetFirstAsync(x => x.ProjectId == eventProject.Id && !x.DeleteMark);
if (projInput.LimitCount.HasValue)
{
if (oldLimit != null)
{
// 更新现有限制
oldLimit.LimitCount = projInput.LimitCount.Value;
oldLimit.UpdatedTime = DateTime.Now;
await _projectLimitRepository.UpdateAsync(oldLimit);
}
else
{
// 新增限制
var projLimit = new EventProjectRegistrationLimit
{
Id = _idGenerator.NewLong(),
EventId = input.EventId,
ProjectId = eventProject.Id,
LimitCount = projInput.LimitCount.Value,
CreatedUserId = _authManager.UserId,
CreatedTime = DateTime.Now
};
await _projectLimitRepository.InsertAsync(projLimit);
}
}
else if (oldLimit != null)
{
// 删除限制
await _projectLimitRepository.SoftDeleteAsync(x => x.Id == oldLimit.Id);
}
}
// 软删除不再存在的项目
var projectsToDelete = oldEventProjects.Where(ep => !newProjectIds.Contains(ep.Id)).Select(ep => ep.Id).ToList();
if (projectsToDelete.Any())
{
await _eventProjectGroupRepository.SoftDeleteAsync(x => projectsToDelete.Contains(x.EventProjectId));
await _projectLimitRepository.SoftDeleteAsync(x => projectsToDelete.Contains(x.ProjectId));
await _eventProjectRepository.SoftDeleteAsync(x => projectsToDelete.Contains(x.Id));
}
}
else
{
// 删除所有项目
if (oldEventProjectIds.Any())
{
await _eventProjectGroupRepository.SoftDeleteAsync(x => oldEventProjectIds.Contains(x.EventProjectId));
await _projectLimitRepository.SoftDeleteAsync(x => oldEventProjectIds.Contains(x.ProjectId));
await _eventProjectRepository.SoftDeleteAsync(x => oldEventProjectIds.Contains(x.Id));
}
}