Exemplo n.º 1
0
        private async Task <IActionResult> LogoutResponseAsync <T>(Saml2Configuration samlConfig, string inResponseTo, string relayState, string loggedOutUrl, Saml2Binding <T> binding, Saml2StatusCodes status, string sessionIndex)
        {
            binding.RelayState = relayState;

            var saml2LogoutResponse = new Saml2LogoutResponse(samlConfig)
            {
                InResponseTo = new Saml2Id(inResponseTo),
                Status       = status,
                Destination  = new Uri(loggedOutUrl),
                SessionIndex = sessionIndex
            };

            binding.Bind(saml2LogoutResponse);
            logger.ScopeTrace($"SAML Logout response '{saml2LogoutResponse.XmlDocument.OuterXml}'.");
            logger.ScopeTrace($"Logged out URL '{loggedOutUrl}'.");
            logger.ScopeTrace("Down, SAML Logout response.", triggerEvent: true);

            await sequenceLogic.RemoveSequenceDataAsync <SamlDownSequenceData>();

            securityHeaderLogic.AddFormAction(loggedOutUrl);
            if (binding is Saml2Binding <Saml2RedirectBinding> )
            {
                return(await(binding as Saml2RedirectBinding).ToActionFormResultAsync());
            }
            if (binding is Saml2Binding <Saml2PostBinding> )
            {
                return(await(binding as Saml2PostBinding).ToActionFormResultAsync());
            }
            else
            {
                throw new NotSupportedException();
            }
        }
Exemplo n.º 2
0
        public async Task <IActionResult> EndSessionResponseAsync(string partyId)
        {
            logger.ScopeTrace(() => "Down, End session response.");
            logger.SetScopeProperty(Constants.Logs.DownPartyId, partyId);

            var sequenceData = await sequenceLogic.GetSequenceDataAsync <OidcDownSequenceData>(false);

            var rpInitiatedLogoutResponse = new RpInitiatedLogoutResponse
            {
                State = sequenceData.State,
            };

            logger.ScopeTrace(() => $"End session response '{rpInitiatedLogoutResponse.ToJsonIndented()}'.", traceType: TraceTypes.Message);
            var nameValueCollection = rpInitiatedLogoutResponse.ToDictionary();

            logger.ScopeTrace(() => $"Redirect Uri '{sequenceData.RedirectUri}'.");
            logger.ScopeTrace(() => "Down, OIDC End session response.", triggerEvent: true);

            await sequenceLogic.RemoveSequenceDataAsync <OidcDownSequenceData>();

            if (sequenceData.RestrictFormAction)
            {
                securityHeaderLogic.AddFormAction(sequenceData.RedirectUri);
            }
            else
            {
                securityHeaderLogic.AddFormActionAllowAll();
            }
            return(await nameValueCollection.ToRedirectResultAsync(sequenceData.RedirectUri));
        }
Exemplo n.º 3
0
        public async Task <IActionResult> AuthenticationResponseAsync(string partyId, List <Claim> claims)
        {
            logger.ScopeTrace(() => "Down, OIDC Authentication response.");
            logger.SetScopeProperty(Constants.Logs.DownPartyId, partyId);
            var party = await tenantRepository.GetAsync <TParty>(partyId);

            if (party.Client == null)
            {
                throw new NotSupportedException("Party Client not configured.");
            }

            var sequenceData = await sequenceLogic.GetSequenceDataAsync <OidcDownSequenceData>(false);

            logger.ScopeTrace(() => $"Down, OIDC received JWT claims '{claims.ToFormattedString()}'", traceType: TraceTypes.Claim);
            claims = await claimTransformLogic.Transform(party.ClaimTransforms?.ConvertAll(t => (ClaimTransform)t), claims);

            logger.ScopeTrace(() => $"Down, OIDC output JWT claims '{claims.ToFormattedString()}'", traceType: TraceTypes.Claim);

            var nameValueCollection = await CreateAuthenticationAndSessionResponse(party, claims, sequenceData);

            var responseMode = GetResponseMode(sequenceData.ResponseMode, sequenceData.ResponseType);
            await sequenceLogic.RemoveSequenceDataAsync <OidcDownSequenceData>();

            if (party.RestrictFormAction)
            {
                securityHeaderLogic.AddFormAction(sequenceData.RedirectUri);
            }
            else
            {
                securityHeaderLogic.AddFormActionAllowAll();
            }
            switch (responseMode)
            {
            case IdentityConstants.ResponseModes.FormPost:
                return(await nameValueCollection.ToHtmlPostContentResultAsync(sequenceData.RedirectUri));

            case IdentityConstants.ResponseModes.Query:
                return(await nameValueCollection.ToRedirectResultAsync(sequenceData.RedirectUri));

            case IdentityConstants.ResponseModes.Fragment:
                return(await nameValueCollection.ToFragmentResultAsync(sequenceData.RedirectUri));

            default:
                throw new NotSupportedException();
            }
        }
Exemplo n.º 4
0
        private async Task <IActionResult> AuthnResponseAsync <T>(SamlDownParty party, Saml2Configuration samlConfig, string inResponseTo, string relayState, string acsUrl, Saml2Binding <T> binding, Saml2StatusCodes status, IEnumerable <Claim> claims)
        {
            binding.RelayState = relayState;

            var saml2AuthnResponse = new FoxIDsSaml2AuthnResponse(settings, samlConfig)
            {
                InResponseTo = new Saml2Id(inResponseTo),
                Status       = status,
                Destination  = new Uri(acsUrl),
            };

            if (status == Saml2StatusCodes.Success && party != null && claims != null)
            {
                claims = await claimTransformationsLogic.Transform(party.ClaimTransforms?.ConvertAll(t => (ClaimTransform)t), claims);

                saml2AuthnResponse.SessionIndex = samlClaimsDownLogic.GetSessionIndex(claims);

                saml2AuthnResponse.NameId = samlClaimsDownLogic.GetNameId(claims);

                var tokenIssueTime  = DateTimeOffset.UtcNow;
                var tokenDescriptor = saml2AuthnResponse.CreateTokenDescriptor(samlClaimsDownLogic.GetSubjectClaims(party, claims), party.Issuer, tokenIssueTime, party.IssuedTokenLifetime);

                var authnContext            = claims.FindFirstValue(c => c.Type == ClaimTypes.AuthenticationMethod);
                var authenticationInstant   = claims.FindFirstValue(c => c.Type == ClaimTypes.AuthenticationInstant);
                var authenticationStatement = saml2AuthnResponse.CreateAuthenticationStatement(authnContext, DateTime.Parse(authenticationInstant));

                var subjectConfirmation = saml2AuthnResponse.CreateSubjectConfirmation(tokenIssueTime, party.SubjectConfirmationLifetime);

                await saml2AuthnResponse.CreateSecurityTokenAsync(tokenDescriptor, authenticationStatement, subjectConfirmation);
            }

            binding.Bind(saml2AuthnResponse);
            logger.ScopeTrace($"SAML Authn response '{saml2AuthnResponse.XmlDocument.OuterXml}'.");
            logger.ScopeTrace($"Acs URL '{acsUrl}'.");
            logger.ScopeTrace("Down, SAML Authn response.", triggerEvent: true);

            await sequenceLogic.RemoveSequenceDataAsync <SamlDownSequenceData>();

            securityHeaderLogic.AddFormAction(acsUrl);
            if (binding is Saml2Binding <Saml2RedirectBinding> )
            {
                return(await(binding as Saml2RedirectBinding).ToActionFormResultAsync());
            }
            else if (binding is Saml2Binding <Saml2PostBinding> )
            {
                return(await(binding as Saml2PostBinding).ToActionFormResultAsync());
            }
            else
            {
                throw new NotSupportedException();
            }
        }
Exemplo n.º 5
0
        public async Task <IActionResult> AuthenticationResponseAsync(string partyId, List <Claim> claims)
        {
            logger.ScopeTrace("Down, OIDC Authentication response.");
            logger.SetScopeProperty("downPartyId", partyId);
            var party = await tenantRepository.GetAsync <TParty>(partyId);

            if (party.Client == null)
            {
                throw new NotSupportedException("Party Client not configured.");
            }

            var sequenceData = await sequenceLogic.GetSequenceDataAsync <OidcDownSequenceData>(false);

            claims = await claimTransformationsLogic.Transform(party.ClaimTransforms?.ConvertAll(t => (ClaimTransform)t), claims);

            var authenticationResponse = new AuthenticationResponse
            {
                State     = sequenceData.State,
                ExpiresIn = party.Client.AccessTokenLifetime,
            };
            var sessionResponse = new SessionResponse
            {
                SessionState = claims.FindFirstValue(c => c.Type == JwtClaimTypes.SessionId).GetSessionStateValue(party.Client.ClientId, sequenceData.RedirectUri)
            };

            logger.ScopeTrace($"Response type '{sequenceData.ResponseType}'.");
            var responseTypes = sequenceData.ResponseType.ToSpaceList();

            if (responseTypes.Where(rt => rt.Contains(IdentityConstants.ResponseTypes.Code)).Any())
            {
                authenticationResponse.Code = await oauthAuthCodeGrantDownLogic.CreateAuthCodeGrantAsync(party.Client as TClient, claims, sequenceData.RedirectUri, sequenceData.Scope, sequenceData.Nonce, sequenceData.CodeChallenge, sequenceData.CodeChallengeMethod);
            }

            string algorithm = IdentityConstants.Algorithms.Asymmetric.RS256;

            if (responseTypes.Where(rt => rt.Contains(IdentityConstants.ResponseTypes.Token)).Any())
            {
                authenticationResponse.TokenType   = IdentityConstants.TokenTypes.Bearer;
                authenticationResponse.AccessToken = await jwtDownLogic.CreateAccessTokenAsync(party.Client as TClient, claims, sequenceData.Scope?.ToSpaceList(), algorithm);
            }
            if (responseTypes.Where(rt => rt.Contains(IdentityConstants.ResponseTypes.IdToken)).Any())
            {
                authenticationResponse.IdToken = await jwtDownLogic.CreateIdTokenAsync(party.Client as TClient, claims, sequenceData.Scope?.ToSpaceList(), sequenceData.Nonce, responseTypes, authenticationResponse.Code, authenticationResponse.AccessToken, algorithm);
            }

            logger.ScopeTrace($"Authentication response '{authenticationResponse.ToJsonIndented()}'.");
            var nameValueCollection = authenticationResponse.ToDictionary();

            if (!sessionResponse.SessionState.IsNullOrWhiteSpace())
            {
                logger.ScopeTrace($"Session response '{sessionResponse.ToJsonIndented()}'.");
                nameValueCollection = nameValueCollection.AddToDictionary(sessionResponse);
            }

            logger.ScopeTrace($"Redirect Uri '{sequenceData.RedirectUri}'.");
            logger.ScopeTrace("Down, OIDC Authentication response.", triggerEvent: true);

            var responseMode = GetResponseMode(sequenceData.ResponseMode, sequenceData.ResponseType);
            await sequenceLogic.RemoveSequenceDataAsync <OidcDownSequenceData>();

            securityHeaderLogic.AddFormAction(sequenceData.RedirectUri);
            switch (responseMode)
            {
            case IdentityConstants.ResponseModes.FormPost:
                return(await nameValueCollection.ToHtmlPostContentResultAsync(sequenceData.RedirectUri));

            case IdentityConstants.ResponseModes.Query:
                return(await nameValueCollection.ToRedirectResultAsync(sequenceData.RedirectUri));

            case IdentityConstants.ResponseModes.Fragment:
                return(await nameValueCollection.ToFragmentResultAsync(sequenceData.RedirectUri));

            default:
                throw new NotSupportedException();
            }
        }