JavaEar 专注于收集分享传播有价值的技术资料

How to specify the location of the signature in an xml document BEFORE computing the signature?

问题描述


英文原文

When trying to sign an xml request using SignedXml in C# , I am able to generate the signature and the signed xml request, but I am getting a failure message from my webservice when I am sending this message. The error states: data and digestvalue do not match.

Digging deeper, I checked an equivalent code we have that was developed in Java. The xml signed request that code is generating has a different digest value than what my C# code is generating, and the Java code gets a success message from the webservice.

After a lot of discussion and analysing using a test tool provided with my webservice, we understand this: the Digest Value changes depending upon where you specify the location of the Digital Signature in your request BEFORE you use ComputeSignature(). But I am unable to find a way by which you can specify the location BEFORE computing the signature. Here's my code:

        /*=================*/
        //CODE to remove whitespaces from the xml before building the xmlDocument

        String thisLine = "";
        String xmlString = "";
        StreamReader br = new StreamReader(Server.MapPath("~/" + fp));
        while ((thisLine = br.ReadLine()) != null)
        {
            xmlString = xmlString + thisLine.Trim();
        }
        br.Close();
        Debug.WriteLine("new logic: " + xmlString);


        XmlDocument xmlDocument = new XmlDocument();
           xmlDocument.LoadXml(xmlString);

        /*================*/





        SignedXml signedXml = new SignedXml(xmlDocument);

        //XmlDsigExcC14NTransformUrl
        signedXml.SignedInfo.CanonicalizationMethod =                SignedXml.XmlDsigC14NTransformUrl;
        signedXml.SigningKey = cert.PrivateKey;

        signedXml.KeyInfo.AddClause(new System.Security.Cryptography.Xml.KeyInfoX509Data(cert));


        Reference tRef = new Reference("");
        /*
                    XmlDsigExcC14NTransform env = new XmlDsigExcC14NTransform();
                    //Transform transf = new XmlDsigEnvelopedSignatureTransform(false);
                    tRef.AddTransform(transf);
                    */

        XmlDsigEnvelopedSignatureTransform env = new XmlDsigEnvelopedSignatureTransform();
        tRef.AddTransform(env);


        signedXml.AddReference(tRef);
        signedXml.ComputeSignature();




        XmlElement xmlDsig = signedXml.GetXml();
        xmlDsig.SetAttribute("Id", "Signature-1");

        XmlElement rootNode = xmlDocument.DocumentElement;
        rootNode.AppendChild(xmlDsig);

        XmlTextWriter w = new XmlTextWriter(Server.MapPath("~/attrdigsig2.xml"), new UTF8Encoding(false));
        w.Formatting = Formatting.Indented;

        xmlDocument.WriteTo(w);
        w.Close();

Here's the signed request I am getting:

<?xml version="1.0" encoding="utf-8"?>
<ns:User xmlns:ns="http://www.user.com">
  <ns:Username>1DDOagUser</ns:Username>
  <ns:Password>toyota12</ns:Password>
  <Signature Id="Signature-1" xmlns="http://www.w3.org/2000/09/xmldsig#">
    <SignedInfo>
      <CanonicalizationMethod Algorithm="http://www.w3.org/TR/2001/REC-xml-c14n-20010315" />
      <SignatureMethod Algorithm="http://www.w3.org/2000/09/xmldsig#rsa-sha1" />
      <Reference URI="">
        <Transforms>
          <Transform Algorithm="http://www.w3.org/2000/09/xmldsig#enveloped-signature" />
        </Transforms>
        <DigestMethod Algorithm="http://www.w3.org/2000/09/xmldsig#sha1" />
        <DigestValue>KEqvZWvpT3yYqMMJSTBmUKNIQw4=</DigestValue>
      </Reference>
    </SignedInfo>
    <SignatureValue>YQ+81KnxwM9RibFpmS48Gbfdv7gBxgXrH6XWdoF+OZaUq+uJOOcuuC9KNmC4pkMs0V/LEw2WI6zjs9ML8kxAx3vcU/8jZ9/b8Z1EK7ndCcqDvkfBUpltHQy9FyP3AQyeFyK0SFvcyJCxvetc7uoJgYDvKUVU/ydqolw2ZbOXCHvN34SwbqGgGlBed++I7yk7KWIOWXsfjdSVwkuIyvEuVwxCmHHhxgjjfVaPnJMBY3D1Ali28d+rwKphT3dXdroEjXIedIK6lkrNOlHsaWZGYgJxNN08nN8bnNCe9QXapzHysSLnc3tkbJ1i2KjVHpLxwDfxFuuhWxh2sCKCoNvLgA==</SignatureValue>
    <KeyInfo>
      <X509Data>
        <X509Certificate>MIIC0TCCAbmgAwIBAgIGATDa3Nm5MA0GCSqGSIb3DQEBBQUAMBgxFjAUBgNVBAMTDVNPQVBCb3hDb25maWcwHhcNMDgwNjE4MTAyODAwWhcNMjEwNjE4MTAyODAwWjAYMRYwFAYDVQQDEw1TT0FQQm94Q29uZmlnMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEApLw4QAWqVmEr+CEo8Fp8WPq9Oo7BdnNOtMT5sUp0IN4NVvKmdI8ju3HsbnXzI7csNDzK6Feo19J/XLZk/Lr3Q4bLmmD+bMLFljiIgQ89+Bwc3mtyT1Rr4WBQUKnF8+8y65m2RebySelzgWIeZM72JoThSw85VBtyHvjlQnTAnfwX0NV7mH+kbQDi0c4Q4UZhKWFfb5L2tbjcknsG0k4De07qIw+RsGipkuNoFyI6BwwC0IERv48sacL30nWAOZMNDkm4S61aAYuzfMZySzPseU6BUdIdYAnITgj4tHRJZ93OYnn6LObEkYxobyGi6SULtBQQYzHKgeeyvru2Z1L7nQIDAQABoyEwHzAdBgNVHQ4EFgQUjq3/y0NF+tlUqwLc8SP4uV4/PK4wDQYJKoZIhvcNAQEFBQADggEBAAJvxTw5cc/32ahQ2TlBCrBNeHvji4QYItimkoqQa1EMyBSnx1FXNRyfJ9Da/20ZdIvIfJvIozIU0V/iFd7Hi+a2bZeMkN/ofvUh3QchHfkP/718JhcIvug3fctUX27ENHLRRU/rzMvKg40+H9BJoos6lu7qgAyayCRgKR5A/U3cSE9ZrYMGBNqy/mSIscZXhDJw0KATLHircXwRjpN+0lk+7/df5T8tc8wJOIvETCfDaQlDzXHw4jhQFydloMY4Tm4//VZTVVh1nzt2rVv52pHZGP8Shb9e5qS/QicBTVqysyVQEpYktRrrTwZcbq/65sV0lOao2JzZOuj3qvdJ4kw=</X509Certificate>
      </X509Data>
    </KeyInfo>
  </Signature>
</ns:User>

Digest Value I am getting: KEqvZWvpT3yYqMMJSTBmUKNIQw4=

Correct Digest Value (The one that's being generated by the Java code and getting success response from the webservice):aa4phJzO4YWc2ZQ1CG8HZ4cB1SA=

Remarks: The xml that is to be signed is a normal xml and not a SOAP xml request. I used the same signing logic for the SOAP xml request and the response generated by it was accepted by the web-service(The web-service contains both the methods: 1 for normal xml request and 1 for soap xml request).


中文翻译

When trying to sign an xml request using SignedXml in C# , I am able to generate the signature and the signed xml request, but I am getting a failure message from my webservice when I am sending this message. The error states: data and digestvalue do not match.

Digging deeper, I checked an equivalent code we have that was developed in Java. The xml signed request that code is generating has a different digest value than what my C# code is generating, and the Java code gets a success message from the webservice.

After a lot of discussion and analysing using a test tool provided with my webservice, we understand this: the Digest Value changes depending upon where you specify the location of the Digital Signature in your request BEFORE you use ComputeSignature(). But I am unable to find a way by which you can specify the location BEFORE computing the signature. Here's my code:

        /*=================*/
        //CODE to remove whitespaces from the xml before building the xmlDocument

        String thisLine = "";
        String xmlString = "";
        StreamReader br = new StreamReader(Server.MapPath("~/" + fp));
        while ((thisLine = br.ReadLine()) != null)
        {
            xmlString = xmlString + thisLine.Trim();
        }
        br.Close();
        Debug.WriteLine("new logic: " + xmlString);


        XmlDocument xmlDocument = new XmlDocument();
           xmlDocument.LoadXml(xmlString);

        /*================*/





        SignedXml signedXml = new SignedXml(xmlDocument);

        //XmlDsigExcC14NTransformUrl
        signedXml.SignedInfo.CanonicalizationMethod =                SignedXml.XmlDsigC14NTransformUrl;
        signedXml.SigningKey = cert.PrivateKey;

        signedXml.KeyInfo.AddClause(new System.Security.Cryptography.Xml.KeyInfoX509Data(cert));


        Reference tRef = new Reference("");
        /*
                    XmlDsigExcC14NTransform env = new XmlDsigExcC14NTransform();
                    //Transform transf = new XmlDsigEnvelopedSignatureTransform(false);
                    tRef.AddTransform(transf);
                    */

        XmlDsigEnvelopedSignatureTransform env = new XmlDsigEnvelopedSignatureTransform();
        tRef.AddTransform(env);


        signedXml.AddReference(tRef);
        signedXml.ComputeSignature();




        XmlElement xmlDsig = signedXml.GetXml();
        xmlDsig.SetAttribute("Id", "Signature-1");

        XmlElement rootNode = xmlDocument.DocumentElement;
        rootNode.AppendChild(xmlDsig);

        XmlTextWriter w = new XmlTextWriter(Server.MapPath("~/attrdigsig2.xml"), new UTF8Encoding(false));
        w.Formatting = Formatting.Indented;

        xmlDocument.WriteTo(w);
        w.Close();

Here's the signed request I am getting:

<?xml version="1.0" encoding="utf-8"?>
<ns:User xmlns:ns="http://www.user.com">
  <ns:Username>1DDOagUser</ns:Username>
  <ns:Password>toyota12</ns:Password>
  <Signature Id="Signature-1" xmlns="http://www.w3.org/2000/09/xmldsig#">
    <SignedInfo>
      <CanonicalizationMethod Algorithm="http://www.w3.org/TR/2001/REC-xml-c14n-20010315" />
      <SignatureMethod Algorithm="http://www.w3.org/2000/09/xmldsig#rsa-sha1" />
      <Reference URI="">
        <Transforms>
          <Transform Algorithm="http://www.w3.org/2000/09/xmldsig#enveloped-signature" />
        </Transforms>
        <DigestMethod Algorithm="http://www.w3.org/2000/09/xmldsig#sha1" />
        <DigestValue>KEqvZWvpT3yYqMMJSTBmUKNIQw4=</DigestValue>
      </Reference>
    </SignedInfo>
    <SignatureValue>YQ+81KnxwM9RibFpmS48Gbfdv7gBxgXrH6XWdoF+OZaUq+uJOOcuuC9KNmC4pkMs0V/LEw2WI6zjs9ML8kxAx3vcU/8jZ9/b8Z1EK7ndCcqDvkfBUpltHQy9FyP3AQyeFyK0SFvcyJCxvetc7uoJgYDvKUVU/ydqolw2ZbOXCHvN34SwbqGgGlBed++I7yk7KWIOWXsfjdSVwkuIyvEuVwxCmHHhxgjjfVaPnJMBY3D1Ali28d+rwKphT3dXdroEjXIedIK6lkrNOlHsaWZGYgJxNN08nN8bnNCe9QXapzHysSLnc3tkbJ1i2KjVHpLxwDfxFuuhWxh2sCKCoNvLgA==</SignatureValue>
    <KeyInfo>
      <X509Data>
        <X509Certificate>MIIC0TCCAbmgAwIBAgIGATDa3Nm5MA0GCSqGSIb3DQEBBQUAMBgxFjAUBgNVBAMTDVNPQVBCb3hDb25maWcwHhcNMDgwNjE4MTAyODAwWhcNMjEwNjE4MTAyODAwWjAYMRYwFAYDVQQDEw1TT0FQQm94Q29uZmlnMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEApLw4QAWqVmEr+CEo8Fp8WPq9Oo7BdnNOtMT5sUp0IN4NVvKmdI8ju3HsbnXzI7csNDzK6Feo19J/XLZk/Lr3Q4bLmmD+bMLFljiIgQ89+Bwc3mtyT1Rr4WBQUKnF8+8y65m2RebySelzgWIeZM72JoThSw85VBtyHvjlQnTAnfwX0NV7mH+kbQDi0c4Q4UZhKWFfb5L2tbjcknsG0k4De07qIw+RsGipkuNoFyI6BwwC0IERv48sacL30nWAOZMNDkm4S61aAYuzfMZySzPseU6BUdIdYAnITgj4tHRJZ93OYnn6LObEkYxobyGi6SULtBQQYzHKgeeyvru2Z1L7nQIDAQABoyEwHzAdBgNVHQ4EFgQUjq3/y0NF+tlUqwLc8SP4uV4/PK4wDQYJKoZIhvcNAQEFBQADggEBAAJvxTw5cc/32ahQ2TlBCrBNeHvji4QYItimkoqQa1EMyBSnx1FXNRyfJ9Da/20ZdIvIfJvIozIU0V/iFd7Hi+a2bZeMkN/ofvUh3QchHfkP/718JhcIvug3fctUX27ENHLRRU/rzMvKg40+H9BJoos6lu7qgAyayCRgKR5A/U3cSE9ZrYMGBNqy/mSIscZXhDJw0KATLHircXwRjpN+0lk+7/df5T8tc8wJOIvETCfDaQlDzXHw4jhQFydloMY4Tm4//VZTVVh1nzt2rVv52pHZGP8Shb9e5qS/QicBTVqysyVQEpYktRrrTwZcbq/65sV0lOao2JzZOuj3qvdJ4kw=</X509Certificate>
      </X509Data>
    </KeyInfo>
  </Signature>
</ns:User>

Digest Value I am getting: KEqvZWvpT3yYqMMJSTBmUKNIQw4=

Correct Digest Value (The one that's being generated by the Java code and getting success response from the webservice):aa4phJzO4YWc2ZQ1CG8HZ4cB1SA=

Remarks: The xml that is to be signed is a normal xml and not a SOAP xml request. I used the same signing logic for the SOAP xml request and the response generated by it was accepted by the web-service(The web-service contains both the methods: 1 for normal xml request and 1 for soap xml request).

When trying to sign an xml request using SignedXml in C# , I am able to generate the signature and the signed xml request, but I am getting a failure message from my webservice when I am sending this message. The error states: data and digestvalue do not match.

Digging deeper, I checked an equivalent code we have that was developed in Java. The xml signed request that code is generating has a different digest value than what my C# code is generating, and the Java code gets a success message from the webservice.

After a lot of discussion and analysing using a test tool provided with my webservice, we understand this: the Digest Value changes depending upon where you specify the location of the Digital Signature in your request BEFORE you use ComputeSignature(). But I am unable to find a way by which you can specify the location BEFORE computing the signature. Here's my code:

        /*=================*/
        //CODE to remove whitespaces from the xml before building the xmlDocument

        String thisLine = "";
        String xmlString = "";
        StreamReader br = new StreamReader(Server.MapPath("~/" + fp));
        while ((thisLine = br.ReadLine()) != null)
        {
            xmlString = xmlString + thisLine.Trim();
        }
        br.Close();
        Debug.WriteLine("new logic: " + xmlString);


        XmlDocument xmlDocument = new XmlDocument();
           xmlDocument.LoadXml(xmlString);

        /*================*/





        SignedXml signedXml = new SignedXml(xmlDocument);

        //XmlDsigExcC14NTransformUrl
        signedXml.SignedInfo.CanonicalizationMethod =                SignedXml.XmlDsigC14NTransformUrl;
        signedXml.SigningKey = cert.PrivateKey;

        signedXml.KeyInfo.AddClause(new System.Security.Cryptography.Xml.KeyInfoX509Data(cert));


        Reference tRef = new Reference("");
        /*
                    XmlDsigExcC14NTransform env = new XmlDsigExcC14NTransform();
                    //Transform transf = new XmlDsigEnvelopedSignatureTransform(false);
                    tRef.AddTransform(transf);
                    */

        XmlDsigEnvelopedSignatureTransform env = new XmlDsigEnvelopedSignatureTransform();
        tRef.AddTransform(env);


        signedXml.AddReference(tRef);
        signedXml.ComputeSignature();




        XmlElement xmlDsig = signedXml.GetXml();
        xmlDsig.SetAttribute("Id", "Signature-1");

        XmlElement rootNode = xmlDocument.DocumentElement;
        rootNode.AppendChild(xmlDsig);

        XmlTextWriter w = new XmlTextWriter(Server.MapPath("~/attrdigsig2.xml"), new UTF8Encoding(false));
        w.Formatting = Formatting.Indented;

        xmlDocument.WriteTo(w);
        w.Close();

Here's the signed request I am getting:

<?xml version="1.0" encoding="utf-8"?>
<ns:User xmlns:ns="http://www.user.com">
  <ns:Username>1DDOagUser</ns:Username>
  <ns:Password>toyota12</ns:Password>
  <Signature Id="Signature-1" xmlns="http://www.w3.org/2000/09/xmldsig#">
    <SignedInfo>
      <CanonicalizationMethod Algorithm="http://www.w3.org/TR/2001/REC-xml-c14n-20010315" />
      <SignatureMethod Algorithm="http://www.w3.org/2000/09/xmldsig#rsa-sha1" />
      <Reference URI="">
        <Transforms>
          <Transform Algorithm="http://www.w3.org/2000/09/xmldsig#enveloped-signature" />
        </Transforms>
        <DigestMethod Algorithm="http://www.w3.org/2000/09/xmldsig#sha1" />
        <DigestValue>KEqvZWvpT3yYqMMJSTBmUKNIQw4=</DigestValue>
      </Reference>
    </SignedInfo>
    <SignatureValue>YQ+81KnxwM9RibFpmS48Gbfdv7gBxgXrH6XWdoF+OZaUq+uJOOcuuC9KNmC4pkMs0V/LEw2WI6zjs9ML8kxAx3vcU/8jZ9/b8Z1EK7ndCcqDvkfBUpltHQy9FyP3AQyeFyK0SFvcyJCxvetc7uoJgYDvKUVU/ydqolw2ZbOXCHvN34SwbqGgGlBed++I7yk7KWIOWXsfjdSVwkuIyvEuVwxCmHHhxgjjfVaPnJMBY3D1Ali28d+rwKphT3dXdroEjXIedIK6lkrNOlHsaWZGYgJxNN08nN8bnNCe9QXapzHysSLnc3tkbJ1i2KjVHpLxwDfxFuuhWxh2sCKCoNvLgA==</SignatureValue>
    <KeyInfo>
      <X509Data>
        <X509Certificate>MIIC0TCCAbmgAwIBAgIGATDa3Nm5MA0GCSqGSIb3DQEBBQUAMBgxFjAUBgNVBAMTDVNPQVBCb3hDb25maWcwHhcNMDgwNjE4MTAyODAwWhcNMjEwNjE4MTAyODAwWjAYMRYwFAYDVQQDEw1TT0FQQm94Q29uZmlnMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEApLw4QAWqVmEr+CEo8Fp8WPq9Oo7BdnNOtMT5sUp0IN4NVvKmdI8ju3HsbnXzI7csNDzK6Feo19J/XLZk/Lr3Q4bLmmD+bMLFljiIgQ89+Bwc3mtyT1Rr4WBQUKnF8+8y65m2RebySelzgWIeZM72JoThSw85VBtyHvjlQnTAnfwX0NV7mH+kbQDi0c4Q4UZhKWFfb5L2tbjcknsG0k4De07qIw+RsGipkuNoFyI6BwwC0IERv48sacL30nWAOZMNDkm4S61aAYuzfMZySzPseU6BUdIdYAnITgj4tHRJZ93OYnn6LObEkYxobyGi6SULtBQQYzHKgeeyvru2Z1L7nQIDAQABoyEwHzAdBgNVHQ4EFgQUjq3/y0NF+tlUqwLc8SP4uV4/PK4wDQYJKoZIhvcNAQEFBQADggEBAAJvxTw5cc/32ahQ2TlBCrBNeHvji4QYItimkoqQa1EMyBSnx1FXNRyfJ9Da/20ZdIvIfJvIozIU0V/iFd7Hi+a2bZeMkN/ofvUh3QchHfkP/718JhcIvug3fctUX27ENHLRRU/rzMvKg40+H9BJoos6lu7qgAyayCRgKR5A/U3cSE9ZrYMGBNqy/mSIscZXhDJw0KATLHircXwRjpN+0lk+7/df5T8tc8wJOIvETCfDaQlDzXHw4jhQFydloMY4Tm4//VZTVVh1nzt2rVv52pHZGP8Shb9e5qS/QicBTVqysyVQEpYktRrrTwZcbq/65sV0lOao2JzZOuj3qvdJ4kw=</X509Certificate>
      </X509Data>
    </KeyInfo>
  </Signature>
</ns:User>

Digest Value I am getting: KEqvZWvpT3yYqMMJSTBmUKNIQw4=

Correct Digest Value (The one that's being generated by the Java code and getting success response from the webservice):aa4phJzO4YWc2ZQ1CG8HZ4cB1SA=

Remarks: The xml that is to be signed is a normal xml and not a SOAP xml request. I used the same signing logic for the SOAP xml request and the response generated by it was accepted by the web-service(The web-service contains both the methods: 1 for normal xml request and 1 for soap xml request).

When trying to sign an xml request using SignedXml in C# , I am able to generate the signature and the signed xml request, but I am getting a failure message from my webservice when I am sending this message. The error states: data and digestvalue do not match.

Digging deeper, I checked an equivalent code we have that was developed in Java. The xml signed request that code is generating has a different digest value than what my C# code is generating, and the Java code gets a success message from the webservice.

After a lot of discussion and analysing using a test tool provided with my webservice, we understand this: the Digest Value changes depending upon where you specify the location of the Digital Signature in your request BEFORE you use ComputeSignature(). But I am unable to find a way by which you can specify the location BEFORE computing the signature. Here's my code:

        /*=================*/
        //CODE to remove whitespaces from the xml before building the xmlDocument

        String thisLine = "";
        String xmlString = "";
        StreamReader br = new StreamReader(Server.MapPath("~/" + fp));
        while ((thisLine = br.ReadLine()) != null)
        {
            xmlString = xmlString + thisLine.Trim();
        }
        br.Close();
        Debug.WriteLine("new logic: " + xmlString);


        XmlDocument xmlDocument = new XmlDocument();
           xmlDocument.LoadXml(xmlString);

        /*================*/





        SignedXml signedXml = new SignedXml(xmlDocument);

        //XmlDsigExcC14NTransformUrl
        signedXml.SignedInfo.CanonicalizationMethod =                SignedXml.XmlDsigC14NTransformUrl;
        signedXml.SigningKey = cert.PrivateKey;

        signedXml.KeyInfo.AddClause(new System.Security.Cryptography.Xml.KeyInfoX509Data(cert));


        Reference tRef = new Reference("");
        /*
                    XmlDsigExcC14NTransform env = new XmlDsigExcC14NTransform();
                    //Transform transf = new XmlDsigEnvelopedSignatureTransform(false);
                    tRef.AddTransform(transf);
                    */

        XmlDsigEnvelopedSignatureTransform env = new XmlDsigEnvelopedSignatureTransform();
        tRef.AddTransform(env);


        signedXml.AddReference(tRef);
        signedXml.ComputeSignature();




        XmlElement xmlDsig = signedXml.GetXml();
        xmlDsig.SetAttribute("Id", "Signature-1");

        XmlElement rootNode = xmlDocument.DocumentElement;
        rootNode.AppendChild(xmlDsig);

        XmlTextWriter w = new XmlTextWriter(Server.MapPath("~/attrdigsig2.xml"), new UTF8Encoding(false));
        w.Formatting = Formatting.Indented;

        xmlDocument.WriteTo(w);
        w.Close();

Here's the signed request I am getting:

<?xml version="1.0" encoding="utf-8"?>
<ns:User xmlns:ns="http://www.user.com">
  <ns:Username>1DDOagUser</ns:Username>
  <ns:Password>toyota12</ns:Password>
  <Signature Id="Signature-1" xmlns="http://www.w3.org/2000/09/xmldsig#">
    <SignedInfo>
      <CanonicalizationMethod Algorithm="http://www.w3.org/TR/2001/REC-xml-c14n-20010315" />
      <SignatureMethod Algorithm="http://www.w3.org/2000/09/xmldsig#rsa-sha1" />
      <Reference URI="">
        <Transforms>
          <Transform Algorithm="http://www.w3.org/2000/09/xmldsig#enveloped-signature" />
        </Transforms>
        <DigestMethod Algorithm="http://www.w3.org/2000/09/xmldsig#sha1" />
        <DigestValue>KEqvZWvpT3yYqMMJSTBmUKNIQw4=</DigestValue>
      </Reference>
    </SignedInfo>
    <SignatureValue>YQ+81KnxwM9RibFpmS48Gbfdv7gBxgXrH6XWdoF+OZaUq+uJOOcuuC9KNmC4pkMs0V/LEw2WI6zjs9ML8kxAx3vcU/8jZ9/b8Z1EK7ndCcqDvkfBUpltHQy9FyP3AQyeFyK0SFvcyJCxvetc7uoJgYDvKUVU/ydqolw2ZbOXCHvN34SwbqGgGlBed++I7yk7KWIOWXsfjdSVwkuIyvEuVwxCmHHhxgjjfVaPnJMBY3D1Ali28d+rwKphT3dXdroEjXIedIK6lkrNOlHsaWZGYgJxNN08nN8bnNCe9QXapzHysSLnc3tkbJ1i2KjVHpLxwDfxFuuhWxh2sCKCoNvLgA==</SignatureValue>
    <KeyInfo>
      <X509Data>
        <X509Certificate>MIIC0TCCAbmgAwIBAgIGATDa3Nm5MA0GCSqGSIb3DQEBBQUAMBgxFjAUBgNVBAMTDVNPQVBCb3hDb25maWcwHhcNMDgwNjE4MTAyODAwWhcNMjEwNjE4MTAyODAwWjAYMRYwFAYDVQQDEw1TT0FQQm94Q29uZmlnMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEApLw4QAWqVmEr+CEo8Fp8WPq9Oo7BdnNOtMT5sUp0IN4NVvKmdI8ju3HsbnXzI7csNDzK6Feo19J/XLZk/Lr3Q4bLmmD+bMLFljiIgQ89+Bwc3mtyT1Rr4WBQUKnF8+8y65m2RebySelzgWIeZM72JoThSw85VBtyHvjlQnTAnfwX0NV7mH+kbQDi0c4Q4UZhKWFfb5L2tbjcknsG0k4De07qIw+RsGipkuNoFyI6BwwC0IERv48sacL30nWAOZMNDkm4S61aAYuzfMZySzPseU6BUdIdYAnITgj4tHRJZ93OYnn6LObEkYxobyGi6SULtBQQYzHKgeeyvru2Z1L7nQIDAQABoyEwHzAdBgNVHQ4EFgQUjq3/y0NF+tlUqwLc8SP4uV4/PK4wDQYJKoZIhvcNAQEFBQADggEBAAJvxTw5cc/32ahQ2TlBCrBNeHvji4QYItimkoqQa1EMyBSnx1FXNRyfJ9Da/20ZdIvIfJvIozIU0V/iFd7Hi+a2bZeMkN/ofvUh3QchHfkP/718JhcIvug3fctUX27ENHLRRU/rzMvKg40+H9BJoos6lu7qgAyayCRgKR5A/U3cSE9ZrYMGBNqy/mSIscZXhDJw0KATLHircXwRjpN+0lk+7/df5T8tc8wJOIvETCfDaQlDzXHw4jhQFydloMY4Tm4//VZTVVh1nzt2rVv52pHZGP8Shb9e5qS/QicBTVqysyVQEpYktRrrTwZcbq/65sV0lOao2JzZOuj3qvdJ4kw=</X509Certificate>
      </X509Data>
    </KeyInfo>
  </Signature>
</ns:User>

Digest Value I am getting: KEqvZWvpT3yYqMMJSTBmUKNIQw4=

Correct Digest Value (The one that's being generated by the Java code and getting success response from the webservice):aa4phJzO4YWc2ZQ1CG8HZ4cB1SA=

Remarks: The xml that is to be signed is a normal xml and not a SOAP xml request. I used the same signing logic for the SOAP xml request and the response generated by it was accepted by the web-service(The web-service contains both the methods: 1 for normal xml request and 1 for soap xml request).

1个回答

    最佳答案

  1. 英文原文

    I figured out the issue. It was related to preservation of whitespaces while sending the signed request to the web service URL. So if you don't add the PreserveWhitespace=true statement, the data that is sent to the verifier is basically different ( because it doesn't contain the whitespaces) than the data that was signed. Hence, different hash values were obtained leading to invalid signature error.

    Here's the code snippet:

    XmlDocument xpdoc = new XmlDocument { PreserveWhitespace = true };
                xpdoc.Load(@fpath);
    
                using (Stream stream = webRequest.GetRequestStream())
                {
                    xpdoc.Save(stream); //writes the request body into the http web request stream 
                }
    

    Can someone help me with marking the answer as solved or closed ? Thanks.


    中文翻译

    I figured out the issue. It was related to preservation of whitespaces while sending the signed request to the web service URL. So if you don't add the PreserveWhitespace=true statement, the data that is sent to the verifier is basically different ( because it doesn't contain the whitespaces) than the data that was signed. Hence, different hash values were obtained leading to invalid signature error.

    Here's the code snippet:

    XmlDocument xpdoc = new XmlDocument { PreserveWhitespace = true };
                xpdoc.Load(@fpath);
    
                using (Stream stream = webRequest.GetRequestStream())
                {
                    xpdoc.Save(stream); //writes the request body into the http web request stream 
                }
    

    Can someone help me with marking the answer as solved or closed ? Thanks.