using AutoMapper;
using Entities.Contracts;
using SharedDATA.Api;
using System.Linq.Expressions;
using System.Linq;
using Entities.DTO;
namespace TechHelper.Services.Beta
{
public class QuestionService : IQuestionService
{
private readonly IUnitOfWork _work;
private readonly IMapper _mapper;
private readonly IExamService _examService;
public QuestionService(IUnitOfWork work, IMapper mapper, IExamService examService)
{
_work = work;
_mapper = mapper;
_examService = examService;
}
#region CRUD Operations
///
/// 创建新题目
///
/// 题目DTO
/// API响应结果
public async Task AddAsync(QuestionDto model)
{
try
{
// 业务逻辑校验:检查题目是否已存在
var existingQuestion = await _work.GetRepository().GetFirstOrDefaultAsync(
predicate: q => q.Title == model.Title && !q.IsDeleted
);
if (existingQuestion != null)
{
return ApiResponse.Error($"题目 '{model.Title}' 已存在,请勿重复添加。");
}
var newQuestion = _mapper.Map(model);
// 插入数据
await _work.GetRepository().InsertAsync(newQuestion);
await _work.SaveChangesAsync();
return ApiResponse.Success("题目添加成功。", newQuestion);
}
catch (Exception ex)
{
return ApiResponse.Error($"添加题目失败: {ex.Message}");
}
}
///
/// 根据ID获取题目
///
/// 题目ID
/// API响应结果
public async Task GetAsync(Guid id)
{
try
{
var question = await _work.GetRepository().GetFirstOrDefaultAsync(
predicate: q => q.Id == id && !q.IsDeleted
);
if (question == null)
{
return ApiResponse.Error($"找不到 ID 为 {id} 的题目。");
}
return ApiResponse.Success(result: question);
}
catch (Exception ex)
{
return ApiResponse.Error($"获取题目时发生错误: {ex.Message}");
}
}
///
/// 获取所有题目(支持分页和搜索)
///
/// 查询参数
/// API响应结果
public async Task GetAllAsync(QueryParameter query)
{
try
{
var repository = _work.GetRepository();
if (query.Search != null && !string.IsNullOrWhiteSpace(query.Search))
{
var questions = await repository.GetPagedListAsync(
predicate: q => q.Title.Contains(query.Search) && !q.IsDeleted,
pageSize: query.PageSize,
pageIndex: query.PageIndex
);
var questionDtosFiltered = _mapper.Map>(questions.Items);
return new ApiResponse(true, questionDtosFiltered);
}
else
{
var questions = await repository.GetPagedListAsync(
predicate: q => !q.IsDeleted,
pageSize: query.PageSize,
pageIndex: query.PageIndex
);
var questionDtos = _mapper.Map>(questions.Items);
return new ApiResponse(true, questionDtos);
}
}
catch (Exception ex)
{
return new ApiResponse($"获取所有题目时发生错误: {ex.Message}");
}
}
///
/// 更新题目信息
///
/// 题目DTO
/// API响应结果
public async Task UpdateAsync(QuestionDto model)
{
try
{
// 检查题目是否存在
var existingQuestion = await _work.GetRepository().GetFirstOrDefaultAsync(
predicate: q => q.Id == model.Id && !q.IsDeleted
);
if (existingQuestion == null)
{
return ApiResponse.Error($"找不到 ID 为 {model.Id} 的题目,无法更新。");
}
// 检查题目文本是否与其他题目重复
var duplicateCheck = await _work.GetRepository().GetFirstOrDefaultAsync(
predicate: q => q.Id != model.Id && q.Title == model.Title && !q.IsDeleted
);
if (duplicateCheck != null)
{
return ApiResponse.Error($"题目文本 '{model.Title}' 已被其他题目占用,请修改。");
}
// 使用mapper更新实体属性,保留系统字段
_mapper.Map(model, existingQuestion);
existingQuestion.UpdatedAt = DateTime.UtcNow;
// 更新数据
_work.GetRepository().Update(existingQuestion);
await _work.SaveChangesAsync();
return ApiResponse.Success("题目更新成功。", existingQuestion);
}
catch (Exception ex)
{
return ApiResponse.Error($"更新题目失败: {ex.Message}");
}
}
///
/// 删除题目(软删除)
///
/// 题目ID
/// API响应结果
public async Task DeleteAsync(Guid id)
{
try
{
var questionToDelete = await _work.GetRepository().GetFirstOrDefaultAsync(
predicate: q => q.Id == id && !q.IsDeleted
);
if (questionToDelete == null)
{
return ApiResponse.Error($"找不到 ID 为 {id} 的题目,或者该题目已被删除。");
}
// 软删除
questionToDelete.IsDeleted = true;
questionToDelete.UpdatedAt = DateTime.UtcNow;
_work.GetRepository().Update(questionToDelete);
await _work.SaveChangesAsync();
return ApiResponse.Success($"ID 为 {id} 的题目已成功删除 (软删除)。");
}
catch (Exception ex)
{
return ApiResponse.Error($"删除题目时发生错误: {ex.Message}");
}
}
#endregion
#region Business Logic Methods
///
/// 根据标题查找题目
///
/// 题目标题
/// API响应结果
public async Task FindByTitle(string title)
{
try
{
var question = await _work.GetRepository().GetFirstOrDefaultAsync(
predicate: q => q.Title == title && !q.IsDeleted
);
if (question == null)
{
return ApiResponse.Error($"未找到题目 '{title}'。");
}
return ApiResponse.Success(result: question);
}
catch (Exception ex)
{
return ApiResponse.Error($"查找题目时出现问题: {ex.Message}");
}
}
///
/// 批量检查题目标题是否存在
///
/// 题目标题集合
/// API响应结果
public async Task CheckTitlesExistence(IEnumerable titles)
{
try
{
if (titles == null || !titles.Any())
{
return ApiResponse.Success("未指定查询的题目文本,返回空结果。", new Dictionary());
}
var distinctTitles = titles.Distinct(StringComparer.OrdinalIgnoreCase).ToList();
var existingQuestions = await _work.GetRepository().GetAllAsync(
predicate: q => distinctTitles.Contains(q.Title) && !q.IsDeleted
);
var existingQuestionTexts = new HashSet(
existingQuestions.Select(q => q.Title),
StringComparer.OrdinalIgnoreCase
);
var resultDictionary = new Dictionary(StringComparer.OrdinalIgnoreCase);
foreach (var title in titles)
{
resultDictionary[title] = existingQuestionTexts.Contains(title);
}
return ApiResponse.Success(result: resultDictionary);
}
catch (Exception ex)
{
return ApiResponse.Error($"批量查找题目存在性时出现问题: {ex.Message}");
}
}
#endregion
}
///
/// 表达式构建器扩展类
///
public static class PredicateBuilder
{
public static Expression> And(
this Expression> first,
Expression> second)
{
var invokedExpr = Expression.Invoke(second, first.Parameters.Cast());
return Expression.Lambda>(
Expression.AndAlso(first.Body, invokedExpr),
first.Parameters
);
}
public static Expression> Or(
this Expression> first,
Expression> second)
{
var invokedExpr = Expression.Invoke(second, first.Parameters.Cast());
return Expression.Lambda>(
Expression.OrElse(first.Body, invokedExpr),
first.Parameters
);
}
public static Expression> True() => f => true;
public static Expression> False() => f => false;
}
}