/// <summary> /// Initiates the asynchronous refresh token authentication flow /// </summary> /// <param name="refreshTokenRequest">InitiateRefreshTokenAuthRequest object containing the necessary /// parameters to initiate the refresh token authentication flow</param> /// <returns>Returns the AuthFlowResponse object that can be used to respond to the next challenge, /// if one exists</returns> public void StartWithRefreshTokenAuthAsync(InitiateRefreshTokenAuthRequest refreshTokenRequest, AsyncCallback <AuthFlowResponse> callback = null) { InitiateAuthRequest initiateAuthRequest = CreateRefreshTokenAuthRequest(refreshTokenRequest.AuthFlowType); Provider.InitiateAuthAsync(initiateAuthRequest, r => { if (r.Exception != null) { callback?.Invoke(new AsyncResult <AuthFlowResponse>(null, r.Exception)); return; } InitiateAuthResponse initiateResponse = r.Response; UpdateSessionIfAuthenticationComplete(initiateResponse.ChallengeName, initiateResponse.AuthenticationResult); callback?.Invoke(new AsyncResult <AuthFlowResponse>(new AuthFlowResponse() { SessionID = initiateResponse.Session, ChallengeName = initiateResponse.ChallengeName, AuthenticationResult = initiateResponse.AuthenticationResult, ChallengeParameters = initiateResponse.ChallengeParameters, ClientMetadata = new Dictionary <string, string>(initiateResponse.ResponseMetadata.Metadata) }, null)); }); }
/// <summary> /// Initiates the asynchronous custom authentication flow /// </summary> /// <param name="customRequest">InitiateCustomAuthRequest object containing the necessary parameters to /// create an InitiateAuthAsync API call for custom authentication</param> /// <returns>Returns the AuthFlowResponse object that can be used to respond to the next challenge, /// if one exists</returns> public void StartWithCustomAuthAsync(InitiateCustomAuthRequest customRequest, AsyncCallback <AuthFlowResponse> callback = null) { InitiateAuthRequest authRequest = new InitiateAuthRequest() { AuthFlow = AuthFlowType.CUSTOM_AUTH, AuthParameters = new Dictionary <string, string>(customRequest.AuthParameters), ClientId = ClientID, ClientMetadata = new Dictionary <string, string>(customRequest.ClientMetadata) }; Provider.InitiateAuthAsync(authRequest, r => { if (r.Exception != null) { callback?.Invoke(new AsyncResult <AuthFlowResponse>(null, r.Exception)); return; } InitiateAuthResponse initiateResponse = r.Response; UpdateUsernameAndSecretHash(initiateResponse.ChallengeParameters); UpdateSessionIfAuthenticationComplete(initiateResponse.ChallengeName, initiateResponse.AuthenticationResult); callback?.Invoke(new AsyncResult <AuthFlowResponse>(new AuthFlowResponse() { SessionID = initiateResponse.Session, ChallengeName = initiateResponse.ChallengeName, AuthenticationResult = initiateResponse.AuthenticationResult, ChallengeParameters = initiateResponse.ChallengeParameters, ClientMetadata = new Dictionary <string, string>(initiateResponse.ResponseMetadata.Metadata) }, null)); }); }
/// <summary> /// Initiates the asynchronous custom authentication flow /// </summary> /// <param name="customRequest">InitiateCustomAuthRequest object containing the necessary parameters to /// create an InitiateAuthAsync API call for custom authentication</param> /// <returns>Returns the AuthFlowResponse object that can be used to respond to the next challenge, /// if one exists</returns> public async Task <AuthFlowResponse> StartWithCustomAuthAsync(InitiateCustomAuthRequest customRequest) { InitiateAuthRequest authRequest = new InitiateAuthRequest() { AuthFlow = AuthFlowType.CUSTOM_AUTH, AuthParameters = new Dictionary <string, string>(customRequest.AuthParameters), ClientId = ClientID, ClientMetadata = new Dictionary <string, string>(customRequest.ClientMetadata) }; InitiateAuthResponse initiateResponse = await Provider.InitiateAuthAsync(authRequest).ConfigureAwait(false); UpdateUsernameAndSecretHash(initiateResponse.ChallengeParameters); UpdateSessionIfAuthenticationComplete(initiateResponse.ChallengeName, initiateResponse.AuthenticationResult); return(new AuthFlowResponse() { SessionID = initiateResponse.Session, ChallengeName = initiateResponse.ChallengeName, AuthenticationResult = initiateResponse.AuthenticationResult, ChallengeParameters = initiateResponse.ChallengeParameters, ClientMetadata = new Dictionary <string, string>(initiateResponse.ResponseMetadata.Metadata) }); }
/// <summary> /// Initiates the asynchronous SRP authentication flow /// </summary> /// <param name="srpRequest">InitiateSrpAuthRequest object containing the necessary parameters to /// create an InitiateAuthAsync API call for SRP authentication</param> /// <returns>Returns the AuthFlowResponse object that can be used to respond to the next challenge, /// if one exists</returns> public async Task <AuthFlowResponse> StartWithSrpAuthAsync(InitiateSrpAuthRequest srpRequest) { if (srpRequest == null || string.IsNullOrEmpty(srpRequest.Password)) { throw new ArgumentNullException("Password required for authentication.", "srpRequest"); } Tuple <BigInteger, BigInteger> tupleAa = AuthenticationHelper.CreateAaTuple(); InitiateAuthRequest initiateRequest = CreateSrpAuthRequest(tupleAa); InitiateAuthResponse initiateResponse = await Provider.InitiateAuthAsync(initiateRequest).ConfigureAwait(false); UpdateUsernameAndSecretHash(initiateResponse.ChallengeParameters); RespondToAuthChallengeRequest challengeRequest = CreateSrpPasswordVerifierAuthRequest(initiateResponse, srpRequest.Password, tupleAa); RespondToAuthChallengeResponse verifierResponse = await Provider.RespondToAuthChallengeAsync(challengeRequest).ConfigureAwait(false); UpdateSessionIfAuthenticationComplete(verifierResponse.ChallengeName, verifierResponse.AuthenticationResult); return(new AuthFlowResponse() { SessionID = verifierResponse.Session, ChallengeName = verifierResponse.ChallengeName, AuthenticationResult = verifierResponse.AuthenticationResult, ChallengeParameters = verifierResponse.ChallengeParameters, ClientMetadata = new Dictionary <string, string>(verifierResponse.ResponseMetadata.Metadata) }); }
/// <summary> /// Internal method which responds to the PASSWORD_VERIFIER challenge in SRP authentication /// </summary> /// <param name="challenge">Response from the InitiateAuth challenge</param> /// <param name="password">Password for the CognitoUser, needed for authentication</param> /// <param name="tupleAa">Tuple of BigIntegers containing the A,a pair for the SRP protocol flow</param> /// <returns>Returns the RespondToAuthChallengeRequest for an SRP authentication flow</returns> private RespondToAuthChallengeRequest CreateSrpPasswordVerifierAuthRequest(InitiateAuthResponse challenge, string password, Tuple <BigInteger, BigInteger> tupleAa) { string username = challenge.ChallengeParameters[CognitoConstants.ChlgParamUsername]; string poolName = PoolName; string secretBlock = challenge.ChallengeParameters[CognitoConstants.ChlgParamSecretBlock]; string salt = challenge.ChallengeParameters[CognitoConstants.ChlgParamSalt]; BigInteger srpb = BigIntegerExtensions.FromUnsignedLittleEndianHex(challenge.ChallengeParameters[CognitoConstants.ChlgParamSrpB]); if ((srpb.TrueMod(AuthenticationHelper.N)).Equals(BigInteger.Zero)) { throw new ArgumentException("SRP error, B mod N cannot be zero.", "challenge"); } DateTime timestamp = DateTime.UtcNow; string timeStr = timestamp.ToString("ddd MMM d HH:mm:ss \"UTC\" yyyy", CultureInfo.InvariantCulture); byte[] claim = AuthenticationHelper.AuthenticateUser(username, password, poolName, tupleAa, salt, challenge.ChallengeParameters[CognitoConstants.ChlgParamSrpB], secretBlock, timeStr); string claimBase64 = Convert.ToBase64String(claim); Dictionary <string, string> srpAuthResponses = new Dictionary <string, string>(StringComparer.Ordinal) { { CognitoConstants.ChlgParamPassSecretBlock, secretBlock }, { CognitoConstants.ChlgParamPassSignature, claimBase64 }, { CognitoConstants.ChlgParamUsername, username }, { CognitoConstants.ChlgParamTimestamp, timeStr }, }; if (!string.IsNullOrEmpty(ClientSecret)) { SecretHash = CognitoAuthHelper.GetUserPoolSecretHash(Username, ClientID, ClientSecret); srpAuthResponses.Add(CognitoConstants.ChlgParamSecretHash, SecretHash); } if (Device != null && !string.IsNullOrEmpty(Device.DeviceKey)) { srpAuthResponses.Add(CognitoConstants.ChlgParamDeviceKey, Device.DeviceKey); } RespondToAuthChallengeRequest authChallengeRequest = new RespondToAuthChallengeRequest() { ChallengeName = challenge.ChallengeName, ClientId = ClientID, Session = challenge.Session, ChallengeResponses = srpAuthResponses }; return(authChallengeRequest); }
/// <summary> /// Initiates the asynchronous refresh token authentication flow /// </summary> /// <param name="refreshTokenRequest">InitiateRefreshTokenAuthRequest object containing the necessary /// parameters to initiate the refresh token authentication flow</param> /// <returns>Returns the AuthFlowResponse object that can be used to respond to the next challenge, /// if one exists</returns> public async Task <AuthFlowResponse> StartWithRefreshTokenAuthAsync(InitiateRefreshTokenAuthRequest refreshTokenRequest) { InitiateAuthRequest initiateAuthRequest = CreateRefreshTokenAuthRequest(refreshTokenRequest.AuthFlowType); InitiateAuthResponse initiateResponse = await Provider.InitiateAuthAsync(initiateAuthRequest).ConfigureAwait(false); UpdateSessionIfAuthenticationComplete(initiateResponse.ChallengeName, initiateResponse.AuthenticationResult); return(new AuthFlowResponse(initiateResponse.Session, initiateResponse.AuthenticationResult, initiateResponse.ChallengeName, initiateResponse.ChallengeParameters, new Dictionary <string, string>(initiateResponse.ResponseMetadata.Metadata))); }
public AuthenticationResult LoginUser(LoginUserQueryParam loginUserQueryParam) { InitiateAuthRequest iaRequest = new InitiateAuthRequest { ClientId = _connectionInfo.ClientId, AuthFlow = AuthFlowType.USER_PASSWORD_AUTH }; iaRequest.AuthParameters.Add("USERNAME", loginUserQueryParam.Email); iaRequest.AuthParameters.Add("PASSWORD", loginUserQueryParam.Password); InitiateAuthResponse authResp = new InitiateAuthResponse(); var authResult = new AuthenticationResult(); try { authResp = _provider.InitiateAuthAsync(iaRequest).Result; authResult.AccessToken = authResp.AuthenticationResult.AccessToken; authResult.IdToken = authResp.AuthenticationResult.IdToken; authResult.RefreshToken = authResp.AuthenticationResult.RefreshToken; authResult.TokenType = authResp.AuthenticationResult.TokenType; authResult.ExpiresIn = authResp.AuthenticationResult.ExpiresIn; authResult.Success = true; } catch (AggregateException e) { e.Handle((x) => { if (x is UserNotConfirmedException) // This we know how to handle. { LoggingHandler.LogInfo("User not confirmed."); authResult.Success = false; authResult.ResponseMessage = "User not confirmed"; return(true); } if (x is NotAuthorizedException) // This we know how to handle. { LoggingHandler.LogInfo("Invalid credentials provided."); authResult.Success = false; authResult.ResponseMessage = "Invalid credentials provided."; return(true); } return(false); // Let anything else stop the application. }); } return(authResult); }
/// <summary> /// Initiates the asynchronous refresh token authentication flow /// </summary> /// <param name="refreshTokenRequest">InitiateRefreshTokenAuthRequest object containing the necessary /// parameters to initiate the refresh token authentication flow</param> /// <returns>Returns the AuthFlowResponse object that can be used to respond to the next challenge, /// if one exists</returns> public virtual async Task <AuthFlowResponse> StartWithRefreshTokenAuthAsync(InitiateRefreshTokenAuthRequest refreshTokenRequest) { InitiateAuthRequest initiateAuthRequest = CreateRefreshTokenAuthRequest(refreshTokenRequest.AuthFlowType); InitiateAuthResponse initiateResponse = await Provider.InitiateAuthAsync(initiateAuthRequest).ConfigureAwait(false); // Service does not return the refresh token. Hence, set it to the old refresh token that was used. if (string.IsNullOrEmpty(initiateResponse.ChallengeName) && string.IsNullOrEmpty(initiateResponse.AuthenticationResult.RefreshToken)) { initiateResponse.AuthenticationResult.RefreshToken = initiateAuthRequest.AuthParameters[CognitoConstants.ChlgParamRefreshToken]; } UpdateSessionIfAuthenticationComplete(initiateResponse.ChallengeName, initiateResponse.AuthenticationResult); return(new AuthFlowResponse(initiateResponse.Session, initiateResponse.AuthenticationResult, initiateResponse.ChallengeName, initiateResponse.ChallengeParameters, new Dictionary <string, string>(initiateResponse.ResponseMetadata.Metadata))); }
public async Task <LoginResponse> LoginAsync(string username, string password) { LoginResponse loginResponse; InitiateAuthRequest auth = new InitiateAuthRequest() { ClientId = CLIENT_ID, AuthFlow = AuthFlowType.USER_PASSWORD_AUTH, }; auth.AuthParameters.Add("USERNAME", username); auth.AuthParameters.Add("PASSWORD", password); InitiateAuthResponse response = await _loginClient.InitiateAuthAsync(auth); if (response.HttpStatusCode == System.Net.HttpStatusCode.OK) { JwtSecurityTokenHandler handler = new JwtSecurityTokenHandler(); JwtSecurityToken jsonToken = handler.ReadToken(response.AuthenticationResult.IdToken) as JwtSecurityToken; loginResponse = new LoginResponse() { Email = jsonToken.Claims.Single(c => c.Type == "email").Value, EmailVerified = bool.Parse(jsonToken.Claims.Single(c => c.Type == "email_verified").Value), FamilyName = jsonToken.Claims.Single(c => c.Type == "family_name").Value, GivenName = jsonToken.Claims.Single(c => c.Type == "given_name").Value, HomeStudioId = jsonToken.Claims.Single(c => c.Type == "custom:home_studio_id").Value, IsMigration = bool.Parse(jsonToken.Claims.Single(c => c.Type == "custom:isMigration").Value), Locale = jsonToken.Claims.Single(c => c.Type == "locale").Value, MemberId = jsonToken.Claims.Single(c => c.Type == "cognito:username").Value, JwtToken = response.AuthenticationResult.IdToken, Expiration = jsonToken.ValidTo, IssuedOn = jsonToken.ValidFrom, }; } else { loginResponse = null; } return(loginResponse); }
/// <summary> /// Unmarshaller the response from the service to the response class. /// </summary> /// <param name="context"></param> /// <returns></returns> public override AmazonWebServiceResponse Unmarshall(JsonUnmarshallerContext context) { InitiateAuthResponse response = new InitiateAuthResponse(); context.Read(); int targetDepth = context.CurrentDepth; while (context.ReadAtDepth(targetDepth)) { if (context.TestExpression("AuthenticationResult", targetDepth)) { var unmarshaller = AuthenticationResultTypeUnmarshaller.Instance; response.AuthenticationResult = unmarshaller.Unmarshall(context); continue; } if (context.TestExpression("ChallengeName", targetDepth)) { var unmarshaller = StringUnmarshaller.Instance; response.ChallengeName = unmarshaller.Unmarshall(context); continue; } if (context.TestExpression("ChallengeParameters", targetDepth)) { var unmarshaller = new DictionaryUnmarshaller <string, string, StringUnmarshaller, StringUnmarshaller>(StringUnmarshaller.Instance, StringUnmarshaller.Instance); response.ChallengeParameters = unmarshaller.Unmarshall(context); continue; } if (context.TestExpression("Session", targetDepth)) { var unmarshaller = StringUnmarshaller.Instance; response.Session = unmarshaller.Unmarshall(context); continue; } } return(response); }
/// <summary> /// Initiates the asynchronous SRP authentication flow /// </summary> /// <param name="srpRequest">InitiateSrpAuthRequest object containing the necessary parameters to /// create an InitiateAuthAsync API call for SRP authentication</param> /// <returns>Returns the AuthFlowResponse object that can be used to respond to the next challenge, /// if one exists</returns> public async Task <AuthFlowResponse> StartWithSrpAuthAsync(InitiateSrpAuthRequest srpRequest) { if (srpRequest == null || string.IsNullOrEmpty(srpRequest.Password)) { throw new ArgumentNullException("Password required for authentication.", "srpRequest"); } Tuple <BigInteger, BigInteger> tupleAa = AuthenticationHelper.CreateAaTuple(); InitiateAuthRequest initiateRequest = CreateSrpAuthRequest(tupleAa); InitiateAuthResponse initiateResponse = await Provider.InitiateAuthAsync(initiateRequest).ConfigureAwait(false); UpdateUsernameAndSecretHash(initiateResponse.ChallengeParameters); RespondToAuthChallengeRequest challengeRequest = CreateSrpPasswordVerifierAuthRequest(initiateResponse, srpRequest.Password, tupleAa); bool challengeResponsesValid = challengeRequest != null && challengeRequest.ChallengeResponses != null; bool deviceKeyValid = Device != null && !string.IsNullOrEmpty(Device.DeviceKey); if (challengeResponsesValid && deviceKeyValid) { challengeRequest.ChallengeResponses.Add(CognitoConstants.ChlgParamDeviceKey, Device.DeviceKey); } RespondToAuthChallengeResponse verifierResponse = await Provider.RespondToAuthChallengeAsync(challengeRequest).ConfigureAwait(false); UpdateSessionIfAuthenticationComplete(verifierResponse.ChallengeName, verifierResponse.AuthenticationResult); return(new AuthFlowResponse(verifierResponse.Session, verifierResponse.AuthenticationResult, verifierResponse.ChallengeName, verifierResponse.ChallengeParameters, new Dictionary <string, string>(verifierResponse.ResponseMetadata.Metadata))); }