public ProtectedResource(Uri baseUri, string[] scopes, AuthenticationFlow authenticationFlow = AuthenticationFlow.OnBehalfOf) { BaseUri = baseUri ?? throw new ArgumentNullException(nameof(baseUri)); Scopes = scopes ?? throw new ArgumentNullException(nameof(scopes)); AuthenticationFlow = authenticationFlow; AcquireTokenAsync = CreateTokenCallback(AuthenticationFlow, Scopes); }
/// <summary> /// Initializes a new instance of the <see cref="AuthenticationFlowTest"/> class. /// </summary> /// <param name="outputHelper">The test output helper.</param> public AuthenticationFlowTest(ITestOutputHelper outputHelper) { this.outputHelper = outputHelper; this.testDatabase = new TestDatabase(outputHelper); this.dbContext = this.testDatabase.CreateContext(); this.identityInstance = IdentityTestHelper.CreateInstance(this.testDatabase, this.outputHelper); this.usedHttpContext = new DefaultHttpContext(); this.httpConctextAccessorMock = new Mock <IHttpContextAccessor>(); this.jwtCrypoMock = new Mock <IJwtCryptoProvider>(); this.momentMock = MomentTestHelper.CreateMomentMock(); this.optionsMonitorMock = OptionsTestHelper.CreateBackendOptionsMock(); this.randomGenerator = new SecureRandomGenerator(); this.loggerFactory = LoggingTestHelper.CreateLoggerFactory(this.outputHelper); this.httpConctextAccessorMock.SetupGet(m => m.HttpContext).Returns(this.usedHttpContext); this.jwtCrypoMock.SetupGet(c => c.Algorithm).Returns(SigningAlgorithm); this.jwtCrypoMock.SetupGet(c => c.SecurityKey).Returns(SigningKey); this.authenticationFlow = new AuthenticationFlow( this.httpConctextAccessorMock.Object, this.jwtCrypoMock.Object, this.identityInstance.UserManager, this.dbContext, this.randomGenerator, this.momentMock.Object, this.optionsMonitorMock.Object, this.loggerFactory.CreateLogger <AuthenticationFlow>()); }
public async Task <bool> CreateAuthenticationFlowAsync(string realm, AuthenticationFlow authenticationFlow) { var response = await GetBaseUrl(realm) .AppendPathSegment($"/admin/realms/{realm}/authentication/flows") .PostJsonAsync(authenticationFlow) .ConfigureAwait(false); return(response.IsSuccessStatusCode); }
/// <summary> /// No validations are performed using this constructor /// </summary> /// <param name="authority"></param> /// <param name="authorizationEndpointRelativePath"></param> /// <param name="clientId"></param> /// <param name="clientSecret"></param> /// <param name="scope"></param> /// <param name="username"></param> /// <param name="password"></param> /// <param name="authenticationFlow"></param> public Options(Uri authority, string authorizationEndpointRelativePath, string clientId, string clientSecret, string scope, string username, string password, AuthenticationFlow authenticationFlow) { Authority = authority; ClientId = clientId; ClientSecret = clientSecret; Scope = scope; Username = username; Password = password; AuthenticationFlow = authenticationFlow; AuthorizationEndpointRelativePath = authorizationEndpointRelativePath; }
public ProtectedResource(string baseUrl, string scopes, AuthenticationFlow authenticationFlow = AuthenticationFlow.OnBehalfOf) { if (string.IsNullOrEmpty(baseUrl)) { throw new ArgumentException("Value cannot be null or empty.", nameof(baseUrl)); } BaseUri = new Uri(baseUrl); Scopes = !string.IsNullOrEmpty(scopes) ? scopes.Split(' ', StringSplitOptions.RemoveEmptyEntries) : Array.Empty <string>(); AuthenticationFlow = authenticationFlow; AcquireTokenAsync = CreateTokenCallback(AuthenticationFlow, Scopes); }
private static Func <ITokenAcquisition, Task <string> > CreateTokenCallback(AuthenticationFlow authenticationFlow, string[] scopes) { switch (authenticationFlow) { case AuthenticationFlow.ClientCredentials: var scope = scopes.Single(); return(tokenProvider => tokenProvider.GetAccessTokenForAppAsync(scope)); case AuthenticationFlow.OnBehalfOf: return(tokenProvider => tokenProvider.GetAccessTokenForUserAsync(scopes)); default: throw new Exception($"AuthenticationFlow \"{authenticationFlow}\" not recognized."); } }
private async Task <string> GenerateAccessToken(Entity.User user, AuthenticationFlow authenticationFlow) { try { var roles = await userManager.GetRolesAsync(user); if (roles is null) { return(null); } var claims = GenerateUserClaims(user, roles, authenticationFlow); if (claims is null) { return(null); } var key = new SymmetricSecurityKey(Encoding.UTF8.GetBytes(tokenSettings.Secret)); var creds = new SigningCredentials(key, SecurityAlgorithms.HmacSha256); var token = new JwtSecurityToken( issuer: tokenSettings.Issuer, audience: tokenSettings.Issuer, claims, expires: DateTime.Now.AddDays(Convert.ToDouble(tokenSettings.AccessTokenExpirationInDays)), signingCredentials: creds ); return(new JwtSecurityTokenHandler().WriteToken(token)); } catch (Exception ex) { logger.LogError($"Generating access token for user: {user.Id} was not successfull", ex); throw; } }
private IList <Claim> GenerateUserClaims(Entity.User user, IList <string> roles, AuthenticationFlow authenticationFlow) { try { var claims = new List <Claim> { new Claim(JwtRegisteredClaimNames.Sub, user.Id.ToString()), new Claim(ClaimTypes.Name, user.UserName), new Claim(JwtRegisteredClaimNames.Jti, Guid.NewGuid().ToString()), new Claim(ClaimTypes.NameIdentifier, user.Id.ToString()) }; if (authenticationFlow.Equals(AuthenticationFlow.Full)) { var roleClaims = roles.Select(r => new Claim(ClaimTypes.Role, r)); claims.AddRange(roleClaims); } return(claims); } catch (Exception ex) { logger.LogError($"Claims could not be generated for user: {user.Id}", ex); throw; } }
public async Task <Result <AuthenticationToken> > GenerateAuthenticationTokenAsync(Entity.User user, string loginProvider, AuthenticationFlow authenticationFlow) { try { var accessToken = await GenerateAccessToken(user, authenticationFlow); if (accessToken is null) { return(new InvalidResult <AuthenticationToken>("Could not generate access token")); } var refreshToken = GenerateRefreshToken(); if (refreshToken is null) { return(new InvalidResult <AuthenticationToken>("Could not generate access token")); } var refreshTokenExpiration = DateTime.Now.AddDays(Convert.ToDouble(tokenSettings.RefreshTokenExpirationInDays)); var accessTokenExpiration = DateTime.Now.AddDays(Convert.ToDouble(tokenSettings.AccessTokenExpirationInDays)); var token = await repository.AddUserTokenAsync(new UserToken() { UserId = user.Id, User = user, LoginProvider = loginProvider, AccessToken = accessToken, RefreshToken = refreshToken, RefreshTokenExpiration = refreshTokenExpiration, AccessTokenExpiration = accessTokenExpiration, AuthenticationFlow = (int)authenticationFlow, }); if (token is null) { return(new InvalidResult <AuthenticationToken>("Could not save new authentication token")); } var result = mapper.Map <UserToken, AuthenticationToken>(token); return(new SuccessResult <AuthenticationToken>(result)); } catch (Exception ex) { return(new UnexpectedResult <AuthenticationToken>(ex.Message)); } }