use fiscal::complement::{attach_inutilizacao, attach_protocol};
// ── Fixture XML data (copied from PHP test fixtures) ────────────────────────
/// Signed NFe model 55 (fixtures/xml/exemplo_xml_envia_lote_modelo_55.xml)
const NFE_REQUEST: &str = r##"<NFe xmlns="http://www.portalfiscal.inf.br/nfe">
<infNFe versao="4.00" Id="NFe43211105730928000145650010000002401717268120">
<ide>
<cUF>43</cUF>
<cNF>71726812</cNF>
<natOp>Venda</natOp>
<mod>55</mod>
<serie>1</serie>
<nNF>240</nNF>
<dhEmi>2021-11-11T18:56:55-03:00</dhEmi>
<tpNF>1</tpNF>
<idDest>1</idDest>
<cMunFG>4322608</cMunFG>
<tpImp>4</tpImp>
<tpEmis>1</tpEmis>
<cDV>9</cDV>
<tpAmb>2</tpAmb>
<finNFe>1</finNFe>
<indFinal>1</indFinal>
<indPres>1</indPres>
<procEmi>0</procEmi>
<verProc>1.00</verProc>
</ide>
<emit>
<CNPJ>42530613000180</CNPJ>
<xNome>NF-E EMITIDA EM AMBIENTE DE HOMOLOGACAO - SEM VALOR FISCAL</xNome>
<xFant>Empresa Fake</xFant>
<enderEmit>
<xLgr>RUA OSVALDO ABC</xLgr>
<nro>911</nro>
<xBairro>CENTRO</xBairro>
<cMun>4322608</cMun>
<xMun>Venâncio Aires</xMun>
<UF>RS</UF>
<CEP>95800000</CEP>
<xPais>Brasil</xPais>
<fone>5199999999</fone>
</enderEmit>
<IE>9999999999</IE>
<CRT>1</CRT>
</emit>
<dest>
<CNPJ>07134266000176</CNPJ>
<xNome>Destinatario Fake</xNome>
<enderDest>
<xLgr>RUA ABC</xLgr>
<nro>913</nro>
<xBairro>CENTRO</xBairro>
<cMun>4322608</cMun>
<xMun>Venâncio Aires</xMun>
<UF>RS</UF>
<CEP>95800000</CEP>
<cPais>1058</cPais>
<xPais>BRASIL</xPais>
</enderDest>
<indIEDest>1</indIEDest>
<IE>1234567890</IE>
<email>contato@teste.com.br</email>
</dest>
<det nItem="1">
<prod>
<cProd>teste</cProd>
<cEAN>SEM GTIN</cEAN>
<xProd>NOTA FISCAL EMITIDA EM AMBIENTE DE HOMOLOGACAO - SEM VALOR FISCAL</xProd>
<NCM>64042000</NCM>
<CFOP>5102</CFOP>
<uCom>UN</uCom>
<qCom>1.0000</qCom>
<vUnCom>1.0000</vUnCom>
<vProd>1.00</vProd>
<cEANTrib>SEM GTIN</cEANTrib>
<uTrib>UN</uTrib>
<qTrib>1.0000</qTrib>
<vUnTrib>1.0000</vUnTrib>
<indTot>1</indTot>
</prod>
<imposto>
<vTotTrib>0.30</vTotTrib>
<ICMS>
<ICMSSN102>
<orig>0</orig>
<CSOSN>102</CSOSN>
</ICMSSN102>
</ICMS>
<PIS>
<PISOutr>
<CST>99</CST>
<vBC>0.00</vBC>
<pPIS>0.00</pPIS>
<vPIS>0.00</vPIS>
</PISOutr>
</PIS>
<COFINS>
<COFINSOutr>
<CST>99</CST>
<vBC>0.00</vBC>
<pCOFINS>0.00</pCOFINS>
<vCOFINS>0.00</vCOFINS>
</COFINSOutr>
</COFINS>
</imposto>
</det>
<total>
<ICMSTot>
<vBC>0.00</vBC>
<vICMS>0.00</vICMS>
<vICMSDeson>0.00</vICMSDeson>
<vFCP>0.00</vFCP>
<vBCST>0.00</vBCST>
<vST>0.00</vST>
<vFCPST>0.00</vFCPST>
<vFCPSTRet>0.00</vFCPSTRet>
<vProd>1.00</vProd>
<vFrete>0.00</vFrete>
<vSeg>0.00</vSeg>
<vDesc>0.00</vDesc>
<vII>0.00</vII>
<vIPI>0.00</vIPI>
<vIPIDevol>0.00</vIPIDevol>
<vPIS>0.00</vPIS>
<vCOFINS>0.00</vCOFINS>
<vOutro>0.00</vOutro>
<vNF>1.00</vNF>
<vTotTrib>0.30</vTotTrib>
</ICMSTot>
</total>
<transp>
<modFrete>9</modFrete>
</transp>
<pag>
<detPag>
<tPag>01</tPag>
<vPag>1.00</vPag>
</detPag>
</pag>
<infAdic>
<infAdFisco>DOCUMENTO EMITIDO POR ME OU EPP OPTANTE PELO SIMPLES NACIONAL. NÃO GERA DIREITO A CRÉDITO.</infAdFisco>
</infAdic>
<infRespTec>
<CNPJ>44738030000175</CNPJ>
<xContato>Contato Teste</xContato>
<email>teste@teste.com.br</email>
<fone>12345678901</fone>
</infRespTec>
</infNFe>
<infNFeSupl>
<qrCode>https://www.sefaz.rs.gov.br/NFCE/NFCE-COM.aspx?p=43211105730928000145650010000002401717268120|2|2|1|75FFAFF74CF8ABDD0153D4D18E27CE17DE14B83F</qrCode>
<urlChave>www.sefaz.rs.gov.br/nfce/consulta</urlChave>
</infNFeSupl>
<Signature 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="#NFe43211105730928000145650010000002401717268120">
<Transforms>
<Transform Algorithm="http://www.w3.org/2000/09/xmldsig#enveloped-signature"/>
<Transform Algorithm="http://www.w3.org/TR/2001/REC-xml-c14n-20010315"/>
</Transforms>
<DigestMethod Algorithm="http://www.w3.org/2000/09/xmldsig#sha1"/>
<DigestValue>aWpBMlDjIlWUn2ALNSdwzLi2ntE=</DigestValue>
</Reference>
</SignedInfo>
<SignatureValue>
BX0WHjsK4qAysObfxqc2iV7hohUZi9z1sLX2kcyqAVYYhcOof8N87z/ZSuX6fyfwfPa8FAdqjrzMSrhRDWFgSWXDlYabPm3g6AcDHUeS3Oo8FIhU5Asb9pGM/KTIAD8BOIqysiOGEpzvsIs+cyNxC4oG21XmSzXSPgxXx1VlU6CMjA1Nn6+LE2PUmvg3T/jHPKl9JW1KfFIh2ce5esWwhbaULcu4DP4gvZvR1CUe4v/yrtUD6PUety12avYX3LCa4WrsnxbUMp6QuffHblej6WTX4TJMwNB7/PpxnpzBRBxIgeqOIbGjrT7XK7GFhMyROZN76bSPhAqAgy3MTjXh9Q==
</SignatureValue>
<KeyInfo>
<X509Data>
<X509Certificate>
MIIHnjCCBYagAwIBAgIUZGnOycI5LCWOh/HutNnQGkOu6iQwDQYJKoZIhvcNAQELBQAwejELMAkGA1UEBhMCQlIxEzARBgNVBAoTCklDUC1CcmFzaWwxNjA0BgNVBAsTLVNlY3JldGFyaWEgZGEgUmVjZWl0YSBGZWRlcmFsIGRvIEJyYXNpbCAtIFJGQjEeMBwGA1UEAxMVQUMgRElHSVRBTFNJR04gUkZCIEcyMB4XDTIxMDIwOTEyNDE1MFoXDTIyMDIwOTEyNDE1MFowgfcxCzAJBgNVBAYTAkJSMRMwEQYDVQQKEwpJQ1AtQnJhc2lsMQswCQYDVQQIEwJSUzEXMBUGA1UEBxMOVmVuYW5jaW8gQWlyZXMxNjA0BgNVBAsTLVNlY3JldGFyaWEgZGEgUmVjZWl0YSBGZWRlcmFsIGRvIEJyYXNpbCAtIFJGQjEWMBQGA1UECxMNUkZCIGUtQ05QSiBBMTEXMBUGA1UECxMOMjY2MzkzNTAwMDAxOTYxEzARBgNVBAsTCnByZXNlbmNpYWwxLzAtBgNVBAMTJkZBQklBTkEgS0lTVCBERSBBTE1FSURBOjA1NzMwOTI4MDAwMTQ1MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEA3gmL3M7w77+Cs52uPyZlHpt4YLs86sCotQWV0GoURpIC4u7oeU0hJ8BXvZWSAAoVEKRTFGOZl2iNSd56V/ZvMZKJYR3V6p9nOWoxwf2HntsM7+GVUYmu4LjarrT3ub3cOnmjYgreInGDQWfE2jKsk40HJgxMZ+v9IR3Qrb4aWCwsoePhAEhVHvZqQF+ZsBn6Lgy+7gaFZUTKqm/zPAxG0tdWefzcXiH5g2dSu6NIlnteOvo46kh3jCmRwyMLEBTCoRp06ZWKIMXPxcyS5NddwAjCSydSogbSs+Mq93Fmew6TZxzWBmwWUhf9X/774SnoEno1vr7NrcuX3nae4XjohQIDAQABo4ICnDCCApgwDgYDVR0PAQH/BAQDAgXgMG0GCCsGAQUFBwEBBGEwXzBdBggrBgEFBQcwAoZRaHR0cDovL3d3dy5kaWdpdGFsc2lnbmNlcnRpZmljYWRvcmEuY29tLmJyL3JlcG9zaXRvcmlvL3JmYi9BQ0RJR0lUQUxTSUdOUkZCRzIucDdiMB8GA1UdIwQYMBaAFMpPQwn2SOBK1W/lLV2Ha6kpjkd7MF0GA1UdIARWMFQwUgYGYEwBAgEsMEgwRgYIKwYBBQUHAgEWOmh0dHA6Ly93d3cuZGlnaXRhbHNpZ25jZXJ0aWZpY2Fkb3JhLmNvbS5ici9yZXBvc2l0b3Jpby9yZmIwCQYDVR0TBAIwADCBsQYDVR0fBIGpMIGmMFegVaBThlFodHRwOi8vd3d3LmRpZ2l0YWxzaWduY2VydGlmaWNhZG9yYS5jb20uYnIvcmVwb3NpdG9yaW8vcmZiL0FDRElHSVRBTFNJR05SRkJHMi5jcmwwS6BJoEeGRWh0dHA6Ly93d3cuZGlnaXRhbHRydXN0LmNvbS5ici9yZXBvc2l0b3Jpby9yZmIvQUNESUdJVEFMU0lHTlJGQkcyLmNybDCBuAYDVR0RBIGwMIGtgRlkaW9yZ2VuZXNrcmVtZXJAZ21haWwuY29toDgGBWBMAQMEoC8ELTAyMTIxOTcyNjEzMzQ0MzAwNjMwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMKAiBgVgTAEDAqAZBBdGQUJJQU5BIEtJU1QgREUgQUxNRUlEQaAZBgVgTAEDA6AQBA4wNTczMDkyODAwMDE0NaAXBgVgTAEDB6AOBAwwMDAwMDAwMDAwMDAwHQYDVR0lBBYwFAYIKwYBBQUHAwIGCCsGAQUFBwMEMA0GCSqGSIb3DQEBCwUAA4ICAQAd1JoAeUH+OZyLpJrkHUkCTqWKqSmvCKZDx/CwNoX7snIEd5Uqa1YZR0KsGKOqoTXGmaAE9FBPdsbFu6Cm+YnryhhLZrgU8wOjiIhBjUOeuchbo4ojCigh+aHaH0bJ2SMUown8gb+LefCXxqLpjV0ZGXc39e/j+NEoBH9faaFBO5zqIHWj8hMxemKO2NLrxKL8Bx7PRco/D1p8Fu0V5vQRtwBX77+czGMN+RjOqPkwI5RwK88RZd0TNVczcQ9mhRpc49Oyw1mTyda8cljNl0rww6OWgVdqX4wHwpsI7TmwBm0qmOiiXBx/AwiZK6L7ocOEUvNitsNxJy4JaAzMdXB6CWWjFbCKd3RBwNhzr9qi1OB5c0QWYOMNEqAScGXMRArVAkkxX3VH0WIkjbBupz0IDNAGmNLK3voXVVmO0aCjs+q+J/OiXZ5zY4vzyn6pVVe3RJ8eIcwp03zhK385XjC+uK3tLR2Kolkc99W+DUOdc9HCc2HgiwcTms931BHBsJRiNWaZnQIClUqtsSoX2E0RVh0V/jWgPvID6DsmA0MSRgiO0q36nyM/W76U3+JrU7E8HF5lelxIxOG68c4NiD3Qk75OKdHcfXHkUGYoQ36CquOe3spCG/qGdNUvR4FgKEbLI7fIhHSIK9nRpXX+vCxS1LVDANaF7owDHjcK4Rpoqw==
</X509Certificate>
</X509Data>
</KeyInfo>
</Signature>
</NFe>"##;
/// Valid SEFAZ response with matching digest (fixtures/xml/retEnviNFe.xml)
const RET_ENVI_NFE_VALID: &str = r##"<retEnviNFe xmlns="http://www.portalfiscal.inf.br/nfe" versao="4.00"><tpAmb>2</tpAmb><verAplic>RSnfce202111190951</verAplic><cStat>104</cStat><xMotivo>Lote processado</xMotivo><cUF>43</cUF><dhRecbto>2022-01-06T17:07:34-03:00</dhRecbto><protNFe versao="4.00"><infProt><tpAmb>2</tpAmb><verAplic>RSnfce202111190951</verAplic><chNFe>43211105730928000145650010000002401717268120</chNFe><dhRecbto>2022-01-06T17:07:34-03:00</dhRecbto><nProt>143220000009921</nProt><digVal>aWpBMlDjIlWUn2ALNSdwzLi2ntE=</digVal><cStat>100</cStat><xMotivo>Autorizado o uso da NF-e</xMotivo></infProt></protNFe></retEnviNFe>"##;
/// SEFAZ response with WRONG digest (digVal has trailing "2")
const RET_ENVI_NFE_INVALID_DIGEST: &str = r##"<retEnviNFe xmlns="http://www.portalfiscal.inf.br/nfe" versao="4.00"><tpAmb>2</tpAmb><verAplic>RSnfce202111190951</verAplic><cStat>104</cStat><xMotivo>Lote processado</xMotivo><cUF>43</cUF><dhRecbto>2022-01-06T17:07:34-03:00</dhRecbto><protNFe versao="4.00"><infProt><tpAmb>2</tpAmb><verAplic>RSnfce202111190951</verAplic><chNFe>43211105730928000145650010000002401717268120</chNFe><dhRecbto>2022-01-06T17:07:34-03:00</dhRecbto><nProt>143220000009921</nProt><digVal>aWpBMlDjIlWUn2ALNSdwzLi2ntE=2</digVal><cStat>100</cStat><xMotivo>Autorizado o uso da NF-e</xMotivo></infProt></protNFe></retEnviNFe>"##;
/// Inutilizacao request with CPF (fixtures/xml/request_inut_cpf.xml)
const REQUEST_INUT_CPF: &str = r##"<inutNFe xmlns="http://www.portalfiscal.inf.br/nfe" versao="4.00">
<infInut Id="ID52250780680800010055003000000049000000049">
<tpAmb>1</tpAmb>
<xServ>INUTILIZAR</xServ>
<cUF>51</cUF>
<ano>25</ano>
<CPF>00000000000</CPF>
<mod>55</mod>
<serie>920</serie>
<nNFIni>429</nNFIni>
<nNFFin>429</nNFFin>
<xJust>Teste inutilização nfe produtor rural</xJust>
</infInut>
<Signature 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="#ID52250780680800010055003000000049000000049">
<Transforms>
<Transform Algorithm="http://www.w3.org/2000/09/xmldsig#enveloped-signature"/>
<Transform Algorithm="http://www.w3.org/TR/2001/REC-xml-c14n-20010315"/>
</Transforms>
<DigestMethod Algorithm="http://www.w3.org/2000/09/xmldsig#sha1"/>
<DigestValue>1c1Vzj0yS6LlTW55pr64DdcG47c=</DigestValue>
</Reference>
</SignedInfo>
<SignatureValue>jinDK5EmwQhBf4+g3XOpOpd/+Ph7vUcTy79ayJ9b2yvnMl9Wu9scZdjL4jKOtf3tLRcthfy2Y/a70O3A33RsKSqXuLZ+DeG/mKh4nUbooieGYI7c56Mr5yfTEgetuJchWkhZSslBvOe0v998yjLNktZ0Iz8/6tvZxBt/hXz5/ClGHPGaF4EYb+vXA0ewt84+Xc/mbk3GmmbzJJzMGj+AdomZQQL7yUw5vsrDyoCpwYnRG4qnxlAL6OYGc0IKsu5P/bJ+Q3tw7NibVCRGV7h7oGRU4dQLb+uU93shKQGZfLABUxJ09b+PbC1MZ35HTCTPiruNCFsQnS6nbTmZeqbxNA==</SignatureValue>
<KeyInfo>
<X509Data>
<X509Certificate>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</X509Certificate>
</X509Data>
</KeyInfo>
</Signature>
</inutNFe>"##;
/// SEFAZ inutilizacao response for CPF (wrapped in SOAP envelope)
const RESPONSE_INUT_CPF: &str = r##"<env:Envelope xmlns:env="http://www.w3.org/2003/05/soap-envelope">
<env:Header/>
<env:Body>
<nfeResultMsg xmlns="http://www.portalfiscal.inf.br/nfe/wsdl/NFeInutilizacao4">
<retInutNFe versao="4.00"
xmlns="http://www.portalfiscal.inf.br/nfe"
xmlns:ns0="http://www.w3.org/2000/09/xmldsig#">
<infInut>
<tpAmb>1</tpAmb>
<verAplic>MT_A2RL-4.00</verAplic>
<cStat>102</cStat>
<xMotivo>Teste inutilização nfe produtor rural</xMotivo>
<cUF>51</cUF>
<ano>25</ano>
<CPF>00000000000</CPF>
<mod>55</mod>
<serie>920</serie>
<nNFIni>429</nNFIni>
<nNFFin>429</nNFFin>
<dhRecbto>2025-02-10T08:59:46-04:00</dhRecbto>
<nProt>151250011427132</nProt>
</infInut>
</retInutNFe>
</nfeResultMsg>
</env:Body>
</env:Envelope>"##;
/// Inutilizacao request with CNPJ (fixtures/xml/request_inut_cnpj.xml)
const REQUEST_INUT_CNPJ: &str = r##"<inutNFe xmlns="http://www.portalfiscal.inf.br/nfe" versao="4.00">
<infInut Id="ID52250780680800010055003000000053000000053">
<tpAmb>2</tpAmb>
<xServ>INUTILIZAR</xServ>
<cUF>52</cUF>
<ano>25</ano>
<CNPJ>00000000000000</CNPJ>
<mod>55</mod>
<serie>3</serie>
<nNFIni>53</nNFIni>
<nNFFin>53</nNFFin>
<xJust>Exemplo de inutilizacao de NFe</xJust>
</infInut>
<Signature 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="#ID52250780680800010055003000000053000000053">
<Transforms>
<Transform Algorithm="http://www.w3.org/2000/09/xmldsig#enveloped-signature"/>
<Transform Algorithm="http://www.w3.org/TR/2001/REC-xml-c14n-20010315"/>
</Transforms>
<DigestMethod Algorithm="http://www.w3.org/2000/09/xmldsig#sha1"/>
<DigestValue>FewnNyjr4Kc+Ql4RAb0ivNQmfZE=</DigestValue>
</Reference>
</SignedInfo>
<SignatureValue>
nRPht71eB16Swx+x5pj63OQzJgR8yhnWljLFeODxvYM+mngeo/OED1MXQyUcjh4aBy3OcZEnftxQLz8jU70izF5tZN0PmJVzFofRiCLXOkkHGVqbXltCoRhHDk5JjCk37R/pR1fbKYNNZmBqt7tJmCaoDaKn6crcpdhO+ODl07AYo8BGINS4lALbfbfO87DFslCAG1JJHz3ypSDbIUaUlfzI+5JULA77QVF0ekomwTyYnFmmwXqYFZXv5/P6hyu4SCBYyY2QbfeMGWXzp5aSEfIu5+aNe8cEuK5C1FoQPKug0r/bkhwsjZMZWyrAH/fCY+IGurbXEYC1kmLsfQRDpg==
</SignatureValue>
<KeyInfo>
<X509Data>
<X509Certificate>
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
</X509Certificate>
</X509Data>
</KeyInfo>
</Signature>
</inutNFe>"##;
/// SEFAZ inutilizacao response for CNPJ (wrapped in SOAP envelope)
const RESPONSE_INUT_CNPJ: &str = r##"<env:Envelope xmlns:env="http://www.w3.org/2003/05/soap-envelope">
<env:Header/>
<env:Body>
<nfeResultMsg xmlns="http://www.portalfiscal.inf.br/nfe/wsdl/NFeInutilizacao4">
<retInutNFe versao="4.00" xmlns="http://www.portalfiscal.inf.br/nfe"
xmlns:ns0="http://www.w3.org/2000/09/xmldsig#">
<infInut>
<tpAmb>2</tpAmb>
<verAplic>GO4.0</verAplic>
<cStat>102</cStat>
<xMotivo>Inutilização de número homologado</xMotivo>
<cUF>52</cUF>
<ano>25</ano>
<CNPJ>00000000000000</CNPJ>
<mod>55</mod>
<serie>3</serie>
<nNFIni>53</nNFIni>
<nNFFin>53</nNFFin>
<dhRecbto>2025-02-10T14:31:01-03:00</dhRecbto>
<nProt>152250025831513</nProt>
</infInut>
</retInutNFe>
</nfeResultMsg>
</env:Body>
</env:Envelope>"##;
// ── Tests (ported from PHP ComplementsTest) ─────────────────────────────────
mod complements_ported_from_php {
use super::*;
#[test]
fn test_to_authorize_nfe_valid() {
let nfe_protocoled =
attach_protocol(NFE_REQUEST, RET_ENVI_NFE_VALID).expect("should succeed");
assert!(nfe_protocoled.contains("143220000009921"));
}
#[test]
fn test_to_authorize_nfe_invalid_digest() {
// PHP behavior: Complements::toAuthorize throws DocumentsException when
// digest values do not match. Rust now matches PHP: returns Err.
let result = attach_protocol(NFE_REQUEST, RET_ENVI_NFE_INVALID_DIGEST);
assert!(
result.is_err(),
"should fail when digests do not match (PHP parity)"
);
let err_msg = format!("{}", result.unwrap_err());
assert!(
err_msg.contains("digest"),
"error message should mention digest mismatch: {err_msg}"
);
}
#[test]
fn test_to_authorize_inut_cpf() {
let output =
attach_inutilizacao(REQUEST_INUT_CPF, RESPONSE_INUT_CPF).expect("should succeed");
assert!(output.contains("ProcInutNFe"));
// Mirrors PHP: assertEquals('151250011427132', $numeroProtocolo)
assert!(output.contains("<nProt>151250011427132</nProt>"));
}
#[test]
fn test_to_authorize_inut_cnpj() {
let output =
attach_inutilizacao(REQUEST_INUT_CNPJ, RESPONSE_INUT_CNPJ).expect("should succeed");
assert!(output.contains("ProcInutNFe"));
// Mirrors PHP: assertEquals('152250025831513', $numeroProtocolo)
assert!(output.contains("<nProt>152250025831513</nProt>"));
}
}