Example #1
0
        public async Task <IActionResult> OnPostUnlock(int puzzleId, int unlockId)
        {
            Puzzle puzzle = await(from puzz in _context.Puzzles
                                  where puzz.ID == puzzleId
                                  select puzz).FirstOrDefaultAsync();

            if (puzzle == null)
            {
                return(NotFound());
            }

            // Restrict this page to whistle stop non-puzzles
            if (puzzle.MinutesOfEventLockout == 0 || puzzle.IsPuzzle)
            {
                return(NotFound());
            }

            Team team = await UserEventHelper.GetTeamForPlayer(_context, Event, LoggedInUser);

            using (var transaction = _context.Database.BeginTransaction())
            {
                var puzzleStateQuery           = PuzzleStateHelper.GetFullReadOnlyQuery(_context, Event, null, team);
                PuzzleStatePerTeam prereqState = await(from pspt in puzzleStateQuery
                                                       where pspt.PuzzleID == puzzle.ID
                                                       select pspt).FirstOrDefaultAsync();
                if (prereqState == null)
                {
                    return(NotFound());
                }

                // Only move forward if the prereq is open and unsolved
                if (prereqState.UnlockedTime == null || prereqState.SolvedTime != null)
                {
                    return(NotFound("Your team has already chosen and can't choose again"));
                }

                PuzzleStatePerTeam unlockState = await(from pspt in puzzleStateQuery
                                                       where pspt.PuzzleID == unlockId
                                                       select pspt).FirstOrDefaultAsync();
                if (unlockState == null)
                {
                    return(NotFound());
                }

                // The chosen puzzle must be locked (and unsolved)
                if (unlockState.UnlockedTime != null || unlockState.SolvedTime != null)
                {
                    return(NotFound("You've already chosen this puzzle"));
                }

                // Ensure the puzzle is actually one of the unlock options
                Prerequisites prereq = await(from pre in _context.Prerequisites
                                             where pre.PrerequisiteID == puzzleId && pre.PuzzleID == unlockId
                                             select pre).FirstOrDefaultAsync();
                if (prereq == null)
                {
                    return(NotFound());
                }

                await PuzzleStateHelper.SetSolveStateAsync(_context, Event, puzzle, team, DateTime.UtcNow);

                await PuzzleStateHelper.SetUnlockStateAsync(_context, Event, unlockState.Puzzle, team, DateTime.UtcNow);

                transaction.Commit();
            }

            Puzzle puzzleToUnlock = await(from p in _context.Puzzles
                                          where p.ID == unlockId
                                          select p).FirstOrDefaultAsync();

            string puzzleUrl;

            if (puzzleToUnlock.CustomURL != null)
            {
                puzzleUrl = PuzzleHelper.GetFormattedUrl(puzzleToUnlock, Event.ID);
            }
            else
            {
                puzzleUrl = puzzleToUnlock.PuzzleFile.UrlString;
            }

            return(Redirect(puzzleUrl));
        }