public async Task <RequestResponseModel <TicketViewModel> > AddTicketAsync(TicketWriteModel ticket) { var validationResults = await _ticketValidator.ValidateTicketBeforeSavingAsync(ticket); if (validationResults.Any()) { return(new RequestResponseModel <TicketViewModel>(StatusCodes.Status400BadRequest, validationResults, null)); } var createdTicket = await SaveTicketAsync(ticket); if (createdTicket == null) { return(new RequestResponseModel <TicketViewModel>(StatusCodes.Status400BadRequest, new List <ErrorViewModel> { ErrorViewModel.Factory.NewErrorFromMessage(_localizer["TicketNotCreatedErrorMessage"] .Value) }, null)); } var result = await _ticketValidator.PrepareResponseTicketAsync(createdTicket); return(new RequestResponseModel <TicketViewModel>(StatusCodes.Status201Created, Enumerable.Empty <ErrorViewModel>(), result)); }
private IEnumerable <int> SearchForDuplicatedEventsOnATicket(TicketWriteModel ticket) => ticket.Events .GroupBy(g => g.GameId) .Where(g => g.Count() > 1) .Select(g => g.Key) .ToList() .GetEmptyIfNull();
private void ValidateTicketEvents(TicketWriteModel ticket, ICollection <ErrorViewModel> errors) { var doesContainEvents = CheckDoesTicketContainEvents(ticket); if (!doesContainEvents) { errors.Add(ErrorViewModel.Factory.NewErrorFromMessage(_localizer["LackOfEventsErrorMessage"] .Value)); } }
private async Task <bool> CheckHasUserPlayedAnyOfGamesBeforeAsync(TicketWriteModel ticket) { var gameIds = ticket.Events.Select(e => e.GameId); var userTickets = await _ticketRepository.GetUserTicketsAsync(ticket.UserId); var playedGames = userTickets.SelectMany(t => t.Events); var isTicketInvalid = playedGames.Any(g => gameIds.Contains(g.GameId)); return(isTicketInvalid); }
private async Task ValidateTicketInRespectOfPreviousUserGamesAsync(TicketWriteModel ticket, ICollection <ErrorViewModel> errors) { var isTicketInvalid = await CheckHasUserPlayedAnyOfGamesBeforeAsync(ticket); if (isTicketInvalid) { errors.Add(ErrorViewModel.Factory.NewErrorFromMessage(_localizer["EventsRepeatedByUserErrorMessage"] .Value)); } }
private async Task ValidateUserAccountBeforeCreatingTicketAsync(TicketWriteModel ticketModel, ICollection <ErrorViewModel> errors) { var isAffordable = await CheckIsTicketAffordableByUserAsync(ticketModel); if (!isAffordable) { errors.Add(ErrorViewModel.Factory.NewErrorFromMessage(_localizer["TicketNotAffordableErrorMessage"] .Value)); } }
private void ValidateTicketStake(TicketWriteModel ticket, ICollection <ErrorViewModel> errors) { var isStakeCorrect = CheckIsStakeCorrect(ticket); if (!isStakeCorrect) { errors.Add(ErrorViewModel.Factory.NewErrorFromMessage(_localizer["IncorrectStakeErrorMessage"] .Value)); } }
private async Task CheckDoTicketGamesExistAsync(TicketWriteModel ticketModel, ICollection <ErrorViewModel> errors) { var incorrectGameIds = (await SearchForIncorrectGamesAsync(ticketModel)) .ToList(); if (incorrectGameIds.Any()) { errors.Add(ErrorViewModel.Factory.NewErrorFromMessage(_localizer["TicketContainingIncorrectGamesErrorMessage", string.Join(';', incorrectGameIds)] .Value)); } }
private void ValidateTicketInRespectOfDuplications(TicketWriteModel ticket, ICollection <ErrorViewModel> errors) { var duplicatedGameIds = SearchForDuplicatedEventsOnATicket(ticket) .ToList(); if (duplicatedGameIds.Any()) { errors.Add(ErrorViewModel.Factory.NewErrorFromMessage(_localizer["TicketContainsDuplicatesErrorMessage", string.Join(';', duplicatedGameIds)] .Value)); } }
private async Task <IEnumerable <int> > SearchForIncorrectGamesAsync(TicketWriteModel ticketModel) { var gameIds = ticketModel.Events.Select(e => e.GameId) .ToList(); var storedGamesIds = (await _gameRepository.GetGamesByBunchOfIdsAsync(gameIds)) .Select(g => g.GameId); var incorrectGameIds = gameIds .Where(g => !storedGamesIds .Contains(g)) .ToList(); return(incorrectGameIds); }
private async Task <TicketEntity> SaveTicketAsync(TicketWriteModel ticket) { var ticketEntity = (TicketEntity)ticket; await FindEventsRatesAsync(ticketEntity); await FindEventResultsAsync(ticketEntity.Events); await ReduceUserAccountBalanceAsync(ticket.UserId, ticket.Stake); var createdTicket = await _ticketRepository.AddTicketAsync(ticketEntity); await _ticketRepository.SaveChangesAsync(); return(createdTicket); }
public async Task <ActionResult <TicketViewModel> > CreateTicketAsync([FromBody] TicketWriteModel ticket) { try { var response = await _ticketService.AddTicketAsync(ticket); return(response.StatusCode == StatusCodes.Status201Created ? CreatedAtAction(nameof(GetTicketById), new { ticketId = response.Result.TicketId }, response.Result) : StatusCode(response.StatusCode, response.Errors)); } catch (Exception ex) { _logger.LogError(ex, string.Empty); return(StatusCode(StatusCodes.Status500InternalServerError, ErrorViewModel.Factory.NewErrorFromException(ex))); } }
public async Task <ICollection <ErrorViewModel> > ValidateTicketBeforeSavingAsync(TicketWriteModel ticket) { var errors = new List <ErrorViewModel>(); ValidateTicketEvents(ticket, errors); ValidateTicketInRespectOfDuplications(ticket, errors); ValidateTicketStake(ticket, errors); var doesExist = await CheckDoesUserExistAsync(ticket.UserId); if (!doesExist) { errors.Add(ErrorViewModel.Factory.NewErrorFromMessage(_localizer["UserNotFoundErrorMessage", ticket.UserId] .Value)); return(errors); } await CheckDoTicketGamesExistAsync(ticket, errors); await ValidateUserAccountBeforeCreatingTicketAsync(ticket, errors); await ValidateTicketInRespectOfPreviousUserGamesAsync(ticket, errors); return(errors); }
private async Task <bool> CheckIsTicketAffordableByUserAsync(TicketWriteModel ticketModel) { var user = await _userRepository.GetUserByIdAsync(ticketModel.UserId, false, false); return(user.AccountBalance >= ticketModel.Stake); }
private static bool CheckIsStakeCorrect(TicketWriteModel ticket) => ticket.Stake >= TicketConstants.MinimumStake && ticket.Stake <= TicketConstants.MaximumStake;
private static bool CheckDoesTicketContainEvents(TicketWriteModel ticket) => ticket.Events.GetEmptyIfNull().Any();