public async Task <Result <SignInResponse> > SignInAsync(string username, string password, Uri returnUrl) { if (string.IsNullOrWhiteSpace(username) || string.IsNullOrWhiteSpace(password)) { return(Result.Failure <SignInResponse>(LoginUserErrors.UserNameOrPasswordIncorrect())); } var user = await _userManager.FindByNameAsync(username); if (user is null) { return(Result.Failure <SignInResponse>(LoginUserErrors.UserNameOrPasswordIncorrect())); } var context = await _interaction.GetAuthorizationContextAsync(returnUrl?.ToString()); var isUserValidResult = await ValidateUserCredentialsAsync(user, password); if (!isUserValidResult.IsSuccess) { await _eventService.RaiseAsync(new UserLoginFailureEvent(user.UserName, ValidateUserMessage, clientId : context?.ClientId)); return(Result.Failure <SignInResponse>(isUserValidResult.Errors)); } var isUserDisabledResult = ValidateIfUserDisabled(user); if (!isUserDisabledResult.IsSuccess) { await _eventService.RaiseAsync(new UserLoginFailureEvent(user.UserName, DisabledEventMessage, clientId : context?.ClientId)); return(Result.Failure <SignInResponse>(isUserDisabledResult.Errors)); } var props = new AuthenticationProperties { RedirectUri = context?.RedirectUri, AllowRefresh = true, IsPersistent = false }; await _signInManager.SignInAsync(user, props); await RaiseLoginSuccessAsync(username, context); // We can trust returnUrl if GetAuthorizationContextAsync returned non-null return(Result.Success(new SignInResponse(context is object))); }
public async Task <IActionResult> Login(LoginViewModel viewModel) { if (viewModel is null) { throw new ArgumentNullException(nameof(viewModel)); } var returnUri = viewModel.ReturnUrl; if (returnUri is null) { return(RedirectToPublicBrowseLogin()); } var signInResult = await loginService.SignInAsync(viewModel.EmailAddress, viewModel.Password, returnUri); LoginViewModel NewLoginViewModel() => new() { ReturnUrl = viewModel.ReturnUrl, EmailAddress = signInResult.Value?.LoginHint }; if (!ModelState.IsValid) { return(View(NewLoginViewModel())); } if (!signInResult.IsSuccess) { var signInErrors = signInResult.Errors; if (signInErrors.Contains(LoginUserErrors.UserNameOrPasswordIncorrect())) { ModelState.Remove(nameof(LoginViewModel.Password)); ModelState.AddModelError(nameof(LoginViewModel.EmailAddress), SignInErrorMessage); ModelState.AddModelError(nameof(LoginViewModel.Password), SignInErrorMessage); } if (!signInErrors.Contains(LoginUserErrors.UserIsDisabled())) { return(View(NewLoginViewModel())); } var disabledErrorFormat = string.Format( CultureInfo.CurrentCulture, UserDisabledErrorMessageTemplate, disabledErrorMessageSettings.EmailAddress, disabledErrorMessageSettings.PhoneNumber); ModelState.AddModelError(nameof(LoginViewModel.DisabledError), disabledErrorFormat); return(View(NewLoginViewModel())); } var returnUrl = returnUri.ToString(); // We can trust viewModel.ReturnUrl since GetAuthorizationContextAsync returned non-null if (signInResult.Value.IsTrustedReturnUrl) { return(Redirect(returnUrl)); } return(LocalRedirect(returnUrl)); }
private async Task <Result> ValidateUserCredentialsAsync(ApplicationUser user, string password) { var result = await _signInManager.CheckPasswordSignInAsync(user, password, true); return(result.Succeeded ? Result.Success() : Result.Failure(LoginUserErrors.UserNameOrPasswordIncorrect())); }
public async Task Login_LoginViewModel_FailedSignIn_AddsUsernameOrPasswordValidationError() { using var controller = AccountControllerBuilder .Create() .WithSignInResult(Result.Failure <SignInResponse>(new List <ErrorDetails> { LoginUserErrors.UserNameOrPasswordIncorrect() })) .Build(); await controller.Login(LoginViewModelBuilder.Create().Build()); var modelState = controller.ModelState; modelState.IsValid.Should().BeFalse(); modelState.Count.Should().Be(2); foreach ((string key, ModelStateEntry entry) in modelState) { entry.Errors.Count.Should().Be(1); entry.Errors.First().ErrorMessage.Should().Be(AccountController.SignInErrorMessage); } }