SAML 2.0 C# - 验证SAML响应的问题

时间:2015-11-24 17:44:29

标签: c# .net certificate saml saml-2.0

我能够成功开发并使用IdP生成SAMLResponse,以将身份验证传递给第三方应用程序。但是,现在我需要创建一个服务提供程序来生成SAMLRequest并使用SAMLResponse。

SAMLRequest部分顺利进行,我能够通过SAMLRequest调用IdP,一旦身份验证成功,IdP就会向我发送SAMLResponse。我遇到问题的部分使用X509Certificate2验证SAMLResponse上的签名

经过广泛的谷歌搜索并跟随其他人的成功,这是我最接近的工作:

SamlSignedXml类

public class SamlSignedXml : SignedXml
{
    private string _referenceAttributeId = "";
    public SamlSignedXml(XmlElement element, string referenceAttributeId)
        : base(element)
    {
        _referenceAttributeId = referenceAttributeId;
    }
    public override XmlElement GetIdElement(XmlDocument document, string idValue)
    {
        return (XmlElement)document.SelectSingleNode(string.Format("//*[@{0}='{1}']", _referenceAttributeId, idValue));
    }
}

代码

String decodedSaml = SAMLResponse;
XmlDocument xmlDoc = new XmlDocument();
xmlDoc.PreserveWhitespace = true;
xmlDoc.Load(new StringReader(decodedSaml));
XmlNamespaceManager nSpace = new XmlNamespaceManager(xmlDoc.NameTable);
nSpace.AddNamespace("ds", SignedXml.XmlDsigNamespaceUrl);
XmlNodeList nodeList = xmlDoc.GetElementsByTagName("ds:Signature");
XmlElement signNode = (XmlElement)nodeList[0];
SamlSignedXml samlSignedXml = new SamlSignedXml((XmlElement)xmlDoc.DocumentElement, "ResponseID");
samlSignedXml.LoadXml((XmlElement)signNode);
X509Certificate2 certificate = new X509Certificate2("C:\\cert.crt");
bool samlValid = samlSignedXml.CheckSignature(certificate, true);

SAMLReponse

<?xml version="1.0" encoding="UTF-8"?>
<Response xmlns="urn:oasis:names:tc:SAML:2.0:protocol" IssueInstant="2015-11-24T15:57:26" ID="_388afdb8-1875-4c9f-a57b-d69983ad8489" Version="2.0">
   <Status>
      <StatusCode Value="urn:oasis:names:tc:SAML:2.0:status:Success" />
   </Status>
   <Assertion xmlns="urn:oasis:names:tc:SAML:2.0:assertion" ID="_c9cb5535-6350-4027-8357-bb39f5128564" IssueInstant="2015-11-24T15:57:26.395Z" Version="2.0">
      <Issuer>https://issuerwebsite.com</Issuer>
      <ds:Signature xmlns:ds="http://www.w3.org/2000/09/xmldsig#">
         <ds:SignedInfo>
            <ds:CanonicalizationMethod Algorithm="http://www.w3.org/2001/10/xml-exc-c14n#" />
            <ds:SignatureMethod Algorithm="http://www.w3.org/2000/09/xmldsig#rsa-sha1" />
            <ds:Reference URI="#_c9cb5535-6350-4027-8357-bb39f5128564">
               <ds:Transforms>
                  <ds:Transform Algorithm="http://www.w3.org/2000/09/xmldsig#enveloped-signature" />
                  <ds:Transform Algorithm="http://www.w3.org/2001/10/xml-exc-c14n#" />
               </ds:Transforms>
               <ds:DigestMethod Algorithm="http://www.w3.org/2000/09/xmldsig#sha1" />
               <ds:DigestValue>78xPMN/sD1QCbzf/h4VMkEHeOVY=</ds:DigestValue>
            </ds:Reference>
         </ds:SignedInfo>
         <ds:SignatureValue>tCyN+6vQP70TRyvZKtM788f90tqVGaQDXO1OotxXi7CRMBiFcQ1xZO4CERCV13dY4EfMy4GAZ27PARNTMwjyyp6SdlvDFffJwNOUydWM3jA9ab3xfp2U7eNWPBp7/fF6caAukl+O9H7Ou91bZVgHlEMfULhy8z2OlDcEeT6KiM2MGLRErfIy1YNeRcoKEtQABVwQYGppgNQcT1IZU0Z+8sF+NBUCiTuby2KUu5+S+M0guYP0encWEQsw2MaXXfiVGOpiZiPkEC01qTcFPu3z86sgc4nOtVlGqTlYMdpV/KWZGvmTc/n7m4rNZYEe3RwMzdBKtUwnyrnHOwf8hMP2cH7R2KDqmysUcq6Xz/mt5JwP7xeV599l8anSFPRME1SiST+VsHDn5hdgjvlqc2TY+baEYWBli8g+cwFrf4+u2X37DIaTBR+7njAfEEXF5EK3jM+hNdBVeaOJr4Ox4ic5FHOLRs7lU2AhbC12g4aZF3rKQRVGaQWgqVuwqJRu6APR3Yi7DwOjPDpiyRl4ZUTci/5EP10vR6D6MJ/ryIS1cz2iTfp6a/C8rc08e2gO+khlhRQ92hdeNV3BD9kaauafjgR5YM9GEkKpn8pQS0qzYKEkqrmMLUBYmxPgbFG4JFLRbhrwembi6UgpHYZs30wgRJ75+XGnsMoUYlIPSiNs6ak=</ds:SignatureValue>
         <KeyInfo xmlns="http://www.w3.org/2000/09/xmldsig#">
            <X509Data>
               <X509Certificate>XXXXXXXXXXXXXXXXXX</X509Certificate>
            </X509Data>
         </KeyInfo>
      </ds:Signature>
      <Subject>
         <NameID>P000037183</NameID>
         <SubjectConfirmation Method="urn:oasis:names:tc:SAML:2.0:cm:bearer" />
         <SubjectConfirmation Method="urn:oasis:names:tc:SAML:2.0:cm:bearer">
            <SubjectConfirmationData InResponseTo="somethinghere" NotOnOrAfter="2015-11-24T15:57:56.395Z" Recipient="http://localhost:62255/Auth.aspx" />
         </SubjectConfirmation>
      </Subject>
      <Conditions NotBefore="2015-11-24T15:57:26.395Z" NotOnOrAfter="2015-11-24T15:58:26.395Z">
         <AudienceRestriction>
            <Audience>http://localhost:62255/Auth.aspx</Audience>
         </AudienceRestriction>
      </Conditions>
      <AttributeStatement>
         <Attribute Name="xxid">
            <AttributeValue>1234</AttributeValue>
         </Attribute>
         <Attribute Name="firstName">
            <AttributeValue>Rafa</AttributeValue>
         </Attribute>
         <Attribute Name="lastName">
            <AttributeValue>Nadal</AttributeValue>
         </Attribute>
         <Attribute Name="emailAddress">
            <AttributeValue>rafa@atp.com</AttributeValue>
         </Attribute>
      </AttributeStatement>
      <AuthnStatement AuthnInstant="2015-11-24T15:57:26.395Z">
         <AuthnContext>
            <AuthnContextClassRef>urn:oasis:names:tc:SAML:2.0:ac:classes:Password</AuthnContextClassRef>
         </AuthnContext>
      </AuthnStatement>
   </Assertion>
</Response>

所以,如果我像这样运行它,我在调用CheckSignature时会收到以下错误:

  

格式错误的参考元素

我尝试将ResponseID更改为ID(因为它实际上是响应XML中的内容)并且我没有得到任何错误,但是,CheckSignature不返回任何内容,没有异常,没有真或假,函数在调用方法时返回。

嗯,这是我用我发现的例子做的最好的,所以如果你知道更好的方法来验证回复,我就等不及听了!

非常感谢。

0 个答案:

没有答案