/// <summary> /// Creates an artifact for the LogoutRequest and redirects the user to the IdP. /// </summary> /// <param name="destination">The destination of the request.</param> /// <param name="request">The logout request.</param> /// <param name="relayState">The query string relay state value (relayState) to add to the communication</param> public void RedirectFromLogout(IdentityProviderEndpoint destination, Saml20LogoutRequest request, string relayState, Action<string, object> cacheInsert) { var index = (short)config.ServiceProvider.Endpoints.DefaultLogoutEndpoint.Index; var doc = request.GetXml(); XmlSignatureUtils.SignDocument(doc, request.Request.Id, config.ServiceProvider.SigningCertificate); ArtifactRedirect(destination, index, doc, relayState, cacheInsert); }
/// <summary> /// Initializes a new instance of the <see cref="HttpPostBindingBuilder"/> class. /// </summary> /// <param name="endpoint">The IdP endpoint that messages will be sent to.</param> public HttpPostBindingBuilder(IdentityProviderEndpoint endpoint) { _destinationEndpoint = endpoint; Action = SamlActionType.SAMLRequest; RelayState = string.Empty; }
/// <summary> /// Handles all artifact creations and redirects. /// </summary> /// <param name="destination">The destination.</param> /// <param name="localEndpointIndex">Index of the local endpoint.</param> /// <param name="signedSamlMessage">The signed SAML message.</param> /// <param name="relayState">The query string relay state value to add to the communication</param> private void ArtifactRedirect(IdentityProviderEndpoint destination, short localEndpointIndex, XmlDocument signedSamlMessage, string relayState, Action<string, object> cacheInsert) { Logger.DebugFormat(TraceMessages.ArtifactRedirectReceived, signedSamlMessage.OuterXml); var sourceId = config.ServiceProvider.Id; var sourceIdHash = ArtifactUtil.GenerateSourceIdHash(sourceId); var messageHandle = ArtifactUtil.GenerateMessageHandle(); var artifact = ArtifactUtil.CreateArtifact(HttpArtifactBindingConstants.ArtifactTypeCode, localEndpointIndex, sourceIdHash, messageHandle); cacheInsert(artifact, signedSamlMessage); var destinationUrl = destination.Url + (destination.Url.Contains("?") ? "&" : "?") + HttpArtifactBindingConstants.ArtifactQueryStringName + "=" + Uri.EscapeDataString(artifact); if (!string.IsNullOrEmpty(relayState)) { destinationUrl += "&relayState=" + relayState; } Logger.DebugFormat(TraceMessages.ArtifactCreated, artifact); redirect(destinationUrl); }
/// <summary> /// Determine which endpoint to use based on the protocol defaults, configuration data and metadata. /// </summary> /// <param name="defaultBinding">The binding to use if none has been specified in the configuration and the metadata allows all bindings.</param> /// <param name="config">The endpoint as described in the configuration. May be null.</param> /// <param name="metadata">A list of endpoints of the given type (e.g. SSO or SLO) that the metadata contains.</param> /// <returns>The <see cref="IdentityProvider"/>.</returns> public static IdentityProviderEndpoint DetermineEndpointConfiguration(BindingType defaultBinding, IdentityProviderEndpoint config, List<IdentityProviderEndpoint> metadata) { var result = new IdentityProviderEndpoint { Binding = defaultBinding }; // Determine which binding to use. if (config != null) { result.Binding = config.Binding; } else { // Verify that the metadata allows the default binding. var allowed = metadata.Exists(el => el.Binding == defaultBinding); if (!allowed) { result.Binding = result.Binding == BindingType.Post ? BindingType.Redirect : BindingType.Post; } } if (config != null && !string.IsNullOrEmpty(config.Url)) { result.Url = config.Url; } else { var endpoint = metadata.Find(el => el.Binding == result.Binding); if (endpoint == null) { throw new FormatException(string.Format("No IdentityProvider supporting SAML binding {0} found in metadata", result.Binding)); } result.Url = endpoint.Url; } return result; }