luisgoncalves / xades4j

A Java library for XAdES signature services
GNU Lesser General Public License v3.0
111 stars 66 forks source link

How to use XpathTransform #236

Closed mohammad0022 closed 3 years ago

mohammad0022 commented 3 years ago

Hi, I'm trying to sign a UBL2.1 with xades4j but I need to exclude some tags from being singed. I used XPathTransform but the resulted digest is not valid.

image

Here is the UBL document (not complete document for simplicity) that I'm trying to sign

<Invoice xmlns="urn:oasis:names:specification:ubl:schema:xsd:Invoice-2" xmlns:cac="urn:oasis:names:specification:ubl:schema:xsd:CommonAggregateComponents-2" xmlns:cbc="urn:oasis:names:specification:ubl:schema:xsd:CommonBasicComponents-2" xmlns:ext="urn:oasis:names:specification:ubl:schema:xsd:CommonExtensionComponents-2" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
   <ext:UBLExtensions>
      <ext:UBLExtension>
         <ext:ExtensionContent>
            <sig:UBLDocumentSignatures xmlns:sig="urn:oasis:names:specification:ubl:schema:xsd:CommonSignatureComponents-2" xmlns:sac="urn:oasis:names:specification:ubl:schema:xsd:SignatureAggregateComponents-2" xmlns:sbc="urn:oasis:names:specification:ubl:schema:xsd:SignatureBasicComponents-2">
               <sac:SignatureInformation>
                  <cbc:ID>urn:oasis:names:specification:ubl:signature:1</cbc:ID>
                  <sbc:ReferencedSignatureID>urn:oasis:names:specification:ubl:signature:Invoice</sbc:ReferencedSignatureID>
               </sac:SignatureInformation>
            </sig:UBLDocumentSignatures>
         </ext:ExtensionContent>
      </ext:UBLExtension>
   </ext:UBLExtensions>
   <cbc:ProfileID>reporting:1.0</cbc:ProfileID>
   <cbc:ID>20210000011041000001</cbc:ID>
   <cbc:UUID>7c0925c8-5536-4b73-aeca-e833f3f78b3c</cbc:UUID>
   <cbc:IssueDate>2021-03-14</cbc:IssueDate>
   <cbc:InvoiceTypeCode name="01000">380</cbc:InvoiceTypeCode>
   <cbc:Note>Some Notes</cbc:Note>
   <cbc:DocumentCurrencyCode>USD</cbc:DocumentCurrencyCode>
   <cbc:TaxCurrencyCode>USD</cbc:TaxCurrencyCode>
   <cac:OrderReference />
   <cac:BillingReference>
      <cac:InvoiceDocumentReference />
   </cac:BillingReference>
   <cac:ContractDocumentReference />
   <cac:AdditionalDocumentReference>
      <cbc:ID>ICV</cbc:ID>
      <cbc:UUID>20210000011041000001</cbc:UUID>
   </cac:AdditionalDocumentReference>
   <cac:AdditionalDocumentReference>
      <cbc:ID>PIH</cbc:ID>
      <cac:Attachment>
         <cbc:EmbeddedDocumentBinaryObject mimeCode="text/plain">X+zrZv/IbzjZUnhsbWlsecLbwjndTpG0ZynXOif7V+k=</cbc:EmbeddedDocumentBinaryObject>
      </cac:Attachment>
   </cac:AdditionalDocumentReference>
   <cac:AdditionalDocumentReference>
      <cbc:ID>QR</cbc:ID>
      <cac:Attachment>
         <cbc:EmbeddedDocumentBinaryObject mimeCode="text/plain">AUrYp9mE2LTYsdmD2Kkg2KfZhNi52LHYqNmK2Kkg2KfZhNmK2YXZhtmK2Kkg2YTZhNin2LPZhdmG2Kog2KfZhNmF2K3Yr9mI2K/YqQIJMTAwMzMxMDMzAxMyMDIxLTAzLTE0MDA6MDA6MDBaBAY0MjU0MDAFATAGQDIyMjk5YjQ0MTU2MDQ0MjYyMzU0YjkzZThhZjNjZThlMjFkNjRjNWVkZWYyZTkxMjk3OTMzNjllM2Y1YmE1MWEHBUVDRHNhWpWNMRzpzfaMmZhfH4APF155H+Fp5LU9xW0umMbEoS47hWKjcYlakCn6Xhx7Ok6iDSN4syJQVaWfAwmARtM1nw==</cbc:EmbeddedDocumentBinaryObject>
      </cac:Attachment>
   </cac:AdditionalDocumentReference>
   <cac:Signature>
      <cbc:ID>urn:oasis:names:specification:ubl:signature:Invoice</cbc:ID>
      <cbc:SignatureMethod>urn:oasis:names:specification:ubl:dsig:enveloped:xades</cbc:SignatureMethod>
   </cac:Signature>
</Invoice>

I want to exclude these elements from the signature:

//ancestor-or-self::ext:UBLExtensions
//ancestor-or-self::cac:Signature
//ancestor-or-self::cac:AdditionalDocumentReference[cbc:ID='QR']

so, I used the following xpath transform

DataObjectDesc obj = new DataObjectReference("")
                .withTransform(new XPathTransform("not(//ancestor-or-self::ext:UBLExtensions)"))
                .withTransform(new XPathTransform("not(//ancestor-or-self::cac:Signature)"))
                .withTransform(new XPathTransform("not(//ancestor-or-self::cac:AdditionalDocumentReference[cbc:ID='QR'])"))
                .withDataObjectFormat(new DataObjectFormatProperty("text/xml"));

However the resulted digest is not valid.

Note: Each time I sign the same file with the same XpathTransform the resulted digest value for the first reference is different, however I'm expecting it not to change each time. I'm sure I'm missing something or doing something wrong.

Thanks in advance.

luisgoncalves commented 3 years ago

This is the same issue as the SO question https://stackoverflow.com/questions/68543067/how-to-use-xpath-transform, right?

At first glance the XPath usage seems correct.

Note that as described in the spec, a reference with URI="" means the whole XML document. How is the signature to the document? Your DataObjectReference probably requires an enveloped signature transform to avoid including the signature itself during validating of the reference (docs). Without this, the verifying party will always calculate a difference digest, because the XML document is different during signature generation (not yet complete).

Regarding the different digest values - assuming you are referring to the XML generated by xades4j - if the input document doesn't change, I'd expect the digest to be the same.

mohammad0022 commented 3 years ago

Thanks @luisgoncalves for you reply.

Yes, it's the same SO question.

I want to point out that the signature is included with the "UBLExtensions" tag, which is already excluded from the signature calculation using the xpath transform :

not(//ancestor-or-self::ext:UBLExtensions)

So, I think I do not need to add enveloped signature transform. right?

luisgoncalves commented 3 years ago

You're probably right.

Regarding the different digest values of the reference, you said you were expecting it to change each time. Why is that? if the input document is not changing, then the reference digest shouldn't change.

Using this xades4j test as an example SignerBESTest#testSignBESDetachedWithXPathAndNamespaces, the digest of the references using XPath transforms doesn't change if you run the test multiple times. Also, if you try modifying XML bits that are excluded by the transform, the digest doesn't change.

This indicates that either:

  1. Your references are picking up nodes that change between executions. If the source document doesn't change, then changing nodes would have to come from the signature itself.
  2. You have other issues in your code. For instance, when parsing the XML document are you setting DocumentBuilderFactory#setNamespaceAware to true?
mohammad0022 commented 3 years ago

I'm so sorry, this was a typing mistake I'm expecting the digest NOT to change each time.

I have tried the the test SignerBESTest#testSignBESWithEllipticCurveKey after adding xpath transform and I have got a different digest each time I run the test.

I will check this test SignerBESTest#testSignBESDetachedWithXPathAndNamespaces and see if it will work will.

I think the key difference between the two test is the reference URI, Also I will try to add URI in my first test.

Thanks @luisgoncalves for your time.

luisgoncalves commented 3 years ago

I pushed a branch with a test to illustrate what we've been discussing.

https://github.com/luisgoncalves/xades4j/commit/78122793da48268b70f4d3caba56448fa23dcdad

In the test I'm adding the signature as a child of an element that is excluded by a XPath transform. I'm also modifying an element that is excluded by another XPath transform in one of the documents. In both cases, the digest is the same. However, if another node is changed, the digest is different.

Are you sure that you are appending the signature as a child of one of the excluded nodes? Can you share that bit of the code (only)?

mohammad0022 commented 3 years ago

As you said, I had an issue with my code, which is not settings DocumentBuilderFactory#setNamespaceAware to ture. After setting it to true I get constant digest for the same xml.

But the main issue of the calculated digest being invalid still exists.

This is the code I'm using

        DocumentBuilderFactory dbFactory = DocumentBuilderFactory.newInstance();
        dbFactory.setNamespaceAware(true);
        Document doc = dbFactory
                .newDocumentBuilder()
                .parse(new File(DOCUMENT));
        Element elem = (Element) doc.getElementsByTagName("sac:SignatureInformation").item(0);
        DOMHelper.useIdAsXmlId(elem);

        KeyingDataProvider kdp = new FileSystemKeyStoreKeyingDataProvider(
                "pkcs12",
                CERT_PATH,
                new FirstCertificateSelector(),
                new DirectPasswordProvider(PASS),
                new DirectPasswordProvider(PASS),
                true);

        DataObjectDesc obj = new DataObjectReference("")
                .withTransform(new XPathTransform("not(ancestor-or-self::ext:UBLExtensions)").withNamespace("ext","urn:oasis:names:specification:ubl:schema:xsd:CommonExtensionComponents-2"))
                .withTransform(new XPathTransform("not(ancestor-or-self::cac:Signature)").withNamespace("cac","urn:oasis:names:specification:ubl:schema:xsd:CommonAggregateComponents-2"))
                .withTransform(new XPathTransform("not(ancestor-or-self::cac:AdditionalDocumentReference[cbc:ID='QR'])").withNamespace("cac","urn:oasis:names:specification:ubl:schema:xsd:CommonAggregateComponents-2"))
                .withDataObjectFormat(new DataObjectFormatProperty("text/xml"));
        SignedDataObjects dataObjs = new SignedDataObjects().withSignedDataObject(obj);

        XadesSigner signer = new XadesBesSigningProfile(kdp)
                .newSigner();
        signer.sign(dataObjs, elem);

        TransformerFactory tFactory = TransformerFactory.newInstance();

        Transformer transformer = tFactory.newTransformer();
        DOMSource source = new DOMSource(doc);
        StreamResult result = new StreamResult(new File(SIGNED));
        transformer.transform(source, result);

This is the complete xml file

<Invoice xmlns="urn:oasis:names:specification:ubl:schema:xsd:Invoice-2" xmlns:cac="urn:oasis:names:specification:ubl:schema:xsd:CommonAggregateComponents-2" xmlns:cbc="urn:oasis:names:specification:ubl:schema:xsd:CommonBasicComponents-2" xmlns:ext="urn:oasis:names:specification:ubl:schema:xsd:CommonExtensionComponents-2" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
   <ext:UBLExtensions>
      <ext:UBLExtension>
         <ext:ExtensionContent>
            <sig:UBLDocumentSignatures xmlns:sig="urn:oasis:names:specification:ubl:schema:xsd:CommonSignatureComponents-2" xmlns:sac="urn:oasis:names:specification:ubl:schema:xsd:SignatureAggregateComponents-2" xmlns:sbc="urn:oasis:names:specification:ubl:schema:xsd:SignatureBasicComponents-2">
               <sac:SignatureInformation>
                  <cbc:ID>urn:oasis:names:specification:ubl:signature:1</cbc:ID>
                  <sbc:ReferencedSignatureID>urn:oasis:names:specification:ubl:signature:Invoice</sbc:ReferencedSignatureID>
               </sac:SignatureInformation>
            </sig:UBLDocumentSignatures>
         </ext:ExtensionContent>
      </ext:UBLExtension>
   </ext:UBLExtensions>
   <cbc:ProfileID>reporting:1.0</cbc:ProfileID>
   <cbc:ID>20210000011041000001</cbc:ID>
   <cbc:UUID>7c0925c8-5536-4b73-aeca-e833f3f78b3c</cbc:UUID>
   <cbc:IssueDate>2021-03-14</cbc:IssueDate>
   <cbc:InvoiceTypeCode name="01000">380</cbc:InvoiceTypeCode>
   <cbc:Note>Some Notes</cbc:Note>
   <cbc:DocumentCurrencyCode>YER</cbc:DocumentCurrencyCode>
   <cbc:TaxCurrencyCode>YER</cbc:TaxCurrencyCode>
   <cac:OrderReference />
   <cac:BillingReference>
      <cac:InvoiceDocumentReference />
   </cac:BillingReference>
   <cac:ContractDocumentReference />
   <cac:AdditionalDocumentReference>
      <cbc:ID>ICV</cbc:ID>
      <cbc:UUID>20210000011041000001</cbc:UUID>
   </cac:AdditionalDocumentReference>
   <cac:AdditionalDocumentReference>
      <cbc:ID>PIH</cbc:ID>
      <cac:Attachment>
         <cbc:EmbeddedDocumentBinaryObject mimeCode="text/plain">X+zrZv/IbzjZUnhsbWlsecLbwjndTpG0ZynXOif7V+k=</cbc:EmbeddedDocumentBinaryObject>
      </cac:Attachment>
   </cac:AdditionalDocumentReference>
   <cac:AdditionalDocumentReference>
      <cbc:ID>QR</cbc:ID>
      <cac:Attachment>
         <cbc:EmbeddedDocumentBinaryObject mimeCode="text/plain">AUrYp9mE2LTYsdmD2Kkg2KfZhNi52LHYqNmK2Kkg2KfZhNmK2YXZhtmK2Kkg2YTZhNin2LPZhdmG2Kog2KfZhNmF2K3Yr9mI2K/YqQIJMTAwMzMxMDMzAxMyMDIxLTAzLTE0MDA6MDA6MDBaBAY0MjU0MDAFATAGQDIyMjk5YjQ0MTU2MDQ0MjYyMzU0YjkzZThhZjNjZThlMjFkNjRjNWVkZWYyZTkxMjk3OTMzNjllM2Y1YmE1MWEHBUVDRHNhWpWNMRzpzfaMmZhfH4APF155H+Fp5LU9xW0umMbEoS47hWKjcYlakCn6Xhx7Ok6iDSN4syJQVaWfAwmARtM1nw==</cbc:EmbeddedDocumentBinaryObject>
      </cac:Attachment>
   </cac:AdditionalDocumentReference>
   <cac:Signature>
      <cbc:ID>urn:oasis:names:specification:ubl:signature:Invoice</cbc:ID>
      <cbc:SignatureMethod>urn:oasis:names:specification:ubl:dsig:enveloped:xades</cbc:SignatureMethod>
   </cac:Signature>
   <cac:AccountingSupplierParty>
      <cac:Party>
         <cac:PartyIdentification>
            <cbc:ID schemeID="HQ">100331033</cbc:ID>
         </cac:PartyIdentification>
         <cac:PartyIdentification>
            <cbc:ID schemeID="CR" />
         </cac:PartyIdentification>
         <cac:PostalAddress>
            <cbc:StreetName>ABC154</cbc:StreetName>
            <cbc:BuildingNumber>1654c</cbc:BuildingNumber>
            <cbc:CitySubdivisionName>Hadramout</cbc:CitySubdivisionName>
            <cbc:CityName>Hadramout</cbc:CityName>
            <cbc:CountrySubentity>Hadramout</cbc:CountrySubentity>
            <cac:Country>
               <cbc:IdentificationCode>YE</cbc:IdentificationCode>
            </cac:Country>
         </cac:PostalAddress>
         <cac:PartyTaxScheme>
            <cbc:CompanyID>100331033</cbc:CompanyID>
            <cac:TaxScheme>
               <cbc:TaxTypeCode>VAT</cbc:TaxTypeCode>
            </cac:TaxScheme>
         </cac:PartyTaxScheme>
         <cac:PartyLegalEntity>
            <cbc:RegistrationName>Invoice Issuer Name</cbc:RegistrationName>
         </cac:PartyLegalEntity>
      </cac:Party>
   </cac:AccountingSupplierParty>
   <cac:AccountingCustomerParty>
      <cac:Party>
         <cac:PartyIdentification>
            <cbc:ID schemeID="HQ">313717919</cbc:ID>
         </cac:PartyIdentification>
         <cac:PartyIdentification>
            <cbc:ID schemeID="NAT" />
         </cac:PartyIdentification>
         <cac:PostalAddress>
            <cbc:StreetName>525A</cbc:StreetName>
            <cbc:BuildingNumber>123</cbc:BuildingNumber>
            <cbc:CitySubdivisionName>Hadramout</cbc:CitySubdivisionName>
            <cbc:CityName>Hadramout</cbc:CityName>
            <cbc:CountrySubentity>Hadramout</cbc:CountrySubentity>
            <cac:Country>
               <cbc:IdentificationCode>YE</cbc:IdentificationCode>
            </cac:Country>
         </cac:PostalAddress>
         <cac:PartyTaxScheme>
            <cbc:CompanyID>313717919</cbc:CompanyID>
            <cac:TaxScheme>
               <cbc:TaxTypeCode>VAT</cbc:TaxTypeCode>
            </cac:TaxScheme>
         </cac:PartyTaxScheme>
         <cac:PartyLegalEntity>
            <cbc:RegistrationName>Invoice Reciver Name</cbc:RegistrationName>
         </cac:PartyLegalEntity>
      </cac:Party>
   </cac:AccountingCustomerParty>
   <cac:Delivery />
   <cac:PaymentMeans>
      <cbc:PaymentMeansCode>30</cbc:PaymentMeansCode>
      <cac:PayeeFinancialAccount />
   </cac:PaymentMeans>
   <cac:AllowanceCharge>
      <cbc:ChargeIndicator>false</cbc:ChargeIndicator>
      <cbc:MultiplierFactorNumeric>0</cbc:MultiplierFactorNumeric>
      <cbc:Amount currencyID="YER">0</cbc:Amount>
      <cbc:BaseAmount currencyID="YER">400000</cbc:BaseAmount>
   </cac:AllowanceCharge>
   <cac:AllowanceCharge>
      <cbc:ChargeIndicator>true</cbc:ChargeIndicator>
      <cbc:MultiplierFactorNumeric>6.3500</cbc:MultiplierFactorNumeric>
      <cbc:Amount currencyID="YER">25400</cbc:Amount>
      <cbc:BaseAmount currencyID="YER">400000</cbc:BaseAmount>
   </cac:AllowanceCharge>
   <cac:TaxTotal>
      <cbc:TaxAmount currencyID="YER">0</cbc:TaxAmount>
   </cac:TaxTotal>
   <cac:LegalMonetaryTotal>
      <cbc:LineExtensionAmount currencyID="YER">400000</cbc:LineExtensionAmount>
      <cbc:TaxExclusiveAmount currencyID="YER">425400</cbc:TaxExclusiveAmount>
      <cbc:TaxInclusiveAmount currencyID="YER">425400</cbc:TaxInclusiveAmount>
      <cbc:AllowanceTotalAmount currencyID="YER">0</cbc:AllowanceTotalAmount>
      <cbc:ChargeTotalAmount currencyID="YER">25400</cbc:ChargeTotalAmount>
      <cbc:PrepaidAmount currencyID="YER">0</cbc:PrepaidAmount>
      <cbc:PayableRoundingAmount currencyID="YER">0</cbc:PayableRoundingAmount>
      <cbc:PayableAmount currencyID="YER">425400</cbc:PayableAmount>
   </cac:LegalMonetaryTotal>
   <cac:InvoiceLine>
      <cbc:ID>1</cbc:ID>
      <cbc:InvoicedQuantity unitCode="BG">100</cbc:InvoicedQuantity>
      <cbc:LineExtensionAmount currencyID="YER">425400</cbc:LineExtensionAmount>
      <cac:AllowanceCharge>
         <cbc:ChargeIndicator>false</cbc:ChargeIndicator>
         <cbc:MultiplierFactorNumeric>0</cbc:MultiplierFactorNumeric>
         <cbc:Amount currencyID="YER">0</cbc:Amount>
         <cbc:BaseAmount currencyID="YER">400000</cbc:BaseAmount>
      </cac:AllowanceCharge>
      <cac:AllowanceCharge>
         <cbc:ChargeIndicator>true</cbc:ChargeIndicator>
         <cbc:MultiplierFactorNumeric>6.3500</cbc:MultiplierFactorNumeric>
         <cbc:Amount currencyID="YER">25400</cbc:Amount>
         <cbc:BaseAmount currencyID="YER">400000</cbc:BaseAmount>
      </cac:AllowanceCharge>
      <cac:TaxTotal>
         <cbc:TaxAmount currencyID="YER">0</cbc:TaxAmount>
         <cbc:RoundingAmount currencyID="YER">400000</cbc:RoundingAmount>
      </cac:TaxTotal>
      <cac:Item>
         <cbc:Name>Item Name</cbc:Name>
         <cac:BuyersItemIdentification>
            <cbc:ID>999.003</cbc:ID>
         </cac:BuyersItemIdentification>
         <cac:SellersItemIdentification>
            <cbc:ID>999.003</cbc:ID>
         </cac:SellersItemIdentification>
         <cac:StandardItemIdentification />
      </cac:Item>
      <cac:Price>
         <cbc:PriceAmount currencyID="YER">4000</cbc:PriceAmount>
         <cbc:BaseQuantity unitCode="BG">1</cbc:BaseQuantity>
         <cac:AllowanceCharge>
            <cbc:ChargeIndicator>false</cbc:ChargeIndicator>
            <cbc:Amount currencyID="YER">0</cbc:Amount>
            <cbc:BaseAmount currencyID="YER">4000</cbc:BaseAmount>
         </cac:AllowanceCharge>
      </cac:Price>
   </cac:InvoiceLine>
</Invoice>

I want to attach the signature to the follwoing element Invoice -> ext:UBLExtensions -> ext:UBLExtension -> ext:ExtensionContent -> sig:UBLDocumentSignatures -> sac:SignatureInformation

Here is the signed version using the above code

<Invoice xmlns="urn:oasis:names:specification:ubl:schema:xsd:Invoice-2" xmlns:cac="urn:oasis:names:specification:ubl:schema:xsd:CommonAggregateComponents-2" xmlns:cbc="urn:oasis:names:specification:ubl:schema:xsd:CommonBasicComponents-2" xmlns:ext="urn:oasis:names:specification:ubl:schema:xsd:CommonExtensionComponents-2" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
   <ext:UBLExtensions>
      <ext:UBLExtension>
         <ext:ExtensionContent>
            <sig:UBLDocumentSignatures xmlns:sig="urn:oasis:names:specification:ubl:schema:xsd:CommonSignatureComponents-2" xmlns:sac="urn:oasis:names:specification:ubl:schema:xsd:SignatureAggregateComponents-2" xmlns:sbc="urn:oasis:names:specification:ubl:schema:xsd:SignatureBasicComponents-2">
               <sac:SignatureInformation>
                  <cbc:ID>urn:oasis:names:specification:ubl:signature:1</cbc:ID>
                  <sbc:ReferencedSignatureID>urn:oasis:names:specification:ubl:signature:Invoice</sbc:ReferencedSignatureID>
               <ds:Signature xmlns:ds="http://www.w3.org/2000/09/xmldsig#" Id="xmldsig-e67e355b-46ad-4b61-b11f-35a7a2be9f55">
<ds:SignedInfo>
<ds:CanonicalizationMethod Algorithm="http://www.w3.org/TR/2001/REC-xml-c14n-20010315"/>
<ds:SignatureMethod Algorithm="http://www.w3.org/2001/04/xmldsig-more#ecdsa-sha256"/>
<ds:Reference Id="xmldsig-e67e355b-46ad-4b61-b11f-35a7a2be9f55-ref0" URI="">
<ds:Transforms>
<ds:Transform Algorithm="http://www.w3.org/TR/1999/REC-xpath-19991116"><ds:XPath xmlns:ext="urn:oasis:names:specification:ubl:schema:xsd:CommonExtensionComponents-2">not(ancestor-or-self::ext:UBLExtensions)</ds:XPath></ds:Transform>
<ds:Transform Algorithm="http://www.w3.org/TR/1999/REC-xpath-19991116"><ds:XPath xmlns:cac="urn:oasis:names:specification:ubl:schema:xsd:CommonAggregateComponents-2">not(ancestor-or-self::cac:Signature)</ds:XPath></ds:Transform>
<ds:Transform Algorithm="http://www.w3.org/TR/1999/REC-xpath-19991116"><ds:XPath xmlns:cac="urn:oasis:names:specification:ubl:schema:xsd:CommonAggregateComponents-2">not(ancestor-or-self::cac:AdditionalDocumentReference[cbc:ID='QR'])</ds:XPath></ds:Transform>
</ds:Transforms>
<ds:DigestMethod Algorithm="http://www.w3.org/2001/04/xmlenc#sha256"/>
<ds:DigestValue>YKFF4dzSGSxGv+Vb4rRnCQRwxVMzw3bbKi1D6qafjIk=</ds:DigestValue>
</ds:Reference>
<ds:Reference Type="http://uri.etsi.org/01903#SignedProperties" URI="#xmldsig-e67e355b-46ad-4b61-b11f-35a7a2be9f55-signedprops">
<ds:Transforms>
<ds:Transform Algorithm="http://www.w3.org/TR/2001/REC-xml-c14n-20010315"/>
</ds:Transforms>
<ds:DigestMethod Algorithm="http://www.w3.org/2001/04/xmlenc#sha256"/>
<ds:DigestValue>A3oSjfbD4VyZoMBSNNybqP1yNZlv8Vhlknw/CuMl+SI=</ds:DigestValue>
</ds:Reference>
</ds:SignedInfo>
<ds:SignatureValue Id="xmldsig-e67e355b-46ad-4b61-b11f-35a7a2be9f55-sigvalue">
c4NIGB7Qk+rvo5zvD/rYJLGoJJJ4iqtwWmU5dm2/8RtlD9PKAUtmCllGUxHGqEAK2xhHC4hO0j3J&#13;
SCQfNBXIRA==
</ds:SignatureValue>
<ds:KeyInfo xmlns:ds="http://www.w3.org/2000/09/xmldsig#">
<ds:X509Data>
<ds:X509Certificate>
MIICpTCCAkugAwIBAgIUFBjA6oeEHBQjFKU1K/YjeDcyeREwCgYIKoZIzj0EAwIwgacxCzAJBgNV&#13;
BAYTAllFMRIwEAYDVQQIDAlIYWRyYW1vdXQxEzARBgNVBAcMCkFsLU11a2FsbGExEzARBgNVBAoM&#13;
Cm1hdHRhci5uZXQxHjAcBgNVBAsMFVNvZnR3YXJlIERldmVsb3BsbWVudDEXMBUGA1UEAwwOd3d3&#13;
Lm1hdHRhci5uZXQxITAfBgkqhkiG9w0BCQEWEnN1cHBvcnRAbWF0dGFyLm5ldDAeFw0yMTA0MjYw&#13;
NzM5NDZaFw0yMjA0MjEwNzM5NDZaMIGnMQswCQYDVQQGEwJZRTESMBAGA1UECAwJSGFkcmFtb3V0&#13;
MRMwEQYDVQQHDApBbC1NdWthbGxhMRMwEQYDVQQKDAptYXR0YXIubmV0MR4wHAYDVQQLDBVTb2Z0&#13;
d2FyZSBEZXZlbG9wbG1lbnQxFzAVBgNVBAMMDnd3dy5tYXR0YXIubmV0MSEwHwYJKoZIhvcNAQkB&#13;
FhJzdXBwb3J0QG1hdHRhci5uZXQwWTATBgcqhkjOPQIBBggqhkjOPQMBBwNCAARJ3bmPxMLqkEoA&#13;
GDDRiZE9xKJeowXVXxWXqACzOLzv2Vdov4yk30D6IfF9sAa4EmqBMQl+szf9D7w6oOk2NSC4o1Mw&#13;
UTAdBgNVHQ4EFgQU1RJrhrdA7VAMNnhGoOQQvmCEoO0wHwYDVR0jBBgwFoAU1RJrhrdA7VAMNnhG&#13;
oOQQvmCEoO0wDwYDVR0TAQH/BAUwAwEB/zAKBggqhkjOPQQDAgNIADBFAiEAth9NczyCooHImNef&#13;
WxfLVTnvnxSaaRss/hGKK4agI8wCIA3JpIIk24iMtXzhgceN2E3FBAeBydIsumFsc8C9ZieW
</ds:X509Certificate>
<ds:X509IssuerSerial>
<ds:X509IssuerName>1.2.840.113549.1.9.1=support@mattar.net,cn=www.mattar.net,ou=Software Developlment,o=mattar.net,l=Al-Mukalla,st=Hadramout,c=YE</ds:X509IssuerName>
<ds:X509SerialNumber>114731838666346015026195663665358635712931592465</ds:X509SerialNumber>
</ds:X509IssuerSerial>
<ds:X509SubjectName>1.2.840.113549.1.9.1=support@mattar.net,cn=www.mattar.net,ou=Software Developlment,o=mattar.net,l=Al-Mukalla,st=Hadramout,c=YE</ds:X509SubjectName>
</ds:X509Data>
</ds:KeyInfo>
<ds:Object><xades:QualifyingProperties xmlns:xades="http://uri.etsi.org/01903/v1.3.2#" xmlns:xades141="http://uri.etsi.org/01903/v1.4.1#" Target="#xmldsig-e67e355b-46ad-4b61-b11f-35a7a2be9f55"><xades:SignedProperties Id="xmldsig-e67e355b-46ad-4b61-b11f-35a7a2be9f55-signedprops"><xades:SignedSignatureProperties><xades:SigningTime>2021-08-01T12:31:00.369+03:00</xades:SigningTime><xades:SigningCertificate><xades:Cert><xades:CertDigest><ds:DigestMethod Algorithm="http://www.w3.org/2001/04/xmlenc#sha256"/><ds:DigestValue>rrrRK1yl+FLbll9FfVQ/8JI6g0l/zHmoqlXmZU8X7ZQ=</ds:DigestValue></xades:CertDigest><xades:IssuerSerial><ds:X509IssuerName>1.2.840.113549.1.9.1=support@mattar.net,cn=www.mattar.net,ou=Software Developlment,o=mattar.net,l=Al-Mukalla,st=Hadramout,c=YE</ds:X509IssuerName><ds:X509SerialNumber>114731838666346015026195663665358635712931592465</ds:X509SerialNumber></xades:IssuerSerial></xades:Cert></xades:SigningCertificate></xades:SignedSignatureProperties><xades:SignedDataObjectProperties><xades:DataObjectFormat ObjectReference="#xmldsig-e67e355b-46ad-4b61-b11f-35a7a2be9f55-ref0"><xades:MimeType>text/xml</xades:MimeType></xades:DataObjectFormat></xades:SignedDataObjectProperties></xades:SignedProperties></xades:QualifyingProperties></ds:Object>
</ds:Signature></sac:SignatureInformation>
            </sig:UBLDocumentSignatures>
         </ext:ExtensionContent>
      </ext:UBLExtension>
   </ext:UBLExtensions>
   <cbc:ProfileID>reporting:1.0</cbc:ProfileID>
   <cbc:ID>20210000011041000001</cbc:ID>
   <cbc:UUID>7c0925c8-5536-4b73-aeca-e833f3f78b3c</cbc:UUID>
   <cbc:IssueDate>2021-03-14</cbc:IssueDate>
   <cbc:InvoiceTypeCode name="01000">380</cbc:InvoiceTypeCode>
   <cbc:Note>Some Notes</cbc:Note>
   <cbc:DocumentCurrencyCode>YER</cbc:DocumentCurrencyCode>
   <cbc:TaxCurrencyCode>YER</cbc:TaxCurrencyCode>
   <cac:OrderReference/>
   <cac:BillingReference>
      <cac:InvoiceDocumentReference/>
   </cac:BillingReference>
   <cac:ContractDocumentReference/>
   <cac:AdditionalDocumentReference>
      <cbc:ID>ICV</cbc:ID>
      <cbc:UUID>20210000011041000001</cbc:UUID>
   </cac:AdditionalDocumentReference>
   <cac:AdditionalDocumentReference>
      <cbc:ID>PIH</cbc:ID>
      <cac:Attachment>
         <cbc:EmbeddedDocumentBinaryObject mimeCode="text/plain">X+zrZv/IbzjZUnhsbWlsecLbwjndTpG0ZynXOif7V+k=</cbc:EmbeddedDocumentBinaryObject>
      </cac:Attachment>
   </cac:AdditionalDocumentReference>
   <cac:AdditionalDocumentReference>
      <cbc:ID>QR</cbc:ID>
      <cac:Attachment>
         <cbc:EmbeddedDocumentBinaryObject mimeCode="text/plain">AUrYp9mE2LTYsdmD2Kkg2KfZhNi52LHYqNmK2Kkg2KfZhNmK2YXZhtmK2Kkg2YTZhNin2LPZhdmG2Kog2KfZhNmF2K3Yr9mI2K/YqQIJMTAwMzMxMDMzAxMyMDIxLTAzLTE0MDA6MDA6MDBaBAY0MjU0MDAFATAGQDIyMjk5YjQ0MTU2MDQ0MjYyMzU0YjkzZThhZjNjZThlMjFkNjRjNWVkZWYyZTkxMjk3OTMzNjllM2Y1YmE1MWEHBUVDRHNhWpWNMRzpzfaMmZhfH4APF155H+Fp5LU9xW0umMbEoS47hWKjcYlakCn6Xhx7Ok6iDSN4syJQVaWfAwmARtM1nw==</cbc:EmbeddedDocumentBinaryObject>
      </cac:Attachment>
   </cac:AdditionalDocumentReference>
   <cac:Signature>
      <cbc:ID>urn:oasis:names:specification:ubl:signature:Invoice</cbc:ID>
      <cbc:SignatureMethod>urn:oasis:names:specification:ubl:dsig:enveloped:xades</cbc:SignatureMethod>
   </cac:Signature>
   <cac:AccountingSupplierParty>
      <cac:Party>
         <cac:PartyIdentification>
            <cbc:ID schemeID="HQ">100331033</cbc:ID>
         </cac:PartyIdentification>
         <cac:PartyIdentification>
            <cbc:ID schemeID="CR"/>
         </cac:PartyIdentification>
         <cac:PostalAddress>
            <cbc:StreetName>ABC154</cbc:StreetName>
            <cbc:BuildingNumber>1654c</cbc:BuildingNumber>
            <cbc:CitySubdivisionName>Hadramout</cbc:CitySubdivisionName>
            <cbc:CityName>Hadramout</cbc:CityName>
            <cbc:CountrySubentity>Hadramout</cbc:CountrySubentity>
            <cac:Country>
               <cbc:IdentificationCode>YE</cbc:IdentificationCode>
            </cac:Country>
         </cac:PostalAddress>
         <cac:PartyTaxScheme>
            <cbc:CompanyID>100331033</cbc:CompanyID>
            <cac:TaxScheme>
               <cbc:TaxTypeCode>VAT</cbc:TaxTypeCode>
            </cac:TaxScheme>
         </cac:PartyTaxScheme>
         <cac:PartyLegalEntity>
            <cbc:RegistrationName>Invoice Issuer Name</cbc:RegistrationName>
         </cac:PartyLegalEntity>
      </cac:Party>
   </cac:AccountingSupplierParty>
   <cac:AccountingCustomerParty>
      <cac:Party>
         <cac:PartyIdentification>
            <cbc:ID schemeID="HQ">313717919</cbc:ID>
         </cac:PartyIdentification>
         <cac:PartyIdentification>
            <cbc:ID schemeID="NAT"/>
         </cac:PartyIdentification>
         <cac:PostalAddress>
            <cbc:StreetName>525A</cbc:StreetName>
            <cbc:BuildingNumber>123</cbc:BuildingNumber>
            <cbc:CitySubdivisionName>Hadramout</cbc:CitySubdivisionName>
            <cbc:CityName>Hadramout</cbc:CityName>
            <cbc:CountrySubentity>Hadramout</cbc:CountrySubentity>
            <cac:Country>
               <cbc:IdentificationCode>YE</cbc:IdentificationCode>
            </cac:Country>
         </cac:PostalAddress>
         <cac:PartyTaxScheme>
            <cbc:CompanyID>313717919</cbc:CompanyID>
            <cac:TaxScheme>
               <cbc:TaxTypeCode>VAT</cbc:TaxTypeCode>
            </cac:TaxScheme>
         </cac:PartyTaxScheme>
         <cac:PartyLegalEntity>
            <cbc:RegistrationName>Invoice Reciver Name</cbc:RegistrationName>
         </cac:PartyLegalEntity>
      </cac:Party>
   </cac:AccountingCustomerParty>
   <cac:Delivery/>
   <cac:PaymentMeans>
      <cbc:PaymentMeansCode>30</cbc:PaymentMeansCode>
      <cac:PayeeFinancialAccount/>
   </cac:PaymentMeans>
   <cac:AllowanceCharge>
      <cbc:ChargeIndicator>false</cbc:ChargeIndicator>
      <cbc:MultiplierFactorNumeric>0</cbc:MultiplierFactorNumeric>
      <cbc:Amount currencyID="YER">0</cbc:Amount>
      <cbc:BaseAmount currencyID="YER">400000</cbc:BaseAmount>
   </cac:AllowanceCharge>
   <cac:AllowanceCharge>
      <cbc:ChargeIndicator>true</cbc:ChargeIndicator>
      <cbc:MultiplierFactorNumeric>6.3500</cbc:MultiplierFactorNumeric>
      <cbc:Amount currencyID="YER">25400</cbc:Amount>
      <cbc:BaseAmount currencyID="YER">400000</cbc:BaseAmount>
   </cac:AllowanceCharge>
   <cac:TaxTotal>
      <cbc:TaxAmount currencyID="YER">0</cbc:TaxAmount>
   </cac:TaxTotal>
   <cac:LegalMonetaryTotal>
      <cbc:LineExtensionAmount currencyID="YER">400000</cbc:LineExtensionAmount>
      <cbc:TaxExclusiveAmount currencyID="YER">425400</cbc:TaxExclusiveAmount>
      <cbc:TaxInclusiveAmount currencyID="YER">425400</cbc:TaxInclusiveAmount>
      <cbc:AllowanceTotalAmount currencyID="YER">0</cbc:AllowanceTotalAmount>
      <cbc:ChargeTotalAmount currencyID="YER">25400</cbc:ChargeTotalAmount>
      <cbc:PrepaidAmount currencyID="YER">0</cbc:PrepaidAmount>
      <cbc:PayableRoundingAmount currencyID="YER">0</cbc:PayableRoundingAmount>
      <cbc:PayableAmount currencyID="YER">425400</cbc:PayableAmount>
   </cac:LegalMonetaryTotal>
   <cac:InvoiceLine>
      <cbc:ID>1</cbc:ID>
      <cbc:InvoicedQuantity unitCode="BG">100</cbc:InvoicedQuantity>
      <cbc:LineExtensionAmount currencyID="YER">425400</cbc:LineExtensionAmount>
      <cac:AllowanceCharge>
         <cbc:ChargeIndicator>false</cbc:ChargeIndicator>
         <cbc:MultiplierFactorNumeric>0</cbc:MultiplierFactorNumeric>
         <cbc:Amount currencyID="YER">0</cbc:Amount>
         <cbc:BaseAmount currencyID="YER">400000</cbc:BaseAmount>
      </cac:AllowanceCharge>
      <cac:AllowanceCharge>
         <cbc:ChargeIndicator>true</cbc:ChargeIndicator>
         <cbc:MultiplierFactorNumeric>6.3500</cbc:MultiplierFactorNumeric>
         <cbc:Amount currencyID="YER">25400</cbc:Amount>
         <cbc:BaseAmount currencyID="YER">400000</cbc:BaseAmount>
      </cac:AllowanceCharge>
      <cac:TaxTotal>
         <cbc:TaxAmount currencyID="YER">0</cbc:TaxAmount>
         <cbc:RoundingAmount currencyID="YER">400000</cbc:RoundingAmount>
      </cac:TaxTotal>
      <cac:Item>
         <cbc:Name>Item Name</cbc:Name>
         <cac:BuyersItemIdentification>
            <cbc:ID>999.003</cbc:ID>
         </cac:BuyersItemIdentification>
         <cac:SellersItemIdentification>
            <cbc:ID>999.003</cbc:ID>
         </cac:SellersItemIdentification>
         <cac:StandardItemIdentification/>
      </cac:Item>
      <cac:Price>
         <cbc:PriceAmount currencyID="YER">4000</cbc:PriceAmount>
         <cbc:BaseQuantity unitCode="BG">1</cbc:BaseQuantity>
         <cac:AllowanceCharge>
            <cbc:ChargeIndicator>false</cbc:ChargeIndicator>
            <cbc:Amount currencyID="YER">0</cbc:Amount>
            <cbc:BaseAmount currencyID="YER">4000</cbc:BaseAmount>
         </cac:AllowanceCharge>
      </cac:Price>
   </cac:InvoiceLine>
</Invoice>

I will check the test 7812279 and try to apply the test code to my case and see if it will work.

EDIT: I checked the test 7812279 but the resulted digest is invalid too. I use this site to validate the signature Chilkat Tools

Thanks @luisgoncalves for your time.

mohammad0022 commented 3 years ago

The issue maybe from the web site I use for the validation Chilkat Tools

I tried to validate the signature using the library with this code sample, and it's valid.

Do you know other web services for validating xml signature ?

luisgoncalves commented 3 years ago

At first glance your code looks correct. I don't know that site nor other sites. Isn't the recipient party of your signature verifying it?

Anyway, I'm not sure how much more I can help. As far as xades4j is concerned, everything seems correct..

mohammad0022 commented 3 years ago

The recipient party (Tax Authority) doesn't expose their API yet. They will expose in a couple of months. I have the specification required for the signature by the Tax Authority. thus I'm working on it so when the API is ready I can start testing.

Now I'm pretty sure that the library is doing very well and the generated signature is valid indeed, because I have tried to sign the same xml file with the .Net SignedXml (after applying some modification to support XAdES and EC key) and I got the same digest value as the one generated with xades4j.

Thanks @luisgoncalves for you help.

luisgoncalves commented 3 years ago

Great! I'm closing this issue then. Reopen if you need further help.