From a05732d2db0ff64559b3d27e57fca6a984cbfa64 Mon Sep 17 00:00:00 2001 From: Chris Barth Date: Thu, 27 Jul 2023 09:46:57 -0400 Subject: [PATCH] Use stricter typing in tests (#366) --- test/c14n-non-exclusive-unit-tests.spec.ts | 17 +-- test/hmac-tests.spec.ts | 51 +++++---- test/saml-response-tests.spec.ts | 117 ++++++++++++--------- test/signature-integration-tests.spec.ts | 106 +++++++++---------- test/wsfed-metadata-tests.spec.ts | 15 +-- 5 files changed, 165 insertions(+), 141 deletions(-) diff --git a/test/c14n-non-exclusive-unit-tests.spec.ts b/test/c14n-non-exclusive-unit-tests.spec.ts index 10d2a6de..44540cca 100644 --- a/test/c14n-non-exclusive-unit-tests.spec.ts +++ b/test/c14n-non-exclusive-unit-tests.spec.ts @@ -7,14 +7,17 @@ import * as utils from "../src/utils"; const test_C14nCanonicalization = function (xml, xpathArg, expected) { const doc = new xmldom.DOMParser().parseFromString(xml); - const elem = xpath.select1(xpathArg, doc); + const node = xpath.select1(xpathArg, doc); const can = new C14nCanonicalization(); - const result = can - // @ts-expect-error FIXME - .process(elem, { - ancestorNamespaces: utils.findAncestorNs(doc, xpathArg), - }) - .toString(); + let result = ""; + + if (xpath.isNodeLike(node)) { + result = can + .process(node, { + ancestorNamespaces: utils.findAncestorNs(doc, xpathArg), + }) + .toString(); + } expect(result).to.equal(expected); }; diff --git a/test/hmac-tests.spec.ts b/test/hmac-tests.spec.ts index 6b0282db..2087f62d 100644 --- a/test/hmac-tests.spec.ts +++ b/test/hmac-tests.spec.ts @@ -12,14 +12,17 @@ describe("HMAC tests", function () { "/*/*[local-name(.)='Signature' and namespace-uri(.)='http://www.w3.org/2000/09/xmldsig#']", doc, ); - const sig = new SignedXml(); - sig.enableHMAC(); - sig.publicCert = fs.readFileSync("./test/static/hmac.key"); - // @ts-expect-error FIXME - sig.loadSignature(signature); - const result = sig.checkSignature(xml); + if (xpath.isNodeLike(signature)) { + const sig = new SignedXml(); + sig.enableHMAC(); + sig.publicCert = fs.readFileSync("./test/static/hmac.key"); + sig.loadSignature(signature); + const result = sig.checkSignature(xml); - expect(result).to.be.true; + expect(result).to.be.true; + } else { + expect(xpath.isNodeLike(signature)).to.be.true; + } }); it("test HMAC signature with incorrect key", function () { @@ -29,14 +32,17 @@ describe("HMAC tests", function () { "/*/*[local-name(.)='Signature' and namespace-uri(.)='http://www.w3.org/2000/09/xmldsig#']", doc, ); - const sig = new SignedXml(); - sig.enableHMAC(); - sig.publicCert = fs.readFileSync("./test/static/hmac-foobar.key"); - // @ts-expect-error FIXME - sig.loadSignature(signature); - const result = sig.checkSignature(xml); + if (xpath.isNodeLike(signature)) { + const sig = new SignedXml(); + sig.enableHMAC(); + sig.publicCert = fs.readFileSync("./test/static/hmac-foobar.key"); + sig.loadSignature(signature); + const result = sig.checkSignature(xml); - expect(result).to.be.false; + expect(result).to.be.false; + } else { + expect(xpath.isNodeLike(signature)).to.be.true; + } }); it("test create and validate HMAC signature", function () { @@ -53,13 +59,16 @@ describe("HMAC tests", function () { "/*/*[local-name(.)='Signature' and namespace-uri(.)='http://www.w3.org/2000/09/xmldsig#']", doc, ); - const verify = new SignedXml(); - verify.enableHMAC(); - verify.publicCert = fs.readFileSync("./test/static/hmac.key"); - // @ts-expect-error FIXME - verify.loadSignature(signature); - const result = verify.checkSignature(sig.getSignedXml()); + if (xpath.isNodeLike(signature)) { + const verify = new SignedXml(); + verify.enableHMAC(); + verify.publicCert = fs.readFileSync("./test/static/hmac.key"); + verify.loadSignature(signature); + const result = verify.checkSignature(sig.getSignedXml()); - expect(result).to.be.true; + expect(result).to.be.true; + } else { + expect(xpath.isNodeLike(signature)).to.be.true; + } }); }); diff --git a/test/saml-response-tests.spec.ts b/test/saml-response-tests.spec.ts index bc2ede49..5960e366 100644 --- a/test/saml-response-tests.spec.ts +++ b/test/saml-response-tests.spec.ts @@ -12,36 +12,45 @@ describe("SAML response tests", function () { "/*/*[local-name(.)='Signature' and namespace-uri(.)='http://www.w3.org/2000/09/xmldsig#']", doc, ); - const sig = new SignedXml(); - sig.publicCert = fs.readFileSync("./test/static/feide_public.pem"); - // @ts-expect-error FIXME - sig.loadSignature(signature); - const result = sig.checkSignature(xml); + if (xpath.isNodeLike(signature)) { + const sig = new SignedXml(); + sig.publicCert = fs.readFileSync("./test/static/feide_public.pem"); + sig.loadSignature(signature); + const result = sig.checkSignature(xml); - expect(result).to.be.true; + expect(result).to.be.true; + } else { + expect(xpath.isNodeLike(signature)).to.be.true; + } }); it("test validating wrapped assertion signature", function () { const xml = fs.readFileSync("./test/static/valid_saml_signature_wrapping.xml", "utf-8"); const doc = new xmldom.DOMParser().parseFromString(xml); const assertion = xpath.select1("//*[local-name(.)='Assertion']", doc); - const signature = xpath.select1( - "//*[local-name(.)='Signature' and namespace-uri(.)='http://www.w3.org/2000/09/xmldsig#']", - // @ts-expect-error FIXME - assertion, - ); - const sig = new SignedXml(); - sig.publicCert = fs.readFileSync("./test/static/feide_public.pem"); - // @ts-expect-error FIXME - sig.loadSignature(signature); - expect( - function () { - sig.checkSignature(xml); - }, - "Should not validate a document which contains multiple elements with the " + - "same value for the ID / Id / Id attributes, in order to prevent " + - "signature wrapping attack.", - ).to.throw(); + if (xpath.isNodeLike(assertion)) { + const signature = xpath.select1( + "//*[local-name(.)='Signature' and namespace-uri(.)='http://www.w3.org/2000/09/xmldsig#']", + assertion, + ); + if (xpath.isNodeLike(signature)) { + const sig = new SignedXml(); + sig.publicCert = fs.readFileSync("./test/static/feide_public.pem"); + sig.loadSignature(signature); + expect( + function () { + sig.checkSignature(xml); + }, + "Should not validate a document which contains multiple elements with the " + + "same value for the ID / Id / Id attributes, in order to prevent " + + "signature wrapping attack.", + ).to.throw(); + } else { + expect(xpath.isNodeLike(signature)).to.be.true; + } + } else { + expect(xpath.isNodeLike(assertion)).to.be.true; + } }); it("test validating SAML response where a namespace is defined outside the signed element", function () { @@ -51,30 +60,39 @@ describe("SAML response tests", function () { "//*//*[local-name(.)='Signature' and namespace-uri(.)='http://www.w3.org/2000/09/xmldsig#']", doc, ); - const sig = new SignedXml(); - sig.publicCert = fs.readFileSync("./test/static/saml_external_ns.pem"); - // @ts-expect-error FIXME - sig.loadSignature(signature); - const result = sig.checkSignature(xml); - expect(result).to.be.true; + if (xpath.isNodeLike(signature)) { + const sig = new SignedXml(); + sig.publicCert = fs.readFileSync("./test/static/saml_external_ns.pem"); + sig.loadSignature(signature); + const result = sig.checkSignature(xml); + expect(result).to.be.true; + } else { + expect(xpath.isNodeLike(signature)).to.be.true; + } }); it("test reference id does not contain quotes", function () { const xml = fs.readFileSync("./test/static/id_with_quotes.xml", "utf-8"); const doc = new xmldom.DOMParser().parseFromString(xml); const assertion = xpath.select1("//*[local-name(.)='Assertion']", doc); - const signature = xpath.select1( - "//*[local-name(.)='Signature' and namespace-uri(.)='http://www.w3.org/2000/09/xmldsig#']", - // @ts-expect-error FIXME - assertion, - ); - const sig = new SignedXml(); - sig.publicCert = fs.readFileSync("./test/static/feide_public.pem"); - // @ts-expect-error FIXME - sig.loadSignature(signature); - expect(function () { - sig.checkSignature(xml); - }, "id should not contain quotes").to.throw(); + if (xpath.isNodeLike(assertion)) { + const signature = xpath.select1( + "//*[local-name(.)='Signature' and namespace-uri(.)='http://www.w3.org/2000/09/xmldsig#']", + assertion, + ); + if (xpath.isNodeLike(signature)) { + const sig = new SignedXml(); + sig.publicCert = fs.readFileSync("./test/static/feide_public.pem"); + sig.loadSignature(signature); + expect(function () { + sig.checkSignature(xml); + }, "id should not contain quotes").to.throw(); + } else { + expect(xpath.isNodeLike(signature)).to.be.true; + } + } else { + expect(xpath.isNodeLike(assertion)).to.be.true; + } }); it("test validating SAML response WithComments", function () { @@ -84,12 +102,15 @@ describe("SAML response tests", function () { "/*/*[local-name(.)='Signature' and namespace-uri(.)='http://www.w3.org/2000/09/xmldsig#']", doc, ); - const sig = new SignedXml(); - sig.publicCert = fs.readFileSync("./test/static/feide_public.pem"); - // @ts-expect-error FIXME - sig.loadSignature(signature); - const result = sig.checkSignature(xml); - // This doesn't matter, just want to make sure that we don't fail due to unknown algorithm - expect(result).to.be.false; + if (xpath.isNodeLike(signature)) { + const sig = new SignedXml(); + sig.publicCert = fs.readFileSync("./test/static/feide_public.pem"); + sig.loadSignature(signature); + const result = sig.checkSignature(xml); + // This doesn't matter, just want to make sure that we don't fail due to unknown algorithm + expect(result).to.be.false; + } else { + expect(xpath.isNodeLike(signature)).to.be.true; + } }); }); diff --git a/test/signature-integration-tests.spec.ts b/test/signature-integration-tests.spec.ts index e4c6f95b..a548424e 100644 --- a/test/signature-integration-tests.spec.ts +++ b/test/signature-integration-tests.spec.ts @@ -8,8 +8,6 @@ describe("Signature integration tests", function () { function verifySignature(xml, expected, xpath) { const sig = new SignedXml(); sig.privateKey = fs.readFileSync("./test/static/client.pem"); - // @ts-expect-error FIXME - sig.keyInfo = null; xpath.map(function (n) { sig.addReference({ xpath: n }); @@ -18,26 +16,8 @@ describe("Signature integration tests", function () { sig.computeSignature(xml); const signed = sig.getSignedXml(); - //fs.writeFileSync("./test/validators/XmlCryptoUtilities/XmlCryptoUtilities/bin/Debug/signedExample.xml", signed) const expectedContent = fs.readFileSync(expected).toString(); expect(signed, "signature xml different than expected").to.equal(expectedContent); - /* - var spawn = require('child_process').spawn - var proc = spawn('./test/validators/XmlCryptoUtilities/XmlCryptoUtilities/bin/Debug/XmlCryptoUtilities.exe', ['verify']) - - proc.stdout.on('data', function (data) { - console.log('stdout: ' + data); - }); - - proc.stderr.on('data', function (data) { - console.log('stderr: ' + data); - }); - - proc.on('exit', function (code) { - test.equal(0, code, "signature validation failed") - test.done() - }); - */ } it("verify signature", function () { @@ -104,83 +84,91 @@ describe("Signature integration tests", function () { xml = xml.replace(/>\s*<"); const doc = new xmldom.DOMParser().parseFromString(xml); - // @ts-expect-error FIXME - xml = doc.firstChild.toString(); + const childXml = doc.firstChild?.toString(); const signature = xpath.select1( "//*//*[local-name(.)='Signature' and namespace-uri(.)='http://www.w3.org/2000/09/xmldsig#']", doc, ); - const sig = new SignedXml(); - sig.publicCert = fs.readFileSync("./test/static/windows_store_certificate.pem"); - // @ts-expect-error FIXME - sig.loadSignature(signature); - const result = sig.checkSignature(xml); - - expect(result).to.be.true; + if (xpath.isNodeLike(signature)) { + const sig = new SignedXml(); + sig.publicCert = fs.readFileSync("./test/static/windows_store_certificate.pem"); + sig.loadSignature(signature); + const result = sig.checkSignature(childXml ?? ""); + + expect(result).to.be.true; + } else { + expect(xpath.isNodeLike(signature)).to.be.true; + } }); it("signature with inclusive namespaces", function () { - let xml = fs.readFileSync("./test/static/signature_with_inclusivenamespaces.xml", "utf-8"); + const xml = fs.readFileSync("./test/static/signature_with_inclusivenamespaces.xml", "utf-8"); const doc = new xmldom.DOMParser().parseFromString(xml); - // @ts-expect-error FIXME - xml = doc.firstChild.toString(); + const childXml = doc.firstChild?.toString(); const signature = xpath.select1( "//*//*[local-name(.)='Signature' and namespace-uri(.)='http://www.w3.org/2000/09/xmldsig#']", doc, ); - const sig = new SignedXml(); - sig.publicCert = fs.readFileSync("./test/static/signature_with_inclusivenamespaces.pem"); - // @ts-expect-error FIXME - sig.loadSignature(signature); - const result = sig.checkSignature(xml); - - expect(result).to.be.true; + if (xpath.isNodeLike(signature)) { + const sig = new SignedXml(); + sig.publicCert = fs.readFileSync("./test/static/signature_with_inclusivenamespaces.pem"); + sig.loadSignature(signature); + const result = sig.checkSignature(childXml ?? ""); + + expect(result).to.be.true; + } else { + expect(xpath.isNodeLike(signature)).to.be.true; + } }); it("signature with inclusive namespaces with unix line separators", function () { - let xml = fs.readFileSync( + const xml = fs.readFileSync( "./test/static/signature_with_inclusivenamespaces_lines.xml", "utf-8", ); const doc = new xmldom.DOMParser().parseFromString(xml); - // @ts-expect-error FIXME - xml = doc.firstChild.toString(); + const childXml = doc.firstChild?.toString(); const signature = xpath.select1( "//*//*[local-name(.)='Signature' and namespace-uri(.)='http://www.w3.org/2000/09/xmldsig#']", doc, ); - const sig = new SignedXml(); - sig.publicCert = fs.readFileSync("./test/static/signature_with_inclusivenamespaces.pem"); - // @ts-expect-error FIXME - sig.loadSignature(signature); - const result = sig.checkSignature(xml); - - expect(result).to.be.true; + if (xpath.isNodeLike(signature)) { + const sig = new SignedXml(); + sig.publicCert = fs.readFileSync("./test/static/signature_with_inclusivenamespaces.pem"); + sig.loadSignature(signature); + const result = sig.checkSignature(childXml ?? ""); + + expect(result).to.be.true; + } else { + expect(xpath.isNodeLike(signature)).to.be.true; + } }); it("signature with inclusive namespaces with windows line separators", function () { - let xml = fs.readFileSync( + const xml = fs.readFileSync( "./test/static/signature_with_inclusivenamespaces_lines_windows.xml", "utf-8", ); const doc = new xmldom.DOMParser().parseFromString(xml); - // @ts-expect-error FIXME - xml = doc.firstChild.toString(); + const childXml = doc.firstChild?.toString(); const signature = xpath.select1( "//*//*[local-name(.)='Signature' and namespace-uri(.)='http://www.w3.org/2000/09/xmldsig#']", doc, ); - const sig = new SignedXml(); - sig.publicCert = fs.readFileSync("./test/static/signature_with_inclusivenamespaces.pem"); - // @ts-expect-error FIXME - sig.loadSignature(signature); - const result = sig.checkSignature(xml); - - expect(result).to.be.true; + if (xpath.isNodeLike(signature)) { + const sig = new SignedXml(); + sig.publicCert = fs.readFileSync("./test/static/signature_with_inclusivenamespaces.pem"); + sig.loadSignature(signature); + const result = sig.checkSignature(childXml ?? ""); + + expect(result).to.be.true; + } else { + expect(xpath.isNodeLike(signature)).to.be.true; + } }); it("should create single root xml document when signing inner node", function () { diff --git a/test/wsfed-metadata-tests.spec.ts b/test/wsfed-metadata-tests.spec.ts index f80491bc..7f742ea7 100644 --- a/test/wsfed-metadata-tests.spec.ts +++ b/test/wsfed-metadata-tests.spec.ts @@ -12,12 +12,15 @@ describe("WS-Fed Metadata tests", function () { "/*/*[local-name(.)='Signature' and namespace-uri(.)='http://www.w3.org/2000/09/xmldsig#']", doc, ); - const sig = new SignedXml(); - sig.publicCert = fs.readFileSync("./test/static/wsfederation_metadata.pem"); - // @ts-expect-error FIXME - sig.loadSignature(signature); - const result = sig.checkSignature(xml); + if (xpath.isNodeLike(signature)) { + const sig = new SignedXml(); + sig.publicCert = fs.readFileSync("./test/static/wsfederation_metadata.pem"); + sig.loadSignature(signature); + const result = sig.checkSignature(xml); - expect(result).to.be.true; + expect(result).to.be.true; + } else { + expect(xpath.isNodeLike(signature)).to.be.true; + } }); });