private static XmlElement GenerateSignature() { Dictionary <string, string> attributes = new Dictionary <string, string>(); // Set Parameters to the method call to either the configuration value or a default value StoreLocation storeLocation = StoreLocation.LocalMachine; StoreName storeName = StoreName.Root; X509FindType findType = X509FindType.FindByThumbprint; string certFileLocation = @"D:\SslCertificates\SamRootCertificate.pfx"; string certPassword = null; string certFindKey = ""; bool signAssertion = false; SigningHelper.SignatureType signatureType = SigningHelper.SignatureType.Response; if (signAssertion) { signatureType = SigningHelper.SignatureType.Assertion; } return(GetSignature("RecipientWontok", "IssuerWontok", "DomainCom", "SubjectSecurity", storeLocation, storeName, findType, certFileLocation, certPassword, certFindKey, attributes, signatureType)); }
/// <summary> /// Call the Saml Helper Class and get the "Post" value, which can then be posted to the web page /// </summary> /// <param name="sender"></param> /// <param name="e"></param> public static string CreateSamlResponse(string recipient, string issuer, string domain, string subject, StoreLocation storeLocation, StoreName storeName, X509FindType findType, string certLocation, string certPassword, string certFindKey, Dictionary <string, string> attributes, string target) { string postData = ""; // Set Parameters to the method call to either the configuration value or a default value SigningHelper.SignatureType signatureType = SigningHelper.SignatureType.Response; postData = SamlHelper.GetPostSamlResponse(recipient, issuer, domain, subject, storeLocation, storeName, findType, certLocation, certPassword, certFindKey, attributes, signatureType); return(postData); }
/// <summary> /// GetPostSamlResponse - Returns a Base64 Encoded String with the SamlResponse in it. /// </summary> /// <param name="recipient">Recipient</param> /// <param name="issuer">Issuer</param> /// <param name="domain">Domain</param> /// <param name="subject">Subject</param> /// <param name="storeLocation">Certificate Store Location</param> /// <param name="storeName">Certificate Store Name</param> /// <param name="findType">Certificate Find Type</param> /// <param name="certLocation">Certificate Location</param> /// <param name="findValue">Certificate Find Value</param> /// <param name="certFile">Certificate File (used instead of the above Certificate Parameters)</param> /// <param name="certPassword">Certificate Password (used instead of the above Certificate Parameters)</param> /// <param name="attributes">A list of attributes to pass</param> /// <param name="signatureType">Whether to sign Response or Assertion</param> /// <returns>A base64Encoded string with a SAML response.</returns> public static string GetPostSamlResponse(string recipient, string issuer, string domain, string subject, StoreLocation storeLocation, StoreName storeName, X509FindType findType, string certFile, string certPassword, object findValue, Dictionary <string, string> attributes, SigningHelper.SignatureType signatureType) { ResponseType response = new ResponseType(); // Response Main Area response.ID = "_" + Guid.NewGuid().ToString(); response.Destination = recipient; response.Version = "2.0"; response.IssueInstant = System.DateTime.UtcNow; NameIDType issuerForResponse = new NameIDType(); issuerForResponse.Value = issuer.Trim(); response.Issuer = issuerForResponse; StatusType status = new StatusType(); status.StatusCode = new StatusCodeType(); status.StatusCode.Value = "urn:oasis:names:tc:SAML:2.0:status:Success"; response.Status = status; XmlSerializer responseSerializer = new XmlSerializer(response.GetType()); StringWriter stringWriter = new StringWriter(); XmlWriterSettings settings = new XmlWriterSettings(); settings.OmitXmlDeclaration = true; settings.Indent = true; settings.Encoding = Encoding.UTF8; XmlWriter responseWriter = XmlTextWriter.Create(stringWriter, settings); string samlString = string.Empty; AssertionType assertionType = SamlHelper.CreateSamlAssertion( issuer.Trim(), recipient.Trim(), domain.Trim(), subject.Trim(), attributes); response.Items = new AssertionType[] { assertionType }; responseSerializer.Serialize(responseWriter, response); responseWriter.Close(); samlString = stringWriter.ToString(); samlString = samlString.Replace("SubjectConfirmationData", string.Format("SubjectConfirmationData NotOnOrAfter=\"{0:o}\" Recipient=\"{1}\"", DateTime.UtcNow.AddMinutes(5), recipient)); stringWriter.Close(); XmlDocument doc = new XmlDocument(); doc.LoadXml(samlString); X509Certificate2 cert = null; if (System.IO.File.Exists(certFile)) { cert = new X509Certificate2(certFile, certPassword); } else { X509Store store = new X509Store(storeName, storeLocation); store.Open(OpenFlags.ReadOnly); X509Certificate2Collection coll = store.Certificates.Find(findType, findValue, true); if (coll.Count < 1) { throw new ArgumentException("Unable to locate certificate"); } cert = coll[0]; store.Close(); } XmlElement signature = SigningHelper.SignDoc(doc, cert, "ID", (signatureType == SigningHelper.SignatureType.Response || signatureType == SigningHelper.SignatureType.TestVU475445) ? response.ID : assertionType.ID); doc.DocumentElement.InsertBefore(signature, doc.DocumentElement.ChildNodes[1]); if (SamlHelper.Logger.IsDebugEnabled) { SamlHelper.Logger.DebugFormat( "Saml Assertion before encoding = {0}", doc.OuterXml.ToString()); } string responseStr = doc.OuterXml; // 2018Ma06 Special Post-signature Maniuplation postsignature to inject comment into subject. if (signatureType == SigningHelper.SignatureType.TestVU475445) { string sub = subject.Trim(); int half = sub.Length / 2; string firstHalf = sub.Substring(0, half); string secondHalf = sub.Substring(half); responseStr = responseStr.Replace(sub, firstHalf + "<!--VU475445-->" + secondHalf); int breaker = 1; } byte[] base64EncodedBytes = Encoding.UTF8.GetBytes(responseStr); string returnValue = System.Convert.ToBase64String( base64EncodedBytes); return(returnValue); }
public static XmlElement GetSignature(string recipient, string issuer, string domain, string subject, StoreLocation storeLocation, StoreName storeName, X509FindType findType, string certFile, string certPassword, object findValue, Dictionary <string, string> attributes, SigningHelper.SignatureType signatureType) { ResponseType response = new ResponseType(); // Response Main Area response.ID = "_" + Guid.NewGuid().ToString(); response.Destination = recipient; response.Version = "2.0"; response.IssueInstant = System.DateTime.UtcNow; NameIDType issuerForResponse = new NameIDType(); issuerForResponse.Value = issuer.Trim(); response.Issuer = issuerForResponse; StatusType status = new StatusType(); status.StatusCode = new StatusCodeType(); status.StatusCode.Value = "urn:oasis:names:tc:SAML:2.0:status:Success"; response.Status = status; XmlSerializer responseSerializer = new XmlSerializer(response.GetType()); StringWriter stringWriter = new StringWriter(); XmlWriterSettings settings = new XmlWriterSettings(); settings.OmitXmlDeclaration = true; settings.Indent = true; settings.Encoding = Encoding.UTF8; XmlWriter responseWriter = XmlTextWriter.Create(stringWriter, settings); string samlString = string.Empty; AssertionType assertionType = CreateSamlAssertion( issuer.Trim(), recipient.Trim(), domain.Trim(), subject.Trim(), attributes); response.Items = new AssertionType[] { assertionType }; responseSerializer.Serialize(responseWriter, response); responseWriter.Close(); samlString = stringWriter.ToString(); samlString = samlString.Replace("SubjectConfirmationData", string.Format("SubjectConfirmationData NotOnOrAfter=\"{0:o}\" Recipient=\"{1}\"", DateTime.UtcNow.AddMinutes(5), recipient)); stringWriter.Close(); XmlDocument doc = new XmlDocument(); doc.LoadXml(samlString); X509Certificate2 cert = null; cert = new X509Certificate2(certFile, certPassword); XmlElement signature = SigningHelper.SignDoc(doc, cert, "ID", signatureType == SigningHelper.SignatureType.Response ? response.ID : assertionType.ID); return(signature); }
/// <summary> /// Call the Saml Helper Class and get the "Post" value, which can then be posted to the web page /// </summary> /// <param name="sender"></param> /// <param name="e"></param> private void btnPostAssertion_Click(object sender, EventArgs e) { try { this.Cursor = Cursors.WaitCursor; // Set Attributes Dictionary <string, string> attributes = new Dictionary <string, string>(); foreach (ConfigurationData.AttributesRow row in configurationData.Attributes.Rows) { attributes.Add(row.Name, row.Value); } string postData = ""; // Set Parameters to the method call to either the configuration value or a default value StoreLocation storeLocation = configurationData.Configuration.Rows[0]["CertStoreLocation"].ToString().Length > 0 ? (StoreLocation)Enum.Parse(typeof(StoreLocation), configurationData.Configuration.Rows[0]["CertStoreLocation"].ToString()) : StoreLocation.LocalMachine; StoreName storeName = configurationData.Configuration.Rows[0]["CertStoreName"].ToString().Length > 0 ? (StoreName)Enum.Parse(typeof(StoreName), configurationData.Configuration.Rows[0]["CertStoreName"].ToString()) : StoreName.Root; X509FindType findType = configurationData.Configuration.Rows[0]["CertFindMethod"].ToString().Length > 0 ? (X509FindType)Enum.Parse(typeof(X509FindType), configurationData.Configuration.Rows[0]["CertFindMethod"].ToString()) : X509FindType.FindByThumbprint; string certFileLocation = configurationData.Configuration.Rows[0]["CertFileLocation"].ToString().Length > 0 ? configurationData.Configuration.Rows[0]["CertFileLocation"].ToString() : null; string certPassword = configurationData.Configuration.Rows[0]["CertPassword"].ToString().Length > 0 ? configurationData.Configuration.Rows[0]["CertPassword"].ToString() : null; string certFindKey = configurationData.Configuration.Rows[0]["CertFindKey"].ToString(); bool signResponse = this.rbSignResponse.Checked; bool signAssertion = this.rbSignAssertion.Checked; SigningHelper.SignatureType signatureType = SigningHelper.SignatureType.Response; if (signAssertion) { signatureType = SigningHelper.SignatureType.Assertion; } //if ( // Get SAML Post Value if (rb_v1.Checked) { postData = String.Format("SAMLResponse={0}&TARGET={1}", System.Web.HttpUtility.UrlEncode( davidsp8.common.Security.Saml11.SamlHelper.GetPostSamlResponse(txtRecipient.Text, txtIssuer.Text, txtDomain.Text, txtSubject.Text, storeLocation, storeName, findType, certFileLocation, certPassword, certFindKey, attributes, signatureType)), txtTarget.Text); } if (rb_v2.Checked) { postData = String.Format("SAMLResponse={0}&RelayState={1}", System.Web.HttpUtility.UrlEncode( davidsp8.common.Security.Saml20.SamlHelper.GetPostSamlResponse(txtRecipient.Text, txtIssuer.Text, txtDomain.Text, txtSubject.Text, storeLocation, storeName, findType, certFileLocation, certPassword, certFindKey, attributes, signatureType)), System.Web.HttpUtility.UrlEncode(txtTarget.Text)); } Logger.DebugFormat( "PostData = {0}", postData); webBrowser1.Navigate(this.txtRecipient.Text, "_self", Encoding.UTF8.GetBytes(postData), "Content-Type: application/x-www-form-urlencoded"); webBrowser1.Visible = true; webBrowser1.BringToFront(); btnShowBrowser.Text = "Hide Browser"; } catch (UriFormatException ex) { MessageBox.Show(ex.Message); } catch (Exception ex) { Logger.Error(ex.Message, ex); MessageBox.Show(ex.Message); } finally { this.Cursor = Cursors.Default; } }
/// <summary> /// /// </summary> /// <param name="UUID"></param> /// <param name="Destination"></param> /// <param name="ConsumerServiceURL"></param> /// <param name="certFile"></param> /// <param name="certPassword"></param> /// <param name="storeLocation"></param> /// <param name="storeName"></param> /// <param name="findType"></param> /// <param name="findValue"></param> /// <param name="signatureType"></param> /// <returns></returns> public static string BuildPostSamlRequest(string UUID, string Destination, string ConsumerServiceURL, int SecurityLevel, string certFile, string certPassword, StoreLocation storeLocation, StoreName storeName, X509FindType findType, object findValue, SigningHelper.SignatureType signatureType, string IdentityProvider, int Enviroment) { AuthnRequestType MyRequest = new AuthnRequestType { ID = UUID, Version = "2.0" }; DateTime now = DateTime.UtcNow; DateTime after = now.AddMinutes(10); string nowString = String.Empty; string afterString = String.Empty; if (IdentityProvider.Contains("sielte")) { // SIELTE nowString = now.AddMinutes(-2).ToString("yyyy'-'MM'-'dd'T'HH':'mm':'ss'Z'"); afterString = after.ToString("yyyy'-'MM'-'dd'T'HH':'mm':'ss'Z'"); } else { // POSTE - TIM - INFOCERT nowString = now.ToString("yyyy'-'MM'-'dd'T'HH':'mm':'ss'.'fff'Z'"); afterString = after.ToString("yyyy'-'MM'-'dd'T'HH':'mm':'ss'.'fff'Z'"); } MyRequest.IssueInstant = nowString; if (SecurityLevel > 1) { MyRequest.ForceAuthn = true; MyRequest.ForceAuthnSpecified = true; } MyRequest.Destination = Destination; MyRequest.AssertionConsumerServiceIndex = (ushort)Enviroment; MyRequest.AssertionConsumerServiceIndexSpecified = true; MyRequest.AttributeConsumingServiceIndex = 1; MyRequest.AttributeConsumingServiceIndexSpecified = true; NameIDType IssuerForRequest = new NameIDType { Value = ConsumerServiceURL.Trim(), Format = "urn:oasis:names:tc:SAML:2.0:nameid-format:entity", NameQualifier = ConsumerServiceURL }; MyRequest.Issuer = IssuerForRequest; NameIDPolicyType NameIdPolicyForRequest = new NameIDPolicyType { Format = "urn:oasis:names:tc:SAML:2.0:nameid-format:transient", AllowCreate = true, AllowCreateSpecified = true }; MyRequest.NameIDPolicy = NameIdPolicyForRequest; ConditionsType Conditional = new ConditionsType(); if (IdentityProvider.Contains("sielte")) { // SIELTE Conditional.NotBefore = nowString; } else { // POSTE - TIM - INFOCERT Conditional.NotBefore = now.AddMinutes(-2).ToString("yyyy'-'MM'-'dd'T'HH':'mm':'ss'.'fff'Z'"); } Conditional.NotBeforeSpecified = true; Conditional.NotOnOrAfter = afterString; Conditional.NotOnOrAfterSpecified = true; MyRequest.Conditions = Conditional; RequestedAuthnContextType RequestedAuthn = new RequestedAuthnContextType { Comparison = AuthnContextComparisonType.minimum, ComparisonSpecified = true, ItemsElementName = new ItemsChoiceType7[] { ItemsChoiceType7.AuthnContextClassRef }, Items = new string[] { "https://www.spid.gov.it/SpidL" + SecurityLevel.ToString() } }; MyRequest.RequestedAuthnContext = RequestedAuthn; XmlSerializerNamespaces ns = new XmlSerializerNamespaces(); ns.Add("saml2p", "urn:oasis:names:tc:SAML:2.0:protocol"); //ns.Add("saml2", "urn:oasis:names:tc:SAML:2.0:assertion"); XmlSerializer responseSerializer = new XmlSerializer(MyRequest.GetType()); StringWriter stringWriter = new StringWriter(); XmlWriterSettings settings = new XmlWriterSettings { OmitXmlDeclaration = true, Indent = true, Encoding = Encoding.UTF8 }; XmlWriter responseWriter = XmlTextWriter.Create(stringWriter, settings); responseSerializer.Serialize(responseWriter, MyRequest, ns); responseWriter.Close(); string samlString = string.Empty; samlString = stringWriter.ToString(); stringWriter.Close(); XmlDocument doc = new XmlDocument(); doc.LoadXml(samlString); X509Certificate2 cert = null; if (System.IO.File.Exists(certFile)) { cert = new X509Certificate2(certFile, certPassword); } else { X509Store store = new X509Store(storeName, storeLocation); store.Open(OpenFlags.ReadOnly | OpenFlags.OpenExistingOnly); X509Certificate2Collection CertCol = store.Certificates; X509Certificate2Collection coll = store.Certificates.Find(findType, findValue.ToString(), false); if (coll.Count < 1) { throw new ArgumentException("Unable to locate certificate"); } cert = coll[0]; store.Close(); } XmlElement signature = SigningHelper.SignDoc(doc, cert, UUID); doc.DocumentElement.InsertBefore(signature, doc.DocumentElement.ChildNodes[1]); string responseStr = doc.OuterXml; //byte[] base64EncodedBytes = // Encoding.UTF8.GetBytes(responseStr); //string returnValue = System.Convert.ToBase64String( // base64EncodedBytes); return("<?xml version=\"1.0\" encoding=\"UTF-8\"?>" + responseStr); }
/// <summary> /// GetPostSamlResponse - Returns a Base64 Encoded String with the SamlResponse in it. /// </summary> /// <param name="recipient">Recipient</param> /// <param name="issuer">Issuer</param> /// <param name="domain">Domain</param> /// <param name="subject">Subject</param> /// <param name="storeLocation">Certificate Store Location</param> /// <param name="storeName">Certificate Store Name</param> /// <param name="findType">Certificate Find Type</param> /// <param name="certLocation">Certificate Location</param> /// <param name="findValue">Certificate Find Value</param> /// <param name="certFile">Certificate File (used instead of the above Certificate Parameters)</param> /// <param name="certPassword">Certificate Password (used instead of the above Certificate Parameters)</param> /// <param name="attributes">A list of attributes to pass</param> /// <param name="signatureType">Whether to sign Response or Assertion</param> /// <returns>A base64Encoded string with a SAML response.</returns> public static string BuildPostSamlResponse(string recipient, string issuer, string domain, string subject, StoreLocation storeLocation, StoreName storeName, X509FindType findType, string certFile, string certPassword, object findValue, Dictionary <string, string> attributes, SigningHelper.SignatureType signatureType) { ResponseType response = new ResponseType { // Response Main Area ID = "_" + Guid.NewGuid().ToString(), Destination = recipient, Version = "2.0", IssueInstant = DateTime.UtcNow }; NameIDType issuerForResponse = new NameIDType { Value = issuer.Trim() }; response.Issuer = issuerForResponse; StatusType status = new StatusType { StatusCode = new StatusCodeType() }; status.StatusCode.Value = "urn:oasis:names:tc:SAML:2.0:status:Success"; response.Status = status; XmlSerializerNamespaces ns = new XmlSerializerNamespaces(); ns.Add("saml2p", "urn:oasis:names:tc:SAML:2.0:protocol"); ns.Add("saml2", "urn:oasis:names:tc:SAML:2.0:assertion"); XmlSerializer responseSerializer = new XmlSerializer(response.GetType()); StringWriter stringWriter = new StringWriter(); XmlWriterSettings settings = new XmlWriterSettings { OmitXmlDeclaration = true, Indent = true, Encoding = Encoding.UTF8 }; XmlWriter responseWriter = XmlWriter.Create(stringWriter, settings); string samlString = string.Empty; AssertionType assertionType = Saml2Helper.CreateSamlAssertion( issuer.Trim(), recipient.Trim(), domain.Trim(), subject.Trim(), attributes); response.Items = new AssertionType[] { assertionType }; responseSerializer.Serialize(responseWriter, response, ns); responseWriter.Close(); samlString = stringWriter.ToString(); samlString = samlString.Replace("SubjectConfirmationData", string.Format("SubjectConfirmationData NotOnOrAfter=\"{0:o}\" Recipient=\"{1}\"", DateTime.UtcNow.AddMinutes(5), recipient)); samlString = samlString.Replace("<saml2:Assertion ", "<saml2:Assertion xmlns:saml2=\"urn:oasis:names:tc:SAML:2.0:assertion\" "); samlString = samlString.Replace("<saml2:AuthnContextClassRef>AuthnContextClassRef</saml2:AuthnContextClassRef>", "<saml2:AuthnContextClassRef>" + issuer + "</saml2:AuthnContextClassRef>"); stringWriter.Close(); XmlDocument doc = new XmlDocument(); doc.LoadXml(samlString); X509Certificate2 cert = null; if (System.IO.File.Exists(certFile)) { cert = new X509Certificate2(certFile, certPassword); } else { X509Store store = new X509Store(storeName, storeLocation); store.Open(OpenFlags.ReadOnly | OpenFlags.OpenExistingOnly); X509Certificate2Collection CertCol = store.Certificates; //foreach (X509Certificate2 c in CertCol) //{ // if (c.Subject.Contains(findValue.ToString())) // { // cert = c; // break; // } //} X509Certificate2Collection coll = store.Certificates.Find(findType, findValue.ToString(), false); //if (cert == null) //{ // throw new ArgumentException("Unable to locate certificate"); //} if (coll.Count < 1) { throw new ArgumentException("Unable to locate certificate"); } cert = coll[0]; store.Close(); } XmlElement signature = SigningHelper.SignDoc(doc, cert, response.ID); doc.DocumentElement.InsertBefore(signature, doc.DocumentElement.ChildNodes[1]); string responseStr = doc.OuterXml; byte[] base64EncodedBytes = Encoding.UTF8.GetBytes(responseStr); string returnValue = System.Convert.ToBase64String( base64EncodedBytes); return(returnValue); }
/// <summary> /// GetPostSamlResponse - Returns a Base64 Encoded String with the SamlResponse in it. /// </summary> /// <param name="recipient">Recipient</param> /// <param name="issuer">Issuer</param> /// <param name="domain">Domain</param> /// <param name="subject">Subject</param> /// <param name="storeLocation">Certificate Store Location</param> /// <param name="storeName">Certificate Store Name</param> /// <param name="findType">Certificate Find Type</param> /// <param name="certLocation">Certificate Location</param> /// <param name="findValue">Certificate Find Value</param> /// <param name="certFile">Certificate File (used instead of the above Certificate Parameters)</param> /// <param name="certPassword">Certificate Password (used instead of the above Certificate Parameters)</param> /// <param name="attributes">A list of attributes to pass</param> /// <param name="signatureType">Whether to sign Response or Assertion</param> /// <returns>A base64Encoded string with a SAML response.</returns> public static string GetPostSamlResponse(string recipient, string issuer, string subject, string audience, string requestid, string nameIdPolicyFormat, StoreLocation storeLocation, StoreName storeName, X509FindType findType, string certFile, string certPassword, object findValue, Dictionary <string, string> attributes, SigningHelper.SignatureType signatureType, Models.IdPOptionsModel options) { ResponseType response = new ResponseType(); // Response Main Area response.ID = "_" + Guid.NewGuid().ToString("N"); response.Destination = recipient; response.Version = "2.0"; response.IssueInstant = System.DateTime.UtcNow; response.InResponseTo = requestid; NameIDType issuerForResponse = new NameIDType(); issuerForResponse.Value = issuer.Trim(); response.Issuer = issuerForResponse; StatusType status = new StatusType(); status.StatusCode = new StatusCodeType(); status.StatusCode.Value = "urn:oasis:names:tc:SAML:2.0:status:Success"; response.Status = status; XmlSerializerNamespaces ns = new XmlSerializerNamespaces(); if (options.UseNamespaces) { ns.Add("saml2p", "urn:oasis:names:tc:SAML:2.0:protocol"); ns.Add("saml2", "urn:oasis:names:tc:SAML:2.0:assertion"); ns.Add("ds", "http://www.w3.org/2000/09/xmldsig#"); } XmlSerializer responseSerializer = new XmlSerializer(response.GetType()); StringWriter stringWriter = new StringWriter(); XmlWriterSettings settings = new XmlWriterSettings(); settings.Encoding = Encoding.UTF8; settings.OmitXmlDeclaration = true; settings.Indent = true; XmlWriter responseWriter = XmlTextWriter.Create(stringWriter, settings); string samlString = string.Empty; AssertionType assertionType = SamlHelper.CreateSamlAssertion( issuer.Trim(), recipient.Trim(), subject.Trim(), audience.Trim(), nameIdPolicyFormat, attributes); response.Items = new AssertionType[] { assertionType }; responseSerializer.Serialize(responseWriter, response, ns); responseWriter.Close(); samlString = stringWriter.ToString(); samlString = samlString.Replace("SubjectConfirmationData", string.Format("SubjectConfirmationData NotOnOrAfter=\"{0:o}\" Recipient=\"{1}\" InResponseTo=\"{2:D}\" ", DateTime.UtcNow.AddMinutes(5), recipient, requestid)); stringWriter.Close(); XmlDocument doc = new XmlDocument(); //doc.LoadXml(samlString); byte[] samlBytes = Encoding.UTF8.GetBytes(samlString); var ms = new MemoryStream(samlBytes); doc.Load(ms); X509Certificate2 cert = null; if (System.IO.File.Exists(certFile)) { try { cert = new X509Certificate2(certFile, certPassword); } catch (Exception ex) { ; } } else { X509Store store = new X509Store(storeName, storeLocation); store.Open(OpenFlags.ReadOnly); X509Certificate2Collection coll = store.Certificates.Find(findType, findValue, false); if (coll.Count < 1) { throw new ArgumentException("Unable to locate certificate"); } cert = coll[0]; store.Close(); } XmlElement signature = SigningHelper.SignDoc(doc, cert, "ID", signatureType == SigningHelper.SignatureType.Response ? response.ID : assertionType.ID, options); doc.DocumentElement.InsertBefore(signature, doc.DocumentElement.ChildNodes[1]); if (SamlHelper.Logger.IsDebugEnabled) { SamlHelper.Logger.DebugFormat( "Saml Assertion before encoding = {0}", doc.OuterXml.ToString()); } //string responseStr = doc.OuterXml; //byte[] base64EncodedBytes = // Encoding.UTF8.GetBytes(responseStr); if (options.IncludeXmlDeclaration) { //Create an XML declaration. XmlDeclaration xmldecl; xmldecl = doc.CreateXmlDeclaration("1.0", "UTF-8", "no"); //Add the new node to the document. XmlElement root = doc.DocumentElement; doc.InsertBefore(xmldecl, root); } byte[] base64EncodedBytes = Encoding.UTF8.GetBytes(doc.OuterXml); string returnValue = System.Convert.ToBase64String( base64EncodedBytes); return(returnValue); }
public ActionResult Signin(Models.IdPOptionsModel options) { string requestId = Session["requestId"].ToString(); string requestVersion = Session["requestVersion"].ToString(); string requestIssuesInstant = Session["requestIssueInstant"].ToString(); string requestIssuer = Session["requestIssuer"].ToString(); string nameIdPolicyFormat = Session["nameIdPolicyFormat"].ToString(); string RelayState = Session["RelayState"].ToString(); string username = Session["username"].ToString(); int spId = Convert.ToInt32(Session["spId"]); SigningHelper.SignatureType signatureType = SigningHelper.SignatureType.Response; if (options.SignAssertion) { signatureType = SigningHelper.SignatureType.Assertion; } string strRecipient = Properties.Settings.Default.Recipient; string strIssuer = Properties.Settings.Default.Issuer; string strSubject = username; string strAudience = requestIssuer; // Set Parameters to the method call to either the configuration value or a default value StoreLocation storeLocation = StoreLocation.CurrentUser; StoreName storeName = StoreName.My; X509FindType findType = X509FindType.FindByThumbprint; string certFileLocation = ""; string certPassword = Properties.Settings.Default.CertPassword; string certFindKey = Properties.Settings.Default.CertThumbprint; Dictionary <string, string> attributes = new Dictionary <string, string>(); attributes.Add("IDPEmail", username); string stringSamlResponse = ""; try { stringSamlResponse = SamlHelper.GetPostSamlResponse(strRecipient, strIssuer, strSubject, strAudience, requestId, nameIdPolicyFormat, storeLocation, storeName, findType, certFileLocation, certPassword, certFindKey, attributes, signatureType, options); if (options.UrlEncodeSamlResponse) { stringSamlResponse = System.Web.HttpUtility.UrlEncode(stringSamlResponse); } } catch (Exception ex) { ViewData["Error"] = ex.ToString(); } Logger.DebugFormat( "PostData = {0}", stringSamlResponse); // var model = new Models.SAMLResponseModel(); model.SAMLResponse = stringSamlResponse; if (options.EchoRelayState) { if (options.UrlEncodeRelayState) { model.RelayState = System.Web.HttpUtility.UrlEncode(RelayState); } else { model.RelayState = RelayState; } } else { //send hardcoded value back model.RelayState = "idp.technicality.online"; if (options.UrlEncodeRelayState) { model.RelayState = System.Web.HttpUtility.UrlEncode(model.RelayState); } } if (spId == 1) { // return to TestSP URL model.Destination = Properties.Settings.Default.TestSPUrl; } else { model.Destination = strRecipient; } if (options.SetHeaderToUrlEncoded) { model.Enctype = "application/x-www-form-urlencoded"; } else { model.Enctype = "multipart/form-data"; } ViewData.Model = model; return(View("SamlResponse")); }
/// <summary> /// Returns a Base64 Encoded String with the SamlResponse in it. /// </summary> /// <param name="recipient">Recipient</param> /// <param name="issuer">Issuer</param> /// <param name="subject">Subject</param> /// <param name="certLocation">Certificate Location</param> /// <param name="certPassword">Certificate Password</param> /// <param name="attributes">A list of attributes to pass</param> /// <returns></returns> public static string GetPostSamlResponse(string recipient, string issuer, string domain, string subject, StoreLocation storeLocation, StoreName storeName, X509FindType findType, string certFile, string certPassword, object findValue, Dictionary <string, string> attributes, SigningHelper.SignatureType signatureType) { ResponseType response = new ResponseType(); // Create Response response.ResponseID = "_" + Guid.NewGuid().ToString(); response.MajorVersion = "1"; response.MinorVersion = "1"; response.IssueInstant = System.DateTime.UtcNow; response.Recipient = recipient; StatusType status = new StatusType(); status.StatusCode = new StatusCodeType(); status.StatusCode.Value = new XmlQualifiedName("Success", "urn:oasis:names:tc:SAML:1.0:protocol"); response.Status = status; // Create Assertion AssertionType assertionType = SamlHelper.CreateSaml11Assertion( issuer.Trim(), domain.Trim(), subject.Trim(), attributes); response.Assertion = new AssertionType[] { assertionType }; //Serialize XmlSerializerNamespaces ns = new XmlSerializerNamespaces(); ns.Add("samlp", "urn:oasis:names:tc:SAML:1.0:protocol"); ns.Add("saml", "urn:oasis:names:tc:SAML:1.0:assertion"); XmlSerializer responseSerializer = new XmlSerializer(response.GetType()); StringWriter stringWriter = new StringWriter(); XmlWriterSettings settings = new XmlWriterSettings(); settings.OmitXmlDeclaration = true; settings.Indent = true; settings.Encoding = Encoding.UTF8; XmlWriter responseWriter = XmlTextWriter.Create(stringWriter, settings); responseSerializer.Serialize(responseWriter, response, ns); responseWriter.Close(); string samlString = stringWriter.ToString(); stringWriter.Close(); // Sign the document XmlDocument doc = new XmlDocument(); doc.LoadXml(samlString); X509Certificate2 cert = null; if (System.IO.File.Exists(certFile)) { cert = new X509Certificate2(certFile, certPassword); } else { X509Store store = new X509Store(storeName, storeLocation); store.Open(OpenFlags.ReadOnly); X509Certificate2Collection coll = store.Certificates.Find(findType, findValue, true); if (coll.Count < 1) { throw new ArgumentException("Unable to locate certificate"); } cert = coll[0]; store.Close(); } XmlElement signature = SigningHelper.SignDoc( doc, cert, "ResponseID", response.ResponseID); doc.DocumentElement.InsertBefore(signature, doc.DocumentElement.ChildNodes[0]); if (SamlHelper.Logger.IsDebugEnabled) { SamlHelper.Logger.DebugFormat( "Saml Assertion before encoding = {0}", doc.OuterXml.ToString()); } // Base64Encode and URL Encode byte[] base64EncodedBytes = Encoding.UTF8.GetBytes(doc.OuterXml); string returnValue = System.Convert.ToBase64String( base64EncodedBytes); return(returnValue); }