UserExamService.cs 52 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129
  1. using Exam.Application.Interface.Exam;
  2. using Exam.Infrastructure.Data.Entity;
  3. using Exam.Infrastructure.Enums;
  4. using Exam.Infrastructure.Extensions;
  5. using Exam.Share;
  6. using Exam.Share.Dtos.ExamManage;
  7. using Exam.Share.ViewResponses.Exam;
  8. using Hotline.Application.Exam.Core.Extensions;
  9. using Hotline.Application.Exam.Extensions;
  10. using Hotline.Application.Exam.Interface.Strategy;
  11. using Hotline.Application.Exam.QueryExtensions.ExamManages;
  12. using Hotline.Application.Exam.Strategy;
  13. using Hotline.Exams.ExamManages;
  14. using Hotline.Repository.SqlSugar;
  15. using Hotline.Repository.SqlSugar.DataPermissions;
  16. using Hotline.Repository.SqlSugar.Exam.Interfaces.ExamManages;
  17. using Hotline.Share.Dtos.ExamManages;
  18. using Hotline.Share.Exams.Extensions;
  19. using Hotline.Share.Requests.Exam;
  20. using Hotline.Share.ViewResponses;
  21. using Hotline.Share.ViewResponses.Exam;
  22. using Hotline.Users;
  23. using JiebaNet.Segmenter.Common;
  24. using MapsterMapper;
  25. using Hotline.Application.Exam.Core.Utilities;
  26. using Hotline.Application.Exam.Interface.ExamManages;
  27. using Hotline.Exams.Validate;
  28. using Hotline.Repository.SqlSugar.Exam.Repositories;
  29. using XF.Domain.Authentications;
  30. using XF.Domain.Dependency;
  31. using XF.Domain.Exceptions;
  32. using XF.Domain.Repository;
  33. using ExamQuestion = Hotline.Exams.Questions.ExamQuestion;
  34. using Hotline.Repository.SqlSugar.Exam.Service;
  35. using Hotline.Repository.SqlSugar.Exam.Extensions;
  36. using Exam.Infrastructure.Data.Interface;
  37. using Hotline.Repository.SqlSugar.Exam.Interface;
  38. using DocumentFormat.OpenXml.Drawing.Charts;
  39. using SqlSugar;
  40. using System.Threading;
  41. using DocumentFormat.OpenXml.Office2013.Excel;
  42. using Hotline.Share.Enums.Exams;
  43. using DocumentFormat.OpenXml.Wordprocessing;
  44. namespace Hotline.Application.Exam.Service.ExamManages
  45. {
  46. public class UserExamService : ApiService<ExamUserExam, AddUserExamDto, UpdateUserExamDto, HotlineDbContext>, IUserExamService, IScopeDependency
  47. {
  48. private readonly IUserExamRepository _repository;
  49. private readonly IUserExamItemRepository _userExamItemRepository;
  50. private readonly IUserExamItemOptionRepository _userExamItemOptionRepository;
  51. private readonly IExamAnswerRepository _examAnswerRepository;
  52. private readonly IExamManageRepository _examManageRepository;
  53. private readonly IDataPermissionFilterBuilder _dataPermissionFilterBuilder;
  54. private readonly IServiceProvider _serviceProvider;
  55. private readonly IMapper _mapper;
  56. private readonly ISessionContext _sessionContext
  57. ;
  58. public UserExamService(IUserExamRepository repository,
  59. IUserExamItemRepository userExamItemRepository,
  60. IUserExamItemOptionRepository userExamItemOptionRepository,
  61. IExamAnswerRepository examAnswerRepository,
  62. IExamManageRepository examManageRepository,
  63. IDataPermissionFilterBuilder dataPermissionFilterBuilder, IServiceProvider serviceProvider,
  64. IMapper mapper, ISessionContext sessionContext) : base(repository, mapper, sessionContext)
  65. {
  66. this._repository = repository;
  67. this._userExamItemRepository = userExamItemRepository;
  68. this._userExamItemOptionRepository = userExamItemOptionRepository;
  69. this._examAnswerRepository = examAnswerRepository;
  70. this._examManageRepository = examManageRepository;
  71. this._dataPermissionFilterBuilder = dataPermissionFilterBuilder;
  72. this._serviceProvider = serviceProvider;
  73. this._mapper = mapper;
  74. this._sessionContext = sessionContext;
  75. }
  76. #region public method
  77. public Task<UserExamDto> GetAsync(EntityQueryRequest entityQueryRequest)
  78. {
  79. throw new NotImplementedException();
  80. }
  81. public Task<(int, List<UserExamResultViewResponse>)> GetListAsync(UserExamPagedRequest queryRequest)
  82. {
  83. throw new NotImplementedException();
  84. }
  85. public async Task<ExamQuestionDto> GetExamQuestionDto(ExamQuestionRequest examQuestionRequest)
  86. {
  87. var expression = examQuestionRequest.GetExpression();
  88. var quesetion = await new ExamRepository<Exams.ExamManages.ExamQuestionBak>(_uow, _dataPermissionFilterBuilder, _serviceProvider).Queryable().Where(expression).FirstAsync();
  89. if (quesetion != null)
  90. {
  91. var examQuestionDto = _mapper.Map<ExamQuestionDto>(quesetion);
  92. if (examQuestionDto.QuestionType.CheckSelectType())
  93. {
  94. var questionOptions = await new ExamRepository<ExamQuestionOptionsBak>(_uow, _dataPermissionFilterBuilder, _serviceProvider).Queryable().Where(x => x.ExamQuestionId == quesetion.Id).ToListAsync();
  95. List<ExamUserExamItemOptions> userItemItemOptions = await GetUserExteamItemOptios(quesetion);
  96. if (questionOptions != null)
  97. {
  98. examQuestionDto.QuestionOptions = new List<ExamQuestionOptionsDto>();
  99. questionOptions.ForEach(item =>
  100. {
  101. var examQuestionOptionsDto = _mapper.Map<ExamQuestionOptionsDto>(item);
  102. if (userItemItemOptions != null)
  103. {
  104. examQuestionOptionsDto.IsSelected = userItemItemOptions.Any(m => m.QuestionOptionId == item.Id);
  105. }
  106. examQuestionDto.QuestionOptions.Add(examQuestionOptionsDto);
  107. });
  108. }
  109. }
  110. else
  111. {
  112. List<ExamAnswer> examAnswers = await GetExamAnswers(examQuestionRequest);
  113. examQuestionDto.Answer = examAnswers != null ? examAnswers.FirstOrDefault()?.Answer : null;
  114. }
  115. return examQuestionDto;
  116. }
  117. else
  118. {
  119. throw new UserFriendlyException(ExamErrorMessage.ServiceError, string.Format(ExamErrorMessage.IsNotExists, string.Concat(typeof(ExamQuestion).GetDescription(), ":", examQuestionRequest.QuestionId)));
  120. }
  121. }
  122. private async Task<List<ExamAnswer>> GetExamAnswers(ExamQuestionRequest examQuestionRequest)
  123. {
  124. var examAnswerRepository = new ExamRepository<ExamAnswer>(_uow, _dataPermissionFilterBuilder, _serviceProvider);
  125. var userExamItemRepository = new ExamRepository<ExamUserExamItem>(_uow, _dataPermissionFilterBuilder, _serviceProvider);
  126. var userExamItemTable = userExamItemRepository.Queryable().Where(i=> i.QuestionId == examQuestionRequest.QuestionId);
  127. var userExamTable = _repository.Queryable().Where(u=> u.UserId == _sessionContext.UserId);
  128. var examAnswerTable = examAnswerRepository.Queryable();
  129. var examAnswers = await examAnswerTable.InnerJoin(userExamItemTable, (e, i) => e.UserExamItemId == i.Id)
  130. .InnerJoin(userExamTable, (e, i, u) => i.UserExamId == u.Id)
  131. .Select((e, i, u) => e).ToListAsync();
  132. return examAnswers;
  133. }
  134. private async Task<List<ExamUserExamItemOptions>> GetUserExteamItemOptios(Exams.ExamManages.ExamQuestionBak quesetion)
  135. {
  136. var userExamItemOptionsRepository = new ExamRepository<ExamUserExamItemOptions>(_uow, _dataPermissionFilterBuilder, _serviceProvider);
  137. var userExamItemOptionsTable = userExamItemOptionsRepository.Queryable();
  138. var userExamItemTable = _userExamItemRepository.Queryable();
  139. var userExamTable = _repository.Queryable();
  140. var userItemItemOptions = await userExamItemOptionsTable
  141. .InnerJoin(userExamItemTable, (o, u) => o.UserExamItemId == u.Id)
  142. .InnerJoin(userExamTable, (o, u, e) => u.UserExamId == e.Id)
  143. .Where((o, u, e) => u.QuestionId == quesetion.QuestionId && e.UserId == _sessionContext.UserId).
  144. Select((o, u, e) => o).ToListAsync();
  145. return userItemItemOptions;
  146. }
  147. public async Task<List<ExamQuestionViewResponse>> GetExamQuestionViewResponses(ExamQuestionGroupRequest examQuestionGroupRequest)
  148. {
  149. if (examQuestionGroupRequest.ExamId.IsNull() && examQuestionGroupRequest.UserId.IsNull())
  150. throw UserFriendlyException.SameMessage("查询参数不能为空");
  151. var expression = examQuestionGroupRequest.GetExpression();
  152. var examManageTable = new ExamRepository<ExamManage>(_uow, _dataPermissionFilterBuilder, _serviceProvider).Queryable().Where(expression);
  153. var testPaperItemTable = new ExamRepository<Exams.ExamManages.ExamQuestionBak>(_uow, _dataPermissionFilterBuilder, _serviceProvider).Queryable();
  154. var queryable = await examManageTable.InnerJoin(testPaperItemTable, (e, i) => e.Id == i.ExamId)
  155. .Select((e, i) => i).ToListAsync();
  156. var result = queryable.GroupBy(x => x.QuestionType).Select(m => new ExamQuestionViewResponse
  157. {
  158. QuestionType = m.Key,
  159. Questions = m.Select(n => new SimpleViewResponse
  160. {
  161. Id = n.QuestionId
  162. }).ToList()
  163. }).ToList();
  164. return result;
  165. }
  166. public async Task<List<GradingQuestionViewResponce>> GetGradingQuestionViewResponces(ExamQuestionGroupRequest examQuestionGroupRequest)
  167. {
  168. var expression = examQuestionGroupRequest.GetExpression();
  169. var examManageTable = _examManageRepository.Queryable().Where(expression);
  170. var testPaperItemTable = new ExamRepository<Exams.ExamManages.ExamQuestionBak>(_uow, _dataPermissionFilterBuilder, _serviceProvider).Queryable();
  171. var queryable = await examManageTable.InnerJoin(testPaperItemTable, (e, i) => e.Id == i.ExamId)
  172. .Select((e, i) => i).ToListAsync();
  173. var examQuestionScores = await new ExamRepository<ExamQuestionScoreBak>(_uow, _dataPermissionFilterBuilder, _serviceProvider).Queryable().Where(x => x.ExamManageId == examQuestionGroupRequest.ExamId).ToListAsync();
  174. var userExamItemTable = _userExamItemRepository.Queryable();
  175. var userExamTable = _repository.Queryable().Where(x => x.ExamId == examQuestionGroupRequest.ExamId && x.UserId == examQuestionGroupRequest.UserId);
  176. var userExamItems = await userExamItemTable.InnerJoin(userExamTable, (i, u) => i.UserExamId == u.Id)
  177. .Select((i, u) => i).ToListAsync();
  178. var result = queryable.GroupBy(x => x.QuestionType).Select(m => new GradingQuestionViewResponce
  179. {
  180. QuestionType = m.Key,
  181. Questions = m.Select(n => new GradingExamViewResponse
  182. {
  183. IsCorrect = CheckCorrect(n, examQuestionScores, userExamItems),
  184. Id = userExamItems.FirstOrDefault(x => x.QuestionId == n.QuestionId)?.Id ?? n.Id
  185. }).ToList()
  186. }).ToList();
  187. return result;
  188. }
  189. private bool CheckCorrect(Exams.ExamManages.ExamQuestionBak n, List<ExamQuestionScoreBak> examQuestionScores, List<ExamUserExamItem> userExamItems)
  190. {
  191. var examQuestionScore = examQuestionScores.FirstOrDefault(x => x.QuestionType == n.QuestionType);
  192. var userItem = userExamItems.FirstOrDefault(x => x.QuestionId == n.QuestionId);
  193. if (userItem != null && examQuestionScore != null)
  194. {
  195. return userItem.Score == examQuestionScore.Score;
  196. }
  197. return false;
  198. }
  199. public async Task<PageViewResponse<UserExamResultViewResponse>> GetPagedListAsync(UserExamPagedRequest queryRequest)
  200. {
  201. SqlSugar.ISugarQueryable<UserExamResultViewResponse> queryable = GetQueryable(queryRequest);
  202. var list = await queryable.ToPageListAsync(queryRequest.PageIndex, queryRequest.PageSize);
  203. var total = await queryable.CountAsync();
  204. var result = new UserExamResultPageViewResponse
  205. {
  206. Items = list,
  207. Pagination = new Pagination(queryRequest.PageIndex, queryRequest.PageSize, total)
  208. };
  209. return result;
  210. }
  211. public async Task<GradingExamQuestionDto> GradingAsync(GradingExamItemDto gradingExtamItemDto, CancellationToken cancellationToken)
  212. {
  213. var userExamItem = await _userExamItemRepository.GetAsync(m => m.Id == gradingExtamItemDto.UserExamItemId);
  214. if (userExamItem != null)
  215. {
  216. userExamItem = _mapper.Map<GradingExamItemDto, ExamUserExamItem>(gradingExtamItemDto, userExamItem);
  217. await _userExamItemRepository.UpdateWithValidateAsync(userExamItem, cancellationToken);
  218. }
  219. return await GetNextExamQuestion(gradingExtamItemDto);
  220. }
  221. public async Task SubmitAsync(SubmitExamDto submitExamDto, CancellationToken cancellationToken)
  222. {
  223. var userExam = await _repository.GetAsync(x => x.Id == submitExamDto.Id);
  224. if (userExam != null)
  225. {
  226. userExam = _mapper.Map<SubmitExamDto, ExamUserExam>(submitExamDto, userExam);
  227. userExam.ExamStatus = EExamStatus.Complete;
  228. await _repository.UpdateWithValidateAsync(userExam, cancellationToken);
  229. await CompleteExamManage(userExam.ExamId, cancellationToken);
  230. }
  231. }
  232. private async Task CompleteExamManage(string examId, CancellationToken cancellationToken)
  233. {
  234. var userExams = await _repository.Queryable().Where(x => x.ExamId == examId).ToListAsync();
  235. if (userExams.All(x => x.IsSubmit))
  236. {
  237. var examManage = await _examManageRepository.GetAsync(x=>x.Id == examId);
  238. examManage.ExamStatus = EExamStatus.Complete;
  239. await _examManageRepository.UpdateWithValidateAsync(examManage, cancellationToken);
  240. }
  241. }
  242. public async Task<StartExamViewResponse> ExamAsync(UpdateUserExamItemDto addUserExamItemDto, CancellationToken cancellationToken)
  243. {
  244. var userExam = await new ExamRepository<ExamUserExam>(_uow, _dataPermissionFilterBuilder, _serviceProvider).Queryable().Where(x => x.Id == addUserExamItemDto.UserExamId).FirstAsync();
  245. var startExamViewResponse = await CheckExamValid(userExam, cancellationToken);
  246. if (!startExamViewResponse.CheckValidate())
  247. {
  248. return startExamViewResponse;
  249. }
  250. var hasUserExamItem = _userExamItemRepository.Queryable().Where(x => x.UserExamId == addUserExamItemDto.UserExamId && x.QuestionId == addUserExamItemDto.QuestionId).Any();
  251. if (!hasUserExamItem)
  252. {
  253. await AddExamAsync(_userExamItemRepository, addUserExamItemDto, cancellationToken);
  254. }
  255. else
  256. {
  257. await UpdateExamAsync(_userExamItemRepository, addUserExamItemDto, cancellationToken);
  258. }
  259. await CalcuteExamItemScore(_userExamItemRepository, addUserExamItemDto, cancellationToken);
  260. return startExamViewResponse;
  261. }
  262. public async Task<StartExamViewResponse> StartUserExamAsync(StartUserExamDto startUserExamDto, CancellationToken cancellationToken)
  263. {
  264. var userExam = await _repository.GetAsync(x => x.Id == startUserExamDto.Id);
  265. if (userExam == null) return new StartExamViewResponse
  266. {
  267. IsJoin = false
  268. };
  269. if (userExam.StartTime == null)
  270. userExam.StartTime = DateTime.Now;
  271. var startExamViewResponse = await CheckExamValid(userExam, cancellationToken);
  272. if (!startExamViewResponse.CheckValidate())
  273. {
  274. return startExamViewResponse;
  275. }
  276. if (userExam.ExamStatus == EExamStatus.NoStart)
  277. {
  278. userExam.ExamStatus = Share.Enums.Exams.EExamStatus.Executing;
  279. userExam.ToUpdate(_sessionContext);
  280. await _repository.UpdateWithValidateAsync(userExam, cancellationToken);
  281. }
  282. var examManage = await _examManageRepository.GetAsync(x => x.Id == userExam.ExamId);
  283. return new StartExamViewResponse
  284. {
  285. StartTime = userExam.StartTime,
  286. TimeSpan = examManage?.TimeSpan,
  287. IsCompleted = false
  288. };
  289. }
  290. private async Task<StartExamViewResponse> CheckExamValid(ExamUserExam examUserExam, CancellationToken cancellationToken)
  291. {
  292. var examManage = await _examManageRepository.Queryable().Where(x => x.Id == examUserExam.ExamId).FirstAsync();
  293. var startExamViewResponse = new StartExamViewResponse
  294. {
  295. IsJoin = true,
  296. IsCompleted = false
  297. };
  298. if (examManage != null)
  299. {
  300. var examStrategyProxy = new ExamStrategyProxy();
  301. var examStrategys = new List<IExamStrategy>();
  302. startExamViewResponse = AddCheckStartTimeStrategy(examUserExam, examManage, startExamViewResponse, examStrategys);
  303. startExamViewResponse = AddCheckEndTimeStrategy(examUserExam, examManage, startExamViewResponse, examStrategys);
  304. startExamViewResponse = AddCheckValidateTimeStrategy(examUserExam, examManage, startExamViewResponse, examStrategys);
  305. startExamViewResponse = AddCheckValidateCountStrategy(examUserExam, examManage, startExamViewResponse, examStrategys);
  306. if (!examStrategyProxy.Validate())
  307. {
  308. return startExamViewResponse;
  309. }
  310. }
  311. startExamViewResponse.IsStart = true;
  312. if (examManage.ExamStatus== EExamStatus.NoStart)
  313. {
  314. await UpdateExamStatus(examManage, cancellationToken);
  315. }
  316. startExamViewResponse.TimeSpan = examManage?.TimeSpan ?? 0;
  317. startExamViewResponse.StartTime = examManage?.StartTime;
  318. return startExamViewResponse;
  319. }
  320. private async Task UpdateExamStatus(ExamManage? examManage, CancellationToken cancellationToken)
  321. {
  322. examManage.ExamStatus = EExamStatus.Executing;
  323. examManage.ToUpdate(_sessionContext);
  324. await _examManageRepository.UpdateWithValidateAsync(examManage, cancellationToken);
  325. }
  326. private StartExamViewResponse AddCheckValidateCountStrategy(ExamUserExam examUserExam, ExamManage examManage, StartExamViewResponse startExamViewResponse, List<IExamStrategy> examStrategys)
  327. {
  328. if (examManage.ExamType == Share.Enums.Exams.EExamType.Simulate)
  329. {
  330. var checkStartTime = new CheckValidateCountStrategy(1, 1)
  331. {
  332. CallBack = () =>
  333. {
  334. startExamViewResponse = new StartExamViewResponse
  335. {
  336. IsJoin = false,
  337. IsStart = false,
  338. IsCompleted = true
  339. };
  340. }
  341. };
  342. examStrategys.Add(checkStartTime);
  343. return startExamViewResponse;
  344. }
  345. else
  346. {
  347. var count = new ExamRepository<ExamUserExam>(_uow, _dataPermissionFilterBuilder, _serviceProvider).CountAsync(x => x.ExamId == examManage.Id && x.UserId == examUserExam.UserId).Result;
  348. var checkStartTime = new CheckValidateCountStrategy(examManage.Count, count)
  349. {
  350. CallBack = () =>
  351. {
  352. startExamViewResponse = new StartExamViewResponse
  353. {
  354. IsJoin = false,
  355. IsStart = false,
  356. IsCompleted = true
  357. };
  358. }
  359. };
  360. examStrategys.Add(checkStartTime);
  361. return startExamViewResponse;
  362. }
  363. }
  364. private StartExamViewResponse AddCheckValidateTimeStrategy(ExamUserExam examUserExam, ExamManage examManage, StartExamViewResponse startExamViewResponse, List<IExamStrategy> examStrategys)
  365. {
  366. if (examManage.ExamType == Share.Enums.Exams.EExamType.Simulate) return startExamViewResponse;
  367. var checkStartTime = new CheckValidateTimeStrategy(examManage.TimeSpan, examUserExam.StartTime)
  368. {
  369. CallBack = () =>
  370. {
  371. startExamViewResponse = new StartExamViewResponse
  372. {
  373. IsJoin = false,
  374. IsStart = false,
  375. IsCompleted = true
  376. };
  377. }
  378. };
  379. examStrategys.Add(checkStartTime);
  380. return startExamViewResponse;
  381. }
  382. private StartExamViewResponse AddCheckEndTimeStrategy(ExamUserExam examUserExam, ExamManage examManage, StartExamViewResponse startExamViewResponse, List<IExamStrategy> examStrategys)
  383. {
  384. if (examManage.ExamType == Share.Enums.Exams.EExamType.Simulate) return startExamViewResponse;
  385. var checkStartTime = new CheckEndTimeStrategy(examManage.EndTime, DateTime.Now)
  386. {
  387. CallBack = () =>
  388. {
  389. startExamViewResponse = new StartExamViewResponse
  390. {
  391. IsJoin = false,
  392. IsStart = false,
  393. IsCompleted = true
  394. };
  395. }
  396. };
  397. examStrategys.Add(checkStartTime);
  398. return startExamViewResponse;
  399. }
  400. private static StartExamViewResponse AddCheckStartTimeStrategy(ExamUserExam examUserExam, ExamManage examManage, StartExamViewResponse startExamViewResponse, List<IExamStrategy> examStrategys)
  401. {
  402. if (examManage.ExamType == Share.Enums.Exams.EExamType.Simulate) return startExamViewResponse;
  403. var checkStartTime = new CheckStartTimeStrategy(examManage.StartTime, examUserExam.StartTime)
  404. {
  405. CallBack = () =>
  406. {
  407. startExamViewResponse = new StartExamViewResponse
  408. {
  409. IsJoin = false,
  410. IsStart = false,
  411. IsCompleted = false
  412. };
  413. }
  414. };
  415. examStrategys.Add(checkStartTime);
  416. return startExamViewResponse;
  417. }
  418. public async Task CompleteGradingAsync(GradingExamDto gradingExtamDto, CancellationToken cancellationToken)
  419. {
  420. var userExam = await _repository.GetAsync(x => x.Id == gradingExtamDto.Id);
  421. if (userExam == null) return;
  422. var userExamItems = await _userExamItemRepository.Queryable().Where(x => x.UserExamId == gradingExtamDto.Id).ToListAsync();
  423. if (userExamItems != null)
  424. {
  425. var totalScore = userExamItems.Sum(x => x.Score);
  426. userExam.Score = totalScore;
  427. var examManage = await new ExamRepository<ExamManage>(_uow, _dataPermissionFilterBuilder, _serviceProvider).GetAsync(x => x.Id == userExam.ExamId);
  428. userExam.IsSuccess = totalScore >= examManage.CutoffScore;
  429. userExam.ExamStatus = Share.Enums.Exams.EExamStatus.Complete;
  430. userExam.ToUpdate(_sessionContext);
  431. await _repository.UpdateWithValidateAsync(userExam, cancellationToken);
  432. }
  433. }
  434. public async Task<List<GradingExamQuestionDto>> GetGradingExamQuestion(GradingExamRequest gradingExamRequest)
  435. {
  436. var expression = gradingExamRequest.GetExpression();
  437. var userExamTable = _repository.Queryable().Where(expression);
  438. var questionScoreRepository = new ExamRepository<ExamQuestionScoreBak>(_uow, _dataPermissionFilterBuilder, _serviceProvider);
  439. var userExamItemTable = _userExamItemRepository.Queryable();
  440. var userExamItemOptionTable = _userExamItemOptionRepository.Queryable();
  441. var examAnswerTable = new ExamRepository<ExamAnswer>(_uow, _dataPermissionFilterBuilder, _serviceProvider).Queryable();
  442. var questionTable = new ExamRepository<Exams.ExamManages.ExamQuestionBak>(_uow, _dataPermissionFilterBuilder, _serviceProvider).Queryable();
  443. var quesitonOptionTable = new ExamRepository<ExamQuestionOptionsBak>(_uow, _dataPermissionFilterBuilder, _serviceProvider).Queryable();
  444. var testPaperItemAnswerTable = new ExamRepository<ExamQuestionAnswerBak>(_uow, _dataPermissionFilterBuilder, _serviceProvider).Queryable();
  445. var questionScoreTable = questionScoreRepository.Queryable();
  446. var queryable = userExamTable.InnerJoin(userExamItemTable, (e, i) => e.Id == i.UserExamId)
  447. .InnerJoin(questionTable, (e, i, q) => i.QuestionId == q.QuestionId)
  448. .LeftJoin(userExamItemOptionTable, (e, i, q, o) => i.Id == o.UserExamItemId)
  449. .LeftJoin(quesitonOptionTable, (e, i, q, o, qo) => o.QuestionOptionId == qo.Id)
  450. .LeftJoin(examAnswerTable, (e, i, q, o, qo, a) => i.Id == a.UserExamItemId)
  451. .LeftJoin(testPaperItemAnswerTable, (e, i, q, o, qo, a, ta) => ta.QuestionId == qo.QuestionId)
  452. .InnerJoin(questionScoreTable, (e, i, q, o, qo, a, ta, s) => q.QuestionType == s.QuestionType && e.ExamId == s.ExamManageId)
  453. .Where((e, i, q, o, qo, a, ta, s) => !(q.QuestionType == EQuestionType.Single || q.QuestionType == EQuestionType.Multi || q.QuestionType == EQuestionType.Judge))
  454. .Select(
  455. (e, i, q, o, qo, a, ta, s) => new GradingExamQuestionTempDto
  456. {
  457. Id = i.Id,
  458. QuestionType = q.QuestionType,
  459. CorrectAnswer = ta.Id != null ? ta.Answer : string.Empty,
  460. Answer = a.Id != null ? a.Answer : string.Empty,
  461. Title = q.Title,
  462. QuestionOptionId = o.Id,
  463. UserExamItemId = i.Id,
  464. Content = qo.Content,
  465. Label = qo.Label,
  466. IsAnswer = qo.IsAnswer,
  467. IsSelected = o.Id != null,
  468. Score = s.Score
  469. }
  470. );
  471. var queryResult = await queryable.ToListAsync();
  472. var gradingExamQuestionDtos = queryResult.GroupBy(x => new
  473. {
  474. Id = x.Id,
  475. QuestionType = x.QuestionType
  476. }).Select(g => new GradingExamQuestionDto
  477. {
  478. Answer = g.FirstOrDefault().Answer,
  479. QuestionType = g.Key.QuestionType,
  480. Id = g.Key.Id,
  481. Score = g.FirstOrDefault().Score,
  482. Title = g.FirstOrDefault().Title,
  483. CorrectAnswer = g.Key.QuestionType.CheckSelectType() ? string.Join(",", g.Where(i => i.IsAnswer).Select(n => n.Label).Distinct()) : g.FirstOrDefault()?.CorrectAnswer
  484. }).ToList();
  485. return gradingExamQuestionDtos;
  486. }
  487. public async Task<GradingExamQuestionDto> ViewGradingExamQuestion(ViewGradingExamRequest viewGradingExamRequest)
  488. {
  489. var gradingExtamItemDto = _mapper.Map<ViewGradingExamRequest, GradingExamItemDto>(viewGradingExamRequest);
  490. return await GetNextExamQuestion(gradingExtamItemDto);
  491. }
  492. public async Task<UnExamUserPageViewResponse> GetUnExamUsers(UnExamUserReportPagedRequest unExamUserReportPagedRequest)
  493. {
  494. unExamUserReportPagedRequest.ResoleEndTime();
  495. var examManageRepository = new ExamRepository<ExamManage>(_uow, _dataPermissionFilterBuilder, _serviceProvider);
  496. var userRepository = new ExamRepository<User>(_uow, _dataPermissionFilterBuilder, _serviceProvider);
  497. var expression = unExamUserReportPagedRequest.GetExpression();
  498. var userExamExpression = unExamUserReportPagedRequest.GetUserExamExpression();
  499. var examManageTable = examManageRepository.Queryable().Where(expression);
  500. var userTable = userRepository.Queryable();
  501. var userExamTable = _repository.Queryable().Where(userExamExpression);
  502. var queryResult = userExamTable.InnerJoin(examManageTable, (ue, e) => ue.ExamId == e.Id)
  503. .InnerJoin(userTable, (ue, e, u) => ue.UserId == u.Id)
  504. .Select((ue, e, u) => new UnExamUserViewResponse
  505. {
  506. ExamName = e.Name,
  507. OrgName = u.Organization.Name,
  508. UserName = u.Name
  509. });
  510. var total = await queryResult.CountAsync();
  511. var items = await queryResult.ToPageListAsync(unExamUserReportPagedRequest.PageIndex, unExamUserReportPagedRequest.PageSize);
  512. return new UnExamUserPageViewResponse
  513. {
  514. Items = items,
  515. Pagination = new Pagination(unExamUserReportPagedRequest.PageIndex, unExamUserReportPagedRequest.PageSize, total)
  516. };
  517. }
  518. public async Task<UserExamResultPageViewResponse> GetUserExamResults(UserExamResultReportPagedRequest userExamResultReportPagedRequest)
  519. {
  520. userExamResultReportPagedRequest.ResoleEndTime();
  521. var examManageRepository = new ExamRepository<ExamManage>(_uow, _dataPermissionFilterBuilder, _serviceProvider);
  522. var userRepository = new ExamRepository<User>(_uow, _dataPermissionFilterBuilder, _serviceProvider);
  523. var expression = userExamResultReportPagedRequest.GetExpression();
  524. var userExamExpression = userExamResultReportPagedRequest.GetUserExamExpression();
  525. var examManageTable = examManageRepository.Queryable().Where(expression);
  526. var userTable = userRepository.Queryable();
  527. var userExamTable = _repository.Queryable().Where(userExamExpression);
  528. var queryResult = userExamTable.InnerJoin(examManageTable, (ue, e) => ue.ExamId == e.Id)
  529. .InnerJoin(userTable, (ue, e, u) => ue.UserId == u.Id)
  530. .Select((ue, e, u) => new UserExamResultViewResponse
  531. {
  532. ExamName = e.Name,
  533. OrgName = u.Organization.Name,
  534. UserName = u.Name,
  535. TotalScore = e.TotalScore,
  536. CutoffScore = e.CutoffScore,
  537. Score = ue.Score ?? 0,
  538. });
  539. var total = await queryResult.CountAsync();
  540. var items = await queryResult.ToPageListAsync(userExamResultReportPagedRequest.PageIndex, userExamResultReportPagedRequest.PageSize);
  541. return new UserExamResultPageViewResponse
  542. {
  543. Items = items,
  544. Pagination = new Pagination(userExamResultReportPagedRequest.PageIndex, userExamResultReportPagedRequest.PageSize, total)
  545. };
  546. }
  547. public async Task<GradingResultPageViewResponse> GetGradingResultPagedList(GradingPagedRequest gradingPagedRequest)
  548. {
  549. // 只要有阅卷记录就在已阅卷列表中,已阅卷和未阅卷会有重复数据,只有所有记录都已阅卷才会从未阅卷列表中排除
  550. var userExamTable = _repository.Queryable().WhereIF(gradingPagedRequest.IsCheck!=null, x => x.IsCheck == gradingPagedRequest.IsCheck && x.IsSubmit);
  551. var examManageTable = new ExamRepository<ExamManage>(_uow, _dataPermissionFilterBuilder, _serviceProvider).Queryable();
  552. var queryable = userExamTable.InnerJoin(examManageTable, (u, e) => u.ExamId == e.Id).GroupBy((u, e) => new
  553. {
  554. ExamName = e.Name,
  555. ExamCode = e.Code,
  556. CutoffScore = e.CutoffScore,
  557. TotalScore = e.TotalScore,
  558. Id = e.Id,
  559. Status = e.Status,
  560. Remark = e.Remark
  561. }).Select((u, e) => new GradingResultViewResponse
  562. {
  563. CutoffScore = e.CutoffScore,
  564. TotalScore = e.TotalScore,
  565. ExamName = e.Name,
  566. ExamCode = e.Code,
  567. IsCheck = SqlFunc.Subqueryable<ExamUserExam>().Where(x=>x.ExamId == e.Id && x.IsCheck).Any(),
  568. Id = e.Id,
  569. Remark = e.Remark
  570. });
  571. var list = await queryable.ToPageListAsync(gradingPagedRequest.PageIndex, gradingPagedRequest.PageSize);
  572. var total = await queryable.CountAsync();
  573. var result = new GradingResultPageViewResponse
  574. {
  575. Items = list,
  576. Pagination = new Pagination(gradingPagedRequest.PageIndex, gradingPagedRequest.PageSize, total)
  577. };
  578. return result;
  579. }
  580. public async Task BatchGradingAsync(BatchGradingExamItemDto batchGradingExamItemDto, CancellationToken cancellationToken)
  581. {
  582. var userExamItemIds = batchGradingExamItemDto.Items.Select(x => x.UserExamItemId);
  583. var userExamItems = await _userExamItemRepository.Queryable().Where(m => userExamItemIds.Contains(m.Id)).ToListAsync();
  584. if (userExamItems != null && userExamItemIds.Any())
  585. {
  586. userExamItems = _mapper.Map<List<GradingExamItemDto>, List<ExamUserExamItem>>(batchGradingExamItemDto.Items, userExamItems);
  587. await _userExamItemRepository.UpdateWithValidateAsync(userExamItems, cancellationToken);
  588. }
  589. }
  590. public async Task<List<ExamUserViewResponse>> GetUserListAsync(ExamUserQueryRequest examUserQueryRequest)
  591. {
  592. var userExamTable = _repository.Queryable().Where(x => x.ExamId == examUserQueryRequest.ExamId);
  593. var queryable = await userExamTable.InnerJoin<User>((ux, u) => ux.UserId == u.Id).Select((ux,u) => new ExamUserViewResponse
  594. {
  595. ExamId = ux.ExamId,
  596. UserId = ux.UserId,
  597. UserName = u.Name,
  598. Id = ux.Id
  599. }).ToListAsync();
  600. return queryable;
  601. }
  602. #endregion
  603. #region private method
  604. private async Task CalcuteExamItemScore(IUserExamItemRepository userExamRepository, UpdateUserExamItemDto addUserExamItemDto, CancellationToken cancellationToken)
  605. {
  606. if (!addUserExamItemDto.QuestionType.CheckSelectType()) return;
  607. var testPaperItemOptionsRepository = new ExamRepository<ExamQuestionOptionsBak>(_uow, _dataPermissionFilterBuilder, _serviceProvider);
  608. var examManageRepository = new ExamRepository<ExamManage>(_uow, _dataPermissionFilterBuilder, _serviceProvider);
  609. var testPaperItemRepository = new ExamRepository<Exams.ExamManages.ExamQuestionBak>(_uow, _dataPermissionFilterBuilder, _serviceProvider);
  610. var examQuestionScoreRepository = new ExamRepository<ExamQuestionScoreBak>(_uow, _dataPermissionFilterBuilder, _serviceProvider);
  611. var testPaperOptionsTable = testPaperItemOptionsRepository.Queryable().Where(x => x.QuestionId == addUserExamItemDto.QuestionId && x.IsAnswer);
  612. var testPaperItemTable = testPaperItemRepository.Queryable();
  613. var userExamTable = _repository.Queryable().Where(x => x.Id == addUserExamItemDto.UserExamId);
  614. var examManageTable = examManageRepository.Queryable();
  615. var testPaperOptionIds = await testPaperOptionsTable.InnerJoin(testPaperItemTable, (t, i) => t.ExamQuestionId == i.Id)
  616. .InnerJoin(examManageTable, (t, i, e) => i.ExamId == e.Id)
  617. .InnerJoin(userExamTable, (t, i, e, u) => e.Id == u.ExamId)
  618. .Select((t, i, e, u) => t.Id).ToListAsync();
  619. var isCorrect = addUserExamItemDto.UserExamItemOptionDtos.Select(x => x.QuestionOptionId).OrderBy(x => x).SequenceEqual(testPaperOptionIds.OrderBy(x => x));
  620. var userExamItem = await userExamRepository.GetAsync(x => x.UserExamId == addUserExamItemDto.UserExamId && x.QuestionId == addUserExamItemDto.QuestionId);
  621. var examQuesiontScores = await examQuestionScoreRepository.Queryable().Where(x => x.QuestionType == addUserExamItemDto.QuestionType)
  622. .InnerJoin(userExamTable, (e, u) => e.Id == u.ExamId)
  623. .Select((e, u) => e).ToListAsync();
  624. userExamItem.IsCheck = true;
  625. userExamItem.Score = isCorrect ? examQuesiontScores.FirstOrDefault()?.Score : 0;
  626. userExamItem.ToUpdate(_sessionContext);
  627. await userExamRepository.UpdateWithValidateAsync(userExamItem, cancellationToken);
  628. }
  629. private async Task AddExamAsync(IRepository<ExamUserExamItem> userExamItemRepository, AddUserExamItemDto addUserExamItemDto, CancellationToken cancellationToken)
  630. {
  631. var userExamItem = await AddUserExamItem(addUserExamItemDto, cancellationToken);
  632. userExamItem.UserExamItemOptionses = await AddUserExamItemOptions(addUserExamItemDto, cancellationToken);
  633. userExamItem.ExamAnswers = await AddExamAnswer(addUserExamItemDto, userExamItem.Id, cancellationToken);
  634. await userExamItemRepository.AddNav(userExamItem)
  635. .Include(x => x.UserExamItemOptionses)
  636. .Include(x => x.ExamAnswers)
  637. .ExecuteCommandAsync();
  638. }
  639. private async Task UpdateExamAsync(IRepository<ExamUserExamItem> userExamItemRepository, UpdateUserExamItemDto updateUserExamItemDto, CancellationToken cancellationToken)
  640. {
  641. var userExamItem = await UpdateUserExamItem(updateUserExamItemDto, cancellationToken);
  642. userExamItem.UserExamItemOptionses = await ModifyUserItemOptions(updateUserExamItemDto, cancellationToken);
  643. userExamItem.ExamAnswers = await UpdateExamAnswer(updateUserExamItemDto, cancellationToken);
  644. await userExamItemRepository.UpdateNav(userExamItem)
  645. .Include(x => x.UserExamItemOptionses)
  646. .Include(x => x.ExamAnswers)
  647. .ExecuteCommandAsync();
  648. }
  649. private async Task<GradingExamQuestionDto> GetNextExamQuestion(GradingExamItemDto gradingExtamItemDto)
  650. {
  651. // TODO: 获取未阅卷的第一道题
  652. var current = _userExamItemRepository.Queryable().Where(x => x.Id == gradingExtamItemDto.UserExamItemId);
  653. var userExamItemTable = _userExamItemRepository.Queryable().Where(x => !x.IsCheck);
  654. var userExamItem = current.InnerJoin(userExamItemTable, (c, u) => c.UserExamId == u.UserExamId).OrderBy((c, u) => c.SortIndex).First();
  655. if (userExamItem != null)
  656. {
  657. var testPaperItem = new ExamRepository<Exams.ExamManages.ExamQuestionBak>(_uow, _dataPermissionFilterBuilder, _serviceProvider).Queryable().Where(x => x.Id == userExamItem.Id && !x.QuestionType.CheckSelectType()).First();
  658. if (testPaperItem == null) return null;
  659. var gradingExamQuestionDto = new GradingExamQuestionDto();
  660. gradingExamQuestionDto = _mapper.Map<Exams.ExamManages.ExamQuestionBak, GradingExamQuestionDto>(testPaperItem, gradingExamQuestionDto);
  661. var examAnswer = new ExamRepository<ExamAnswer>(_uow, _dataPermissionFilterBuilder, _serviceProvider).Queryable().Where(x => x.UserExamItemId == userExamItem.Id).First();
  662. var testPaperItemAnswer = await new ExamRepository<ExamQuestionAnswerBak>(_uow, _dataPermissionFilterBuilder, _serviceProvider).Queryable().FirstAsync(x => x.QuestionId == testPaperItem.QuestionId && x.ExamQuestionId == testPaperItem.Id);
  663. gradingExamQuestionDto.Answer = examAnswer.Answer ?? string.Empty;
  664. gradingExamQuestionDto.CorrectAnswer = testPaperItemAnswer != null ? testPaperItemAnswer.Answer ?? string.Empty : string.Empty;
  665. return gradingExamQuestionDto;
  666. }
  667. return null;
  668. }
  669. private async Task<List<ExamAnswer>> AddExamAnswer(AddUserExamItemDto addUserExamItemDto,string id, CancellationToken cancellationToken)
  670. {
  671. if (addUserExamItemDto.QuestionType.CheckSelectType()) return null;
  672. var examAnswers = new List<ExamAnswer>();
  673. var examAnswer = new ExamAnswer
  674. {
  675. UserId = _sessionContext.UserId,
  676. UserExamItemId = id,
  677. Answer = addUserExamItemDto.Answer
  678. };
  679. examAnswer.ToInsert(_sessionContext);
  680. await _examAnswerRepository.ValidateAddAsync(examAnswer, cancellationToken);
  681. return examAnswers;
  682. }
  683. private async Task<UserExamQuestionDto> GetNextExamQuestion(AddUserExamItemDto addUserExamItemDto)
  684. {
  685. // TODO: 获取未阅卷的第一道题
  686. var testPaperItemRepository = new ExamRepository<Exams.ExamManages.ExamQuestionBak>(_uow, _dataPermissionFilterBuilder, _serviceProvider);
  687. var examRepository = new ExamRepository<ExamManage>(_uow, _dataPermissionFilterBuilder, _serviceProvider);
  688. var userExamTable = _repository.Queryable().Where(x => x.Id == addUserExamItemDto.UserExamId);
  689. var userExamItemTable = _userExamItemRepository.Queryable().WhereIF(addUserExamItemDto.QuestionId.IsNotNullOrEmpty(), x => x.QuestionId == addUserExamItemDto.QuestionId);
  690. var examTable = examRepository.Queryable();
  691. var testPaperItemTable = testPaperItemRepository.Queryable();
  692. var current = examTable.InnerJoin(testPaperItemTable, (e, t) => e.Id == t.ExamId)
  693. .InnerJoin(userExamTable, (e, t, u) => e.Id == u.ExamId)
  694. .InnerJoin(userExamItemTable, (e, t, u, i) => t.QuestionId == i.QuestionId).Select((e, t, u, i) => t);
  695. var nextTable = testPaperItemTable.InnerJoin(current, (t, c) => t.SortIndex > c.SortIndex).OrderBy((t, c) => t.SortIndex).Select((t, c) => t);
  696. var userExamItem = userExamItemTable.InnerJoin(nextTable, (u, n) => u.QuestionId == n.QuestionId).OrderBy((u, n) => u.SortIndex).Select((u, n) => u).First();
  697. if (userExamItem != null)
  698. {
  699. var question = testPaperItemRepository.Queryable().Where(x => x.Id == userExamItem.Id).First();
  700. if (question == null) return null;
  701. var userExamQuestionDto = new UserExamQuestionDto();
  702. userExamQuestionDto = _mapper.Map<Exams.ExamManages.ExamQuestionBak, UserExamQuestionDto>(question, userExamQuestionDto);
  703. if (question.QuestionType.CheckSelectType())
  704. {
  705. var userExamItemOptionTable = _userExamItemOptionRepository.Queryable().Where(x => x.UserExamItemId == userExamItem.Id);
  706. var quesitonOptionTable = new ExamRepository<ExamQuestionOptionsBak>(_uow, _dataPermissionFilterBuilder, _serviceProvider).Queryable();
  707. var queryResult = userExamItemOptionTable.InnerJoin(quesitonOptionTable, (u, q) => u.QuestionOptionId == q.Id)
  708. .Select((u, q) => new UserExamItemOptionDto
  709. {
  710. Content = q.Content,
  711. QuestionOptionId = u.QuestionOptionId,
  712. UserExamItemId = u.UserExamItemId
  713. });
  714. userExamQuestionDto.UserExamItemOptionDtos = queryResult.ToList();
  715. }
  716. else
  717. {
  718. var examAnswer = new ExamRepository<ExamAnswer>(_uow, _dataPermissionFilterBuilder, _serviceProvider).Queryable().Where(x => x.UserExamItemId == userExamItem.Id).First();
  719. userExamQuestionDto.Answer = examAnswer.Answer ?? string.Empty;
  720. }
  721. return userExamQuestionDto;
  722. }
  723. else
  724. {
  725. return null;
  726. }
  727. }
  728. private async Task<List<ExamAnswer>> UpdateExamAnswer(UpdateUserExamItemDto updateUserExamItemDto, CancellationToken cancellationToken)
  729. {
  730. var examAnswerTable = _examAnswerRepository.Queryable();
  731. var userExamItemTable = _userExamItemRepository.Queryable().Where(x => x.Id == updateUserExamItemDto.Id);
  732. var examAnswer = await examAnswerTable.InnerJoin(userExamItemTable, (e, u) => e.UserExamItemId == u.Id).Select((e, u) => e).FirstAsync();
  733. if (!updateUserExamItemDto.QuestionType.CheckSelectType())
  734. {
  735. var examAnswers = new List<ExamAnswer>();
  736. if (examAnswer != null)
  737. {
  738. examAnswer.Answer = updateUserExamItemDto.Answer;
  739. examAnswer.UserId = _sessionContext.UserId;
  740. examAnswer.UserExamItemId = updateUserExamItemDto.Id;
  741. examAnswer.ToUpdate(_sessionContext);
  742. await _examAnswerRepository.UpdateWithValidateAsync(examAnswer, cancellationToken);
  743. examAnswers.Add(examAnswer);
  744. }
  745. else
  746. {
  747. examAnswer = new ExamAnswer
  748. {
  749. Answer = updateUserExamItemDto.Answer,
  750. UserId = _sessionContext.UserId,
  751. UserExamItemId = updateUserExamItemDto.Id
  752. };
  753. examAnswer.ToInsert(_sessionContext);
  754. await _examAnswerRepository.ValidateAddAsync(examAnswer, cancellationToken);
  755. examAnswers.Add(examAnswer);
  756. }
  757. return examAnswers;
  758. }
  759. return null;
  760. }
  761. private async Task<List<ExamUserExamItemOptions>> ModifyUserItemOptions(UpdateUserExamItemDto updateUserExamItemDto, CancellationToken cancellationToken)
  762. {
  763. if (updateUserExamItemDto.QuestionType.CheckSelectType())
  764. {
  765. var entityQuestionRequest = new EntityQueryRequest
  766. {
  767. Expression = ExpressionableUtility.CreateExpression<ExamUserExamItemOptions>()
  768. .AndIF(updateUserExamItemDto.Id.IsNotEmpty(), x => x.UserExamItemId == updateUserExamItemDto.Id).ToExpression()
  769. };
  770. await DeleteUserExamItemOptions(entityQuestionRequest, cancellationToken);
  771. //await UpdateUserItemOptions(updateUserExamItemDto, cancellationToken);
  772. var addUserExamItemDto = _mapper.Map<AddUserExamItemDto>(updateUserExamItemDto);
  773. addUserExamItemDto.UserExamItemOptionDtos = new List<AddUserExamItemOptionDto>();
  774. updateUserExamItemDto.UserExamItemOptionDtos.ForEach(item =>
  775. {
  776. addUserExamItemDto.UserExamItemOptionDtos.Add(_mapper.Map<AddUserExamItemOptionDto>(item));
  777. });
  778. return await AddUserExamItemOptions(addUserExamItemDto, cancellationToken);
  779. }
  780. return null;
  781. }
  782. private async Task UpdateUserItemOptions(UpdateUserExamItemDto updateUserExamItemDto, CancellationToken cancellationToken)
  783. {
  784. if (updateUserExamItemDto.QuestionType.CheckSelectType())
  785. {
  786. var userExamItemOptions = await _userExamItemOptionRepository.Queryable().Where(x => x.UserExamItemId == updateUserExamItemDto.Id).ToListAsync();
  787. var entities = new List<ExamUserExamItemOptions>();
  788. if (updateUserExamItemDto.UserExamItemOptionDtos != null)
  789. {
  790. updateUserExamItemDto.UserExamItemOptionDtos.Where(m => m.OperationStatus == EEOperationStatus.Update).ToList().ForEach(x =>
  791. {
  792. var entity = userExamItemOptions.FirstOrDefault(m => m.Id == x.Id);
  793. if (entity != null)
  794. {
  795. entities.Add(_mapper.Map<UpdateUserExamItemOptionDto, ExamUserExamItemOptions>(x, entity));
  796. }
  797. });
  798. }
  799. entities.ToUpdate(_sessionContext);
  800. await _userExamItemOptionRepository.UpdateWithValidateAsync(entities, cancellationToken);
  801. }
  802. }
  803. private async Task<ExamUserExamItem> UpdateUserExamItem(UpdateUserExamItemDto updateUserExamItemDto, CancellationToken cancellationToken)
  804. {
  805. var userExamItem = await _userExamItemRepository.GetAsync(x => x.UserExamId == updateUserExamItemDto.UserExamId && x.QuestionId == updateUserExamItemDto.QuestionId);
  806. userExamItem = _mapper.Map<UpdateUserExamItemDto, ExamUserExamItem>(updateUserExamItemDto, userExamItem);
  807. updateUserExamItemDto.Id = userExamItem.Id;
  808. userExamItem.ToUpdate(_sessionContext);
  809. await _userExamItemRepository.UpdateWithValidateAsync(userExamItem, cancellationToken);
  810. if (updateUserExamItemDto.QuestionType.CheckSelectType())
  811. {
  812. if (updateUserExamItemDto.UserExamItemOptionDtos != null)
  813. {
  814. updateUserExamItemDto.UserExamItemOptionDtos.ForEach(x => x.UserExamItemId = updateUserExamItemDto.Id);
  815. }
  816. }
  817. return userExamItem;
  818. }
  819. private async Task<List<ExamUserExamItemOptions>> AddUserExamItemOptions(AddUserExamItemDto addUserExamItemDto, CancellationToken cancellationToken)
  820. {
  821. var userExamItemOptions = new List<ExamUserExamItemOptions>();
  822. if (addUserExamItemDto.QuestionType.CheckSelectType())
  823. {
  824. if (addUserExamItemDto.UserExamItemOptionDtos != null)
  825. {
  826. addUserExamItemDto.UserExamItemOptionDtos.ToList().ForEach(x =>
  827. {
  828. userExamItemOptions.Add(_mapper.Map<ExamUserExamItemOptions>(x));
  829. });
  830. }
  831. }
  832. userExamItemOptions.ToInsert(_sessionContext);
  833. await _userExamItemOptionRepository.ValidateAddAsync(userExamItemOptions, cancellationToken);
  834. return userExamItemOptions;
  835. }
  836. private async Task<ExamUserExamItem> AddUserExamItem(AddUserExamItemDto addUserExamItemDto, CancellationToken cancellationToken)
  837. {
  838. var userExamItem = _mapper.Map<ExamUserExamItem>(addUserExamItemDto);
  839. userExamItem.ToInsert(_sessionContext);
  840. await _userExamItemRepository.ValidateAddAsync(userExamItem, cancellationToken);
  841. if (addUserExamItemDto.QuestionType.CheckSelectType())
  842. {
  843. if (addUserExamItemDto.UserExamItemOptionDtos != null)
  844. {
  845. addUserExamItemDto.UserExamItemOptionDtos.ForEach(x => x.UserExamItemId = userExamItem.Id);
  846. }
  847. }
  848. return userExamItem;
  849. }
  850. private async Task DeleteUserExamItemOptions(EntityQueryRequest entityQueryRequest, CancellationToken cancellationToken)
  851. {
  852. await _userExamItemOptionRepository.DeleteWithValidateAsync(entityQueryRequest, cancellationToken);
  853. }
  854. private SqlSugar.ISugarQueryable<UserExamResultViewResponse> GetQueryable(UserExamPagedRequest queryRequest)
  855. {
  856. if (_sessionContext.UserId != null)
  857. {
  858. queryRequest.UserId = _sessionContext.UserId;
  859. }
  860. var expression = queryRequest.GetExpression();
  861. var userExamTable = _repository.Queryable().Where(expression);
  862. var examManageExpression = queryRequest.GetExamManageExpression();
  863. var examManageTable = new ExamRepository<ExamManage>(_uow, _dataPermissionFilterBuilder, _serviceProvider).Queryable().Where(examManageExpression);
  864. var queryable = userExamTable.InnerJoin(examManageTable, (u, e) => u.ExamId == e.Id).Select((u, e) => new UserExamResultViewResponse
  865. {
  866. Id = u.Id,
  867. CutoffScore = e.CutoffScore,
  868. TotalScore = e.TotalScore,
  869. ExamName = e.Name,
  870. Score = u.Score ?? 0,
  871. Status = u.Status,
  872. SortIndex = u.SortIndex,
  873. ExamStatus = u.ExamStatus,
  874. IsSuccess = u.IsSuccess,
  875. EndTime = e.EndTime,
  876. StartTime = e.StartTime,
  877. TimeSpan = e.TimeSpan,
  878. ExamType = e.ExamType,
  879. ExamId = e.Id
  880. });
  881. return queryable;
  882. }
  883. #endregion
  884. }
  885. }