/// <summary>
        /// Sends the SAML response to the Service Provider.
        /// </summary>
        /// <param name="samlResponse">The SAML response object.</param>
        /// <param name="relayState">The relay state.</param>
        public static void SendResponse(Page page, ComponentPro.Saml2.Response samlResponse, string relayState)
        {
            // Sign the SAML response.
            X509Certificate2 x509Certificate = (X509Certificate2)page.Application[Global.IdPCertKey];

            samlResponse.Sign(x509Certificate);

            switch (Global.AssertionServiceSamlBinding)
            {
            case SamlBinding.HttpPost:
                // Send the SAML Response object.
                samlResponse.SendPostBindingForm(page.Response.OutputStream, Global.AssertionServiceUrl, relayState);
                break;

            case SamlBinding.HttpArtifact:
                // Create the artifact.
                string identificationUrl           = GetAbsoluteUrl(page, "~/");
                Saml2ArtifactType0004 httpArtifact = new Saml2ArtifactType0004(SamlArtifact.GetSourceId(identificationUrl), SamlArtifact.GetHandle());

                // Convert the authentication request to XML and save to the application Cache.
                SamlSettings.CacheProvider.Insert(httpArtifact.ToString(), samlResponse.GetXml(), new TimeSpan(1, 0, 0));

                // Send the artifact with POST form.
                httpArtifact.SendPostForm(page.Response.OutputStream, Global.AssertionServiceUrl, relayState);
                break;

            default:
                throw new ApplicationException("Invalid assertion consumer service binding.");
            }
        }
        /// <summary>
        /// Processes a successful SAML response.
        /// </summary>
        private void ProcessSuccessResponse(ComponentPro.Saml2.Response samlResponse, string relayState)
        {
            // Extract the asserted identity from the SAML response.
            Assertion samlAssertion = (Assertion)samlResponse.Assertions[0];

            // Get the subject name identifier.
            string userName = samlAssertion.Subject.NameId.NameIdentifier;

            // Get the originally requested resource URL from the relay state.
            string resourceUrl = (string)SamlSettings.CacheProvider.Remove(relayState);

            if (resourceUrl == null)
            {
                Trace.Write("ServiceProvider", "Nothing in cache");

                // Set resource Url to the root dir
                resourceUrl = "/";
            }

            // Create a login context for the asserted identity.
            FormsAuthentication.SetAuthCookie(userName, false);

            // Redirect to the originally requested resource URL.
            Response.Redirect(resourceUrl);
        }
        // Send the SAML response over the specified binding.
        public static void SendSamlResponse(Page page, ComponentPro.Saml2.Response samlResponse, SsoAuthnState ssoState)
        {
            // Sign the SAML response
            X509Certificate2 x509Certificate = (X509Certificate2)page.Application[Global.IdPCertKey];

            samlResponse.Sign(x509Certificate);

            // Send the SAML response to the service provider.
            switch (ssoState.IdpProtocolBinding)
            {
            case SamlBinding.HttpPost:
                samlResponse.SendPostBindingForm(page.Response.OutputStream, ssoState.AssertionConsumerServiceURL, ssoState.RelayState);
                break;

            case SamlBinding.HttpArtifact:
                // Create the artifact.
                string identificationUrl           = Util.GetAbsoluteUrl(page, "~/");
                Saml2ArtifactType0004 httpArtifact = new Saml2ArtifactType0004(SamlArtifact.GetSourceId(identificationUrl), SamlArtifact.GetHandle());

                // Cache the authentication request for subsequent sending using the artifact resolution protocol. Sliding expiration time is 1 hour.
                SamlSettings.CacheProvider.Insert(httpArtifact.ToString(), samlResponse.GetXml(), new TimeSpan(1, 0, 0));

                // Send the artifact.
                httpArtifact.SendPostForm(page.Response.OutputStream, ssoState.AssertionConsumerServiceURL,
                                          ssoState.RelayState);
                break;

            default:
                Trace.Write("IdentityProvider", "Invalid identity provider binding");
                break;
            }
        }
示例#4
0
        /// <summary>
        /// Processes a successful SAML response and redirect to the requested URL.
        /// </summary>
        /// <param name="page">The page object.</param>
        /// <param name="samlResponse">The SAML response object.</param>
        /// <param name="relayState">The relay state.</param>
        public static void SamlSuccessRedirect(Page page, ComponentPro.Saml2.Response samlResponse, string relayState)
        {
            // Get the previously loaded certificate.
            X509Certificate2 x509Certificate = (X509Certificate2)page.Application[Global.SpCertKey];

            Assertion samlAssertion;

            // Check assertions.
            if (samlResponse.GetAssertions().Count > 0)
            {
                // Extract the first assertion.
                samlAssertion = samlResponse.GetAssertions()[0];
            }
            else if (samlResponse.GetEncryptedAssertions().Count > 0)
            {
                // Extract the first assertion.
                samlAssertion = samlResponse.GetEncryptedAssertions()[0].Decrypt(x509Certificate.PrivateKey, null);
            }
            else
            {
                throw new ApplicationException("No assertions in response");
            }

            string userName;

            // Get the subject name identifier.
            if (samlAssertion.Subject.NameId != null)
            {
                userName = samlAssertion.Subject.NameId.NameIdentifier;
            }
            else if (samlAssertion.Subject.EncryptedId != null)
            {
                NameId nameId = samlAssertion.Subject.EncryptedId.Decrypt(x509Certificate.PrivateKey, null);
                userName = nameId.NameIdentifier;
            }
            else
            {
                throw new ApplicationException("No name in subject");
            }

            // Get the originally requested resource URL from the relay state.
            string resourceUrl = (string)SamlSettings.CacheProvider.Remove(relayState);

            if (resourceUrl == null)
            {
                throw new ApplicationException("Invalid relay state");
            }

            // Create a login context for the asserted identity.
            FormsAuthentication.SetAuthCookie(userName, false);

            // Redirect to the originally requested resource URL.
            page.Response.Redirect(resourceUrl, false);
        }
示例#5
0
        /// <summary>
        /// Processes an error SAML response.
        /// </summary>
        private void ProcessErrorResponse(ComponentPro.Saml2.Response samlResponse)
        {
            string errorMessage = null;

            if ((samlResponse.Status.StatusMessage != null))
            {
                errorMessage = samlResponse.Status.StatusMessage.Message;
            }

            string redirectUrl = string.Format("~/UserLogin.aspx?{0}={1}", Util.ErrorVarName, HttpUtility.UrlEncode(errorMessage));

            Response.Redirect(redirectUrl, false);
        }
示例#6
0
        /// <summary>
        /// Processes an error SAML response and redirect to the requested URL.
        /// </summary>
        /// <param name="page">The page object.</param>
        /// <param name="samlResponse">The SAML response object.</param>
        /// <param name="relayState">The relay state.</param>
        public static void SamlErrorRedirect(Page page, ComponentPro.Saml2.Response samlResponse)
        {
            string errorMessage = null;

            if (samlResponse.Status.StatusMessage != null)
            {
                errorMessage = samlResponse.Status.StatusMessage.Message;
            }

            string redirectUrl = String.Format("~/UserLogin.aspx?error={0}", HttpUtility.UrlEncode(errorMessage));

            page.Response.Redirect(redirectUrl, false);
        }
示例#7
0
        /// <summary>
        /// Processes the SAML response received from the IdP.
        /// </summary>
        /// <param name="page">The page object.</param>
        /// <param name="relayState">The relay state</param>
        /// <param name="samlResponse">The SAML response object.</param>
        public static void ProcessResponse(Page page, out ComponentPro.Saml2.Response samlResponse, out string relayState)
        {
            // Extract the binding type from the query string.
            string bindingType = page.Request.QueryString["binding"];

            switch (bindingType)
            {
                case "artifact":
                    // Create an artifact from the query string.
                    Saml2ArtifactType0004 httpArtifact = Saml2ArtifactType0004.CreateFromHttpArtifactQueryString(page.Request);

                    // Create an artifact resolve request.
                    ArtifactResolve artifactResolve = new ArtifactResolve();
                    artifactResolve.Issuer = new Issuer(GetAbsoluteUrl(page, "~/"));
                    artifactResolve.Artifact = new Artifact(httpArtifact.ToString());

                    // Send the artifact resolve request and create an artifact response from the received XML.
                    ArtifactResponse artifactResponse = ArtifactResponse.SendSamlMessageReceiveAftifactResponse(Global.ArtifactServiceUrl, artifactResolve);

                    // Get the SAML Response from the artifact response.
                    samlResponse = new ComponentPro.Saml2.Response(artifactResponse.Message);
                    relayState = httpArtifact.RelayState;
                    break;

                case "post":
                    System.Diagnostics.Debug.WriteLine("POST");
                    // Create a SAML response from the form data.
                    samlResponse = ComponentPro.Saml2.Response.Create(page.Request);
                    relayState = samlResponse.RelayState;
                    break;                

                default:
                    throw new ApplicationException("Unknown binding type");
            }

            // Is the SAML response signed?
            if (samlResponse.IsSigned())
            {
                // Get the previously loaded certificate.
                X509Certificate2 x509Certificate = (X509Certificate2)page.Application[Global.IdPCertKey];

                // Validate the certificate.
                if (!samlResponse.Validate(x509Certificate))
                {
                    throw new ApplicationException("The SAML response signature failed to verify.");
                }
            }
        }
示例#8
0
        /// <summary>
        /// Processes the SAML response received from the IdP.
        /// </summary>
        /// <param name="page">The page object.</param>
        /// <param name="relayState">The relay state</param>
        /// <param name="samlResponse">The SAML response object.</param>
        public static void ProcessResponse(Page page, out ComponentPro.Saml2.Response samlResponse, out string relayState)
        {
            // Extract the binding type from the query string.
            string bindingType = page.Request.QueryString["binding"];

            switch (bindingType)
            {
                case "artifact":
                    // Create an artifact from the query string.
                    Saml2ArtifactType0004 httpArtifact = Saml2ArtifactType0004.CreateFromHttpArtifactQueryString(page.Request);

                    // Create an artifact resolve request.
                    ArtifactResolve artifactResolve = new ArtifactResolve();
                    artifactResolve.Issuer = new Issuer(GetAbsoluteUrl(page, "~/"));
                    artifactResolve.Artifact = new Artifact(httpArtifact.ToString());

                    // Send the artifact resolve request and create an artifact response from the received XML.
                    ArtifactResponse artifactResponse = ArtifactResponse.SendSamlMessageReceiveAftifactResponse(Global.ArtifactServiceUrl, artifactResolve);

                    // Get the SAML Response from the artifact response.
                    samlResponse = new ComponentPro.Saml2.Response(artifactResponse.Message);
                    relayState = httpArtifact.RelayState;
                    break;

                case "post":
                    // Create a SAML response from the form data.
                    samlResponse = ComponentPro.Saml2.Response.Create(page.Request);
                    relayState = samlResponse.RelayState;
                    break;

                default:
                    throw new ApplicationException("Unknown binding type");
            }

            // Is the SAML response signed?
            if (samlResponse.IsSigned())
            {
                // Get the previously loaded certificate.
                X509Certificate2 x509Certificate = (X509Certificate2)page.Application[Global.IdPCertKey];

                // Validate the certificate.
                if (!samlResponse.Validate(x509Certificate))
                {
                    throw new ApplicationException("The SAML response signature failed to verify.");
                }
            }
        }
示例#9
0
        /// <summary>
        /// Receives the SAML response from the identity provider.
        /// </summary>
        /// <param name="samlResponse"></param>
        /// <param name="relayState"></param>
        private void ReceiveResponse(out ComponentPro.Saml2.Response samlResponse, out string relayState)
        {
            // Determine the identity provider to service provider binding type.
            // We use a query string parameter rather than having separate endpoints per binding.
            string bindingType = Request.QueryString[Util.BindingVarName];

            switch (bindingType)
            {
            case SamlBindingUri.HttpPost:
                samlResponse = ComponentPro.Saml2.Response.Create(Request);
                relayState   = samlResponse.RelayState;
                break;

            case SamlBindingUri.HttpArtifact:
                Saml2ArtifactType0004 httpArtifact = Saml2ArtifactType0004.CreateFromHttpArtifactHttpForm(Request);

                // Create an artifact resolve request.
                ArtifactResolve artifactResolve = new ArtifactResolve();
                artifactResolve.Issuer   = new Issuer(Util.GetAbsoluteUrl(this, "~/"));
                artifactResolve.Artifact = new Artifact(httpArtifact.ToString());

                // Send the artifact resolve request and receive the artifact response.
                string spArtifactResponderUrl = WebConfigurationManager.AppSettings["ArtifactIdProviderUrl"];

                ArtifactResponse artifactResponse = ArtifactResponse.SendSamlMessageReceiveAftifactResponse(spArtifactResponderUrl, artifactResolve);

                // Extract the authentication request from the artifact response.
                samlResponse = new Response(artifactResponse.Message);
                relayState   = httpArtifact.RelayState;
                break;

            default:
                Trace.Write("ServiceProvider", "Invalid identity provider to service provider binding");
                samlResponse = null;
                relayState   = null;
                return;
            }

            // Verify the response's signature.
            X509Certificate2 x509Certificate = (X509Certificate2)Application[Global.IdPCertKey];

            if (!samlResponse.Validate(x509Certificate))
            {
                throw new System.ApplicationException("The SAML response signature failed to verify.");
            }
        }
        /// <summary>
        /// Builds the SAML response.
        /// </summary>
        /// <param name="authnRequest">The AuthnRequest object.</param>
        /// <returns>A SAML Response object.</returns>
        public static ComponentPro.Saml2.Response BuildResponse(Page page, AuthnRequest authnRequest)
        {
            ComponentPro.Saml2.Response samlResponse = new ComponentPro.Saml2.Response();
            samlResponse.Destination = Global.AssertionServiceUrl;
            Issuer issuer = new Issuer(GetAbsoluteUrl(page, "~/"));

            samlResponse.Issuer = issuer;

            if (page.User.Identity.IsAuthenticated)
            {
                samlResponse.Status = new Status(SamlPrimaryStatusCode.Success, null);

                Assertion samlAssertion = new Assertion();
                samlAssertion.Issuer = issuer;

                Subject                 subject                 = new Subject(new NameId(page.User.Identity.Name));
                SubjectConfirmation     subjectConfirmation     = new SubjectConfirmation(SamlSubjectConfirmationMethod.Bearer);
                SubjectConfirmationData subjectConfirmationData = new SubjectConfirmationData();
                subjectConfirmationData.InResponseTo        = authnRequest.Id;
                subjectConfirmationData.Recipient           = Global.AssertionServiceUrl;
                subjectConfirmation.SubjectConfirmationData = subjectConfirmationData;
                subject.SubjectConfirmations.Add(subjectConfirmation);
                samlAssertion.Subject = subject;

                AuthnStatement authnStatement = new AuthnStatement();
                authnStatement.AuthnContext = new AuthnContext();
                authnStatement.AuthnContext.AuthnContextClassRef = new AuthnContextClassRef(SamlAuthenticateContext.Password);
                samlAssertion.Statements.Add(authnStatement);

                samlResponse.Assertions.Add(samlAssertion);
            }
            else
            {
                samlResponse.Status = new Status(SamlPrimaryStatusCode.Responder, SamlSecondaryStatusCode.AuthnFailed, "The user is not authenticated at the identity provider");
            }

            return(samlResponse);
        }
        // Create a SAML response with the user's local identity, if any, or indicating an error.
        public static ComponentPro.Saml2.Response CreateSamlResponse(Page page)
        {
            ComponentPro.Saml2.Response samlResponse = new ComponentPro.Saml2.Response();
            string issuerUrl = Util.GetAbsoluteUrl(page, "~/");

            samlResponse.Issuer = new Issuer(issuerUrl);

            if (page.User.Identity.IsAuthenticated)
            {
                samlResponse.Status = new Status(SamlPrimaryStatusCode.Success, null);

                Assertion samlAssertion = new Assertion();

                samlAssertion.Subject = new Subject(new NameId(page.User.Identity.Name));
                samlAssertion.Statements.Add(new AuthnStatement());
                samlResponse.Assertions.Add(samlAssertion);
            }
            else
            {
                samlResponse.Status = new Status(SamlPrimaryStatusCode.Responder, SamlSecondaryStatusCode.AuthnFailed, "The user is not authenticated at the identity provider");
            }

            return(samlResponse);
        }
示例#12
0
        private void RecieveResponse(out ComponentPro.Saml2.Response samlResponse, out string relayState, string binding)
        {
            var bindingType = binding;

            if (bindingType == null)
            {
                if (HttpContext.Session.GetString("User") != null)
                {
                    HttpContext.Session.Set("User", null);
                }
                else
                {
                    HttpContext.Response.Redirect("trylogin");
                }
            }

            switch (bindingType)
            {
            case SamlBindingUri.HttpPost:
                samlResponse = ComponentPro.Saml2.Response.Create(HttpContext.Request);
                relayState   = samlResponse.RelayState;
                break;

            default:
                samlResponse = null;
                relayState   = null;
                return;
            }

            var x509Certificate = _certificateProvider.GetCertificate();

            if (!samlResponse.Validate(x509Certificate))
            {
                throw new ApplicationException("The SAML response signature failed to verify.");
            }
        }
        protected override void OnLoad(EventArgs e)
        {
            base.OnLoad(e);

            try
            {
                #region Receive SAML Response

                // Create a SAML response from the HTTP request.
                ComponentPro.Saml2.Response samlResponse = ComponentPro.Saml2.Response.Create(Request);

                // Is it signed?
                if (samlResponse.IsSigned())
                {
                    // Loaded the previously loaded certificate.
                    X509Certificate2 x509Certificate = (X509Certificate2)Application[Global.CertKeyName];

                    // Validate the SAML response with the certificate.
                    if (!samlResponse.Validate(x509Certificate))
                    {
                        throw new ApplicationException("SAML response signature is not valid.");
                    }
                }

                #endregion

                #region Process the response

                // Success?
                if (!samlResponse.IsSuccess())
                {
                    throw new ApplicationException("SAML response is not success");
                }

                Assertion samlAssertion;

                // Define ENCRYPTEDSAML preprocessor flag if you wish to decrypt the SAML response.
#if ENCRYPTEDSAML
                if (samlResponse.GetEncryptedAssertions().Count > 0)
                {
                    EncryptedAssertion encryptedAssertion = samlResponse.GetEncryptedAssertions()[0];

                    // Load the private key.
                    // Consider caching the loaded key in production environment for better performance.
                    X509Certificate2 decryptionKey = new X509Certificate2(Path.Combine(HttpRuntime.AppDomainAppPath, "EncryptionKey.pfx"), "password");

                    // Decrypt the encrypted assertion.
                    samlAssertion = encryptedAssertion.Decrypt(decryptionKey.PrivateKey, null);
                }
                else
                {
                    throw new ApplicationException("No encrypted assertions found in the SAML response");
                }
#else
                // Get the asserted identity.
                if (samlResponse.GetAssertions().Count > 0)
                {
                    samlAssertion = samlResponse.GetAssertions()[0];
                }
                else
                {
                    throw new ApplicationException("No assertions found in the SAML response");
                }
#endif

                // Get the subject name identifier.
                string userName;

                if (samlAssertion.Subject.NameId != null)
                {
                    userName = samlAssertion.Subject.NameId.NameIdentifier;
                }
                else
                {
                    throw new ApplicationException("Name identifier not found in subject");
                }

                #region Extract Custom Attributes

                // If you need to add custom attributes, uncomment the following code
                //if (samlAssertion.AttributeStatements.Count > 0)
                //{
                //    foreach (AttributeStatement attributeStatement in samlAssertion.AttributeStatements)
                //    {
                //        // If you need to decrypt encrypted attributes, refer to this topic: http://www.samlcomponent.net/encrypting-and-decrypting-saml-response-xml
                //        foreach (ComponentPro.Saml2.Attribute attribute in attributeStatement.Attributes)
                //        {
                //            // Process your custom attribute here.
                //            // ...
                //        }
                //    }
                //}

                #endregion

                // Set authentication cookie.
                FormsAuthentication.SetAuthCookie(userName, false);

                // Redirect to the requested URL.
                Response.Redirect(samlResponse.RelayState, false);

                #endregion
            }

            catch (Exception exception)
            {
                Trace.Write("ServiceProvider", "An Error occurred", exception);
            }
        }
示例#14
0
        protected override void OnLoad(EventArgs e)
        {
            base.OnLoad(e);

            try
            {
                // Load the Single Sign On state from the Session state.
                // If the saved authentication state is a null reference, receive the authentication request from the query string and form data.
                SsoAuthnState ssoState = (SsoAuthnState)Session[SsoAuthnStateSessionKey];

                if (ssoState == null || !User.Identity.IsAuthenticated)
                {
                    AuthnRequest authnRequest;
                    string       relayState;

                    // Receive the authentication request and relay state.
                    Util.ProcessAuthnRequest(this, out authnRequest, out relayState);

                    // Check whether the provider MUST authenticate the presenter directly rather than rely on a previous security context.
                    bool forceAuthn  = authnRequest.ForceAuthn;
                    bool allowCreate = false;

                    if (authnRequest.NameIdPolicy != null)
                    {
                        // Check whether the identity provider is allowed.
                        allowCreate = authnRequest.NameIdPolicy.AllowCreate;
                    }

                    ssoState = new SsoAuthnState();
                    ssoState.AuthnRequest = authnRequest;
                    ssoState.State        = relayState;

                    // A boolean flag determining whether or not a local login is required.
                    bool requireLocalLogin = false;

                    if (forceAuthn)
                    {
                        requireLocalLogin = true;
                    }
                    else
                    {
                        if (!User.Identity.IsAuthenticated && allowCreate)
                        {
                            requireLocalLogin = true;
                        }
                    }

                    // Local login is required?
                    if (requireLocalLogin)
                    {
                        // Then save the session state.
                        Session[SsoAuthnStateSessionKey] = ssoState;
                        // And redirect to the login page.
                        FormsAuthentication.RedirectToLoginPage();

                        return;
                    }
                }

                // Create a new SAML 2 Response.
                ComponentPro.Saml2.Response samlResponse = Util.BuildResponse(this, ssoState.AuthnRequest);

                // Send the SAML response to the service provider.
                Util.SendResponse(this, samlResponse, ssoState.State);
            }

            catch (Exception exception)
            {
                Trace.Write("IdentityProvider", "An Error occurred", exception);
            }
        }
        protected override void OnLoad(EventArgs e)
        {
            base.OnLoad(e);

            try
            {
                // Extract the SP target url.
                string targetUrl = Request.QueryString["spUrl"];

                // Validate it.
                if (string.IsNullOrEmpty(targetUrl))
                {
                    return;
                }

                // Create a SAML response object.
                ComponentPro.Saml2.Response samlResponse = new ComponentPro.Saml2.Response();
                // Assign the consumer service url.
                samlResponse.Destination = ConsumerServiceUrl;
                Issuer issuer = new Issuer(GetAbsoluteUrl("~/"));
                samlResponse.Issuer = issuer;
                samlResponse.Status = new Status(SamlPrimaryStatusCode.Success, null);

                Assertion samlAssertion = new Assertion();
                samlAssertion.Issuer = issuer;

                // Use the local user's local identity.
                Subject                 subject                 = new Subject(new NameId(User.Identity.Name));
                SubjectConfirmation     subjectConfirmation     = new SubjectConfirmation(SamlSubjectConfirmationMethod.Bearer);
                SubjectConfirmationData subjectConfirmationData = new SubjectConfirmationData();
                subjectConfirmationData.Recipient           = ConsumerServiceUrl;
                subjectConfirmation.SubjectConfirmationData = subjectConfirmationData;
                subject.SubjectConfirmations.Add(subjectConfirmation);
                samlAssertion.Subject = subject;

                // Create a new authentication statement.
                AuthnStatement authnStatement = new AuthnStatement();
                authnStatement.AuthnContext = new AuthnContext();
                authnStatement.AuthnContext.AuthnContextClassRef = new AuthnContextClassRef(SamlAuthenticateContext.Password);
                samlAssertion.Statements.Add(authnStatement);

                // If you need to add custom attributes, uncomment the following code
                // #region Custom Attributes
                // AttributeStatement attributeStatement = new AttributeStatement();
                // attributeStatement.Attributes.Add(new ComponentPro.Saml2.Attribute("email", SamlAttributeNameFormat.Basic, null,
                // "*****@*****.**"));
                // attributeStatement.Attributes.Add(new ComponentPro.Saml2.Attribute("FirstName", SamlAttributeNameFormat.Basic, null,
                // "John"));
                // attributeStatement.Attributes.Add(new ComponentPro.Saml2.Attribute("LastName", SamlAttributeNameFormat.Basic, null,
                // "Smith"));

                // // Insert a custom token key to the SAML response.
                // attributeStatement.Attributes.Add(new ComponentPro.Saml2.Attribute("CustomTokenForVerification", SamlAttributeNameFormat.Basic, null,
                // "YourEncryptedTokenHere"));

                // samlAssertion.Statements.Add(attributeStatement);
                // #endregion


                // Define ENCRYPTEDSAML preprocessor flag if you wish to encrypt the SAML response.
#if ENCRYPTEDSAML
                // Load the certificate for the encryption.
                // Please make sure the file is in the root directory.
                X509Certificate2 encryptingCert = new X509Certificate2(Path.Combine(HttpRuntime.AppDomainAppPath, "EncryptionX509Certificate.cer"), "password");

                // Create an encrypted SAML assertion from the SAML assertion we have created.
                EncryptedAssertion encryptedSamlAssertion = new EncryptedAssertion(samlAssertion, encryptingCert, new System.Security.Cryptography.Xml.EncryptionMethod(SamlKeyAlgorithm.TripleDesCbc));

                // Add encrypted assertion to the SAML response object.
                samlResponse.Assertions.Add(encryptedSamlAssertion);
#else
                // Add assertion to the SAML response object.
                samlResponse.Assertions.Add(samlAssertion);
#endif

                // Get the previously loaded certificate.
                X509Certificate2 x509Certificate = (X509Certificate2)Application[Global.CertKeyName];

                // Sign the SAML response with the certificate.
                samlResponse.Sign(x509Certificate);

                // Send the SAML response to the service provider.
                samlResponse.SendPostBindingForm(Response.OutputStream, ConsumerServiceUrl, targetUrl);
            }

            catch (Exception exception)
            {
                Trace.Write("IdentityProvider", "An Error occurred", exception);
            }
        }
示例#16
0
        /// <summary>
        /// Processes a successful SAML response and redirect to the requested URL.
        /// </summary>
        /// <param name="page">The page object.</param>
        /// <param name="samlResponse">The SAML response object.</param>
        /// <param name="relayState">The relay state.</param>
        public static void SamlSuccessRedirect(Page page, ComponentPro.Saml2.Response samlResponse, string relayState)
        {
            // Get the previously loaded certificate.
            X509Certificate2 x509Certificate = (X509Certificate2)page.Application[Global.SpCertKey];

            Assertion samlAssertion;

            // Check assertions.
            if (samlResponse.GetAssertions().Count > 0)
            {
                // Extract the first assertion.
                samlAssertion = samlResponse.GetAssertions()[0];
            }
            else if (samlResponse.GetEncryptedAssertions().Count > 0)
            {
                // Extract the first assertion.
                samlAssertion = samlResponse.GetEncryptedAssertions()[0].Decrypt(x509Certificate.PrivateKey, null);
            }
            else
            {
                throw new ApplicationException("No assertions in response");
            }

            string userName;

            // Get the subject name identifier.
            if (samlAssertion.Subject.NameId != null)
            {
                //userName = samlAssertion.Subject.NameId.NameIdentifier;
                userName = samlAssertion.GetAttributeValueByFriendlyName("eduPersonPrincipalName");

                System.Collections.Generic.Dictionary<string, string> dict = new System.Collections.Generic.Dictionary<string, string>();

                foreach (ComponentPro.Saml2.Attribute attribute in samlAssertion.AttributeStatements[0].Attributes)
                {
                    dict.Add(attribute.FriendlyName, attribute.Values[0].ToString());
                    System.Diagnostics.Trace.WriteLine(attribute.FriendlyName + ":" + attribute.Values[0].ToString());
                }
                HttpContext.Current.Session.Add("samlAttributes", dict);
            }
            else if (samlAssertion.Subject.EncryptedId != null)
            {
                NameId nameId = samlAssertion.Subject.EncryptedId.Decrypt(x509Certificate.PrivateKey, null);
                userName = nameId.NameIdentifier;
            }
            else
            {
                throw new ApplicationException("No name in subject");
            }


            try
            {
                string aaURL = "https://idp.testshib.org:8443/idp/profile/SAML2/SOAP/AttributeQuery";
                //Testing subject
                NameId subje = new NameId(userName,null,null,SamlNameIdentifierFormat.Unspecified,aaURL);
                
                //Testing subject
                Subject subject = new Subject(new NameId(userName));
                SubjectConfirmation subjectConfirmation = new SubjectConfirmation(SamlSubjectConfirmationMethod.Bearer);
                SubjectConfirmationData subjectConfirmationData = new SubjectConfirmationData();
                subjectConfirmationData.Recipient = aaURL;
                subjectConfirmation.SubjectConfirmationData = subjectConfirmationData;
                subject.SubjectConfirmations.Add(subjectConfirmation);

                AttributeQuery attributeQuery = new AttributeQuery();
                //attributeQuery.Subject = subject;
                attributeQuery.Destination = aaURL;
                attributeQuery.Issuer = new Issuer(Global.entityId);
                attributeQuery.Attributes.Add(new ComponentPro.Saml2.Attribute() { FriendlyName = "givenName" });
                attributeQuery.Subject = new Subject(samlAssertion.Subject.NameId);
                
                
                attributeQuery.Sign(x509Certificate);
                System.Diagnostics.Trace.WriteLine("Trying to get attributes from AA");
                System.Diagnostics.Trace.WriteLine("AA query " + attributeQuery.GetXml().OuterXml);
                System.Diagnostics.Trace.WriteLine("AA Subject " + attributeQuery.Subject.ToString());

                ArtifactResponse artifactResponse = ArtifactResponse.SendSamlMessageReceiveAftifactResponse(aaURL, attributeQuery);

                Response attrResponse;
                attrResponse = new ComponentPro.Saml2.Response(artifactResponse.Message);
                System.Diagnostics.Trace.WriteLine("AA reponse " + attrResponse.GetXml().OuterXml);

            }
            catch (Exception e)
            {
                System.Diagnostics.Trace.WriteLine("Execption: " + e.ToString());
                //throw;
            }
            // Get the originally requested resource URL from the relay state.
            string resourceUrl = (string)SamlSettings.CacheProvider.Remove(relayState);
            if (resourceUrl == null)
            {
                throw new ApplicationException("Invalid relay state");
            }

            // Create a login context for the asserted identity.
            FormsAuthentication.SetAuthCookie(userName, false);
            

            // Redirect to the originally requested resource URL.
            page.Response.Redirect(resourceUrl, false);
        }
示例#17
0
        protected override void OnLoad(System.EventArgs e)
        {
            base.OnLoad(e);

            try
            {
                // Look up for the SP ID
                string referer = this.Request.UrlReferrer.AbsoluteUri;
                int    i       = -1;
                if (!referer.StartsWith(Services.LocalUri))
                {
                    for (i = 0; i < Services.AllowedServiceUrls.Length; i++)
                    {
                        string url = Services.AllowedServiceUrls[i];

                        if (referer.StartsWith(url))
                        {
                            break;
                        }
                    }

                    if (i == Services.AllowedServiceUrls.Length)
                    {
                        throw new Exception("Your SP is not allowed");
                    }
                }

                // Get the saved SSO state, if any.
                // If there isn't saved state then receive the authentication request.
                // If there is saved state then we've just completed a local login in response
                // to a prior authentication request.
                SsoAuthnState ssoState = (SsoAuthnState)Session[SsoSessionKey];

                // Receive the authentication request.
                AuthnRequest authnRequest = null;
                string       relayState   = null;

                if (i != -1)
                {
                    Util.ReceiveAuthnRequest(this, out authnRequest, out relayState);

                    if (authnRequest == null)
                    {
                        // No authentication request found.
                        return;
                    }
                }

                if (ssoState == null)
                {
                    // Process the authentication request.
                    bool forceAuthn  = authnRequest.ForceAuthn;
                    bool allowCreate = false;

                    if (authnRequest.NameIdPolicy != null)
                    {
                        allowCreate = authnRequest.NameIdPolicy.AllowCreate;
                    }

                    ssoState = new SsoAuthnState();
                    ssoState.AuthnRequest                = authnRequest;
                    ssoState.RelayState                  = relayState;
                    ssoState.IdpProtocolBinding          = SamlBindingUri.UriToBinding(authnRequest.ProtocolBinding);
                    ssoState.AssertionConsumerServiceURL = authnRequest.AssertionConsumerServiceUrl;

                    // Determine whether or not a local login is required.
                    bool requireLocalLogin = false;

                    if (forceAuthn)
                    {
                        requireLocalLogin = true;
                    }
                    else
                    {
                        if (!User.Identity.IsAuthenticated & allowCreate)
                        {
                            requireLocalLogin = true;
                        }
                    }

                    // If a local login is required then save the authentication request
                    // and initiate a local login.
                    if (requireLocalLogin)
                    {
                        // Save the SSO state.
                        Session[SsoSessionKey] = ssoState;

                        // Initiate a local login.
                        System.Web.Security.FormsAuthentication.RedirectToLoginPage();
                        return;
                    }
                }

                // Create a SAML response with the user's local identity, if any.
                ComponentPro.Saml2.Response samlResponse = Util.CreateSamlResponse(this);

                if (i != -1)
                {
                    // Update the Relay state before sending SAML response.
                    // Dynamically update the assertion consumer service URL corresponding to the service provider.
                    ssoState.AssertionConsumerServiceURL = authnRequest.AssertionConsumerServiceUrl;
                }

                // Send the SAML response to the service provider.
                Util.SendSamlResponse(this, samlResponse, ssoState);
            }

            catch (Exception exception)
            {
                Trace.Write("IdentityProvider", "An Error occurred", exception);
            }
        }