public async Task <String> LoginAsync([Required] LoginParams parameters) { var player = await _repository.Players.FirstAsync(x => x.Username == parameters.Username); if (player != null && PasswordHelper.CheckHash(parameters.Password, player.PasswordHash, player.PasswordSalt)) { // The player's username and password are correct. We need to create a session token (security) // that we will send the to the player so when he/she communicates later on with the API // we will know who he or she is. var randomBytes = new Byte[20]; using (var rng = new RNGCryptoServiceProvider()) { rng.GetBytes(randomBytes); } var currentTime = DateTime.UtcNow; var session = new Session { Token = Convert.ToBase64String(randomBytes), Created = currentTime, LastActivity = currentTime, PlayerId = player.Id }; // Check if user with that id already have a session. // To avoid duplication of session autentication token. var duplication = await _repository.Sessions.FirstOrDefaultAsync(x => x.Player.Id == player.Id); // Check if the player that wants to login have session, let him login again. // Update session token, created and last activity properties. // If the player is different, redirect to login page. // Check that the session token and player id properties are not in the database. // If there is a player with the found id if (duplication != null) { throw new SystemException("This player already have a session."); } _repository.Sessions.Add(session); await _repository.SaveChangesAsync(); // Returns the token of the logged user // This way we will know who makes the requests return(session.Token); } // Authentication failed, return null as to the specification return(null); }
public IActionResult Login([FromBody] LoginCredentials loginCredentials) { // List of messages to return to the client var messages = new List <Message>(); // Input validation if (loginCredentials.LoginApplicationName == null) { messages.Add(new Message(MessageTypeEnum.Error, 1001, new List <string>())); } if (loginCredentials.Username == null) { messages.Add(new Message(MessageTypeEnum.Error, 1002, new List <string>())); } if (loginCredentials.Password == null) { messages.Add(new Message(MessageTypeEnum.Error, 1003, new List <string>())); } if (messages.Count != 0) { return(BadRequest(messages)); } // Get application var applicationRepository = new ApplicationRepository(context); var applicationModel = applicationRepository.GetByLoginApplicationName(loginCredentials.LoginApplicationName); if (applicationModel == null) { messages.Add(new Message(MessageTypeEnum.Error, 1004, new List <string>())); return(BadRequest(messages)); } // Get user var userRepository = new UserRepository(context); var user = userRepository.GetByApplicationIdAndUsername(applicationModel.Id, loginCredentials.Username); // User not found or password not correct if (user == null || !PasswordHelper.CheckHash(user.PasswordSalt, loginCredentials.Password, user.PasswordHash)) { messages.Add(new Message(MessageTypeEnum.Error, 1005, new List <string>() { loginCredentials.LoginApplicationName, loginCredentials.Username })); return(BadRequest(messages)); } // Login credentials are valid, create JWT token var claims = new[] { new Claim(Constants.JWTClaimUserId, user.Id.ToString()), new Claim(Constants.JWTClaimApplicationId, user.ApplicationId.ToString()), new Claim(JwtRegisteredClaimNames.Jti, Guid.NewGuid().ToString()) }; var token = new JwtSecurityToken ( issuer: configuration["TokenAuthentication:Issuer"], audience: configuration["TokenAuthentication:Audience"], claims: claims, expires: DateTime.UtcNow.AddMinutes(60), notBefore: DateTime.UtcNow, signingCredentials: new SigningCredentials(new SymmetricSecurityKey(Encoding.UTF8.GetBytes(configuration["TokenAuthentication:SecretKey"])), SecurityAlgorithms.HmacSha256) ); return(Ok(new { Value = new JwtSecurityTokenHandler().WriteToken(token) })); }