public async Task <IActionResult> SetNewPassword(Guid token, [FromBody] ValidatedChangeUserPasswordModel user) { var existingToken = await _context.Accounts.FromSqlInterpolated($"SELECT * FROM accounts WHERE recover_password_token = UNHEX(REPLACE({token}, {"-"}, {""}))").ToListAsync(); if (existingToken.Count > 0) { // token was found, get user id and change their password var existingUser = await _context.Users.FirstOrDefaultAsync(u => u.Id == existingToken[0].UserId); if (existingUser != null) { string salt = _authenticationService.GenerateSalt(); string hash = _authenticationService.HashPassword(user.UserPassword, salt); existingUser.UserPasswordHash = hash; existingUser.UserPasswordSalt = salt; _context.Entry(existingUser).State = EntityState.Modified; // invalidate token, now that the password has changed var accountEntry = await _context.Accounts.FirstOrDefaultAsync(a => a.UserId == existingUser.Id); if (accountEntry != null) { accountEntry.RecoverPasswordToken = null; _context.Entry(accountEntry).State = EntityState.Modified; } await _context.SaveChangesAsync(); var origin = Request.Headers["Origin"]; var forgotPasswordLink = $@"{origin}/forgot_password"; var emailBody = $@"Hi {existingUser.UserName}, Your password has been reset @HairdressingProject Admin Portal. If you have not made this request, please contact us or navigate to the page below to reset it again: {forgotPasswordLink} Regards, HairdressingProject Admin. "; try { _emailService.SendEmail(existingUser.UserEmail, existingUser.UserName, "Password successfully reset", emailBody); return(NoContent()); } catch (Exception ex) { Console.WriteLine("Failed to send email:"); Console.WriteLine(ex); return(StatusCode(StatusCodes.Status500InternalServerError, new { errors = new { Email = new string[] { ex.Message } } })); } } return(NotFound(new { errors = new { Token = new string[] { "User not found" } }, status = 404 })); } return(NotFound(new { errors = new { Token = new string[] { "Token not found" } }, status = 404 })); }
public async Task <IActionResult> SetNewPassword(ulong id, [FromBody] ValidatedChangeUserPasswordModel user) { if (!_authorizationService.ValidateJWTToken(Request)) { return(Unauthorized(new { errors = new { Token = new string[] { "Invalid token" } }, status = 401 })); } if (id != user.Id) { return(BadRequest(new { errors = new { Id = new string[] { "ID sent does not match the one in the endpoint" } }, status = 400 })); } var userMod = await _context.Users.FirstOrDefaultAsync(u => u.Id == id); if (userMod == null) { return(NotFound(new { errors = new { Id = new string[] { "User not found" } }, status = 404 })); } // hash + salt new password string salt = _authenticationService.GenerateSalt(); string hash = _authenticationService.HashPassword(user.UserPassword, salt); userMod.UserPasswordHash = hash; userMod.UserPasswordSalt = salt; _context.Entry(userMod).State = EntityState.Modified; try { await _context.SaveChangesAsync(); } catch (DbUpdateConcurrencyException) { if (!UsersExists(id)) { return(NotFound()); } else { throw; } } return(NoContent()); }