diff --git a/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/facets/OOXMLSignatureFacet.java b/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/facets/OOXMLSignatureFacet.java index 8ba8bf2395..9e094a6415 100644 --- a/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/facets/OOXMLSignatureFacet.java +++ b/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/facets/OOXMLSignatureFacet.java @@ -33,7 +33,6 @@ import java.util.HashSet; import java.util.List; import java.util.Locale; import java.util.Set; -import java.util.TimeZone; import javax.xml.XMLConstants; import javax.xml.crypto.XMLStructure; @@ -113,6 +112,7 @@ public class OOXMLSignatureFacet extends SignatureFacet { references.add(reference); } + @SuppressWarnings("resource") protected void addManifestReferences(List manifestReferences) throws XMLSignatureException { @@ -149,7 +149,10 @@ public class OOXMLSignatureFacet extends SignatureFacet { parameterSpec.addRelationshipReference(relationship.getId()); // TODO: find a better way ... - String partName = baseUri + relationship.getTargetURI().toString(); + String partName = relationship.getTargetURI().toString(); + if (!partName.startsWith(baseUri)) { + partName = baseUri + partName; + } try { partName = new URI(partName).normalize().getPath().replace('\\', '/'); LOG.log(POILogger.DEBUG, "part name: " + partName); diff --git a/src/ooxml/testcases/org/apache/poi/poifs/crypt/TestSignatureInfo.java b/src/ooxml/testcases/org/apache/poi/poifs/crypt/TestSignatureInfo.java index 6f43fdd1f1..d2fead012d 100644 --- a/src/ooxml/testcases/org/apache/poi/poifs/crypt/TestSignatureInfo.java +++ b/src/ooxml/testcases/org/apache/poi/poifs/crypt/TestSignatureInfo.java @@ -28,6 +28,8 @@ import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertNotNull; import static org.junit.Assert.assertTrue; +import java.io.ByteArrayInputStream; +import java.io.ByteArrayOutputStream; import java.io.File; import java.io.FileInputStream; import java.io.FileOutputStream; @@ -68,11 +70,13 @@ import org.apache.poi.poifs.crypt.dsig.services.RevocationData; import org.apache.poi.poifs.crypt.dsig.services.RevocationDataService; import org.apache.poi.poifs.crypt.dsig.services.TimeStampService; import org.apache.poi.poifs.crypt.dsig.services.TimeStampServiceValidator; +import org.apache.poi.ss.usermodel.WorkbookFactory; import org.apache.poi.util.DocumentHelper; import org.apache.poi.util.IOUtils; import org.apache.poi.util.LocaleUtil; import org.apache.poi.util.POILogFactory; import org.apache.poi.util.POILogger; +import org.apache.poi.xssf.streaming.SXSSFWorkbook; import org.apache.poi.xssf.usermodel.XSSFWorkbook; import org.apache.xmlbeans.XmlObject; import org.bouncycastle.asn1.x509.KeyUsage; @@ -240,6 +244,7 @@ public class TestSignatureInfo { public void testManipulation() throws Exception { // sign & validate String testFile = "hello-world-unsigned.xlsx"; + @SuppressWarnings("resource") OPCPackage pkg = OPCPackage.open(copy(testdata.getFile(testFile)), PackageAccess.READ_WRITE); sign(pkg, "Test", "CN=Test", 1); @@ -379,6 +384,7 @@ public class TestSignatureInfo { try { si.confirmSignature(); } catch (RuntimeException e) { + pkg.close(); // only allow a ConnectException because of timeout, we see this in Jenkins from time to time... if(e.getCause() == null) { throw e; @@ -546,6 +552,32 @@ public class TestSignatureInfo { } } } + + @Test + public void bug58630() throws Exception { + // test deletion of sheet 0 and signing + File tpl = copy(testdata.getFile("bug58630.xlsx")); + SXSSFWorkbook wb1 = new SXSSFWorkbook((XSSFWorkbook)WorkbookFactory.create(tpl), 10); + wb1.setCompressTempFiles(true); + wb1.removeSheetAt(0); + ByteArrayOutputStream os = new ByteArrayOutputStream(); + wb1.write(os); + wb1.close(); + OPCPackage pkg = OPCPackage.open(new ByteArrayInputStream(os.toByteArray())); + + initKeyPair("Test", "CN=Test"); + SignatureConfig signatureConfig = new SignatureConfig(); + signatureConfig.setKey(keyPair.getPrivate()); + signatureConfig.setSigningCertificateChain(Collections.singletonList(x509)); + signatureConfig.setOpcPackage(pkg); + + SignatureInfo si = new SignatureInfo(); + si.setSignatureConfig(signatureConfig); + si.confirmSignature(); + assertTrue("invalid signature", si.verifySignature()); + + pkg.close(); + } private void sign(OPCPackage pkgCopy, String alias, String signerDn, int signerCount) throws Exception { diff --git a/test-data/xmldsign/bug58630.xlsx b/test-data/xmldsign/bug58630.xlsx new file mode 100644 index 0000000000..cf7b1cc4f5 Binary files /dev/null and b/test-data/xmldsign/bug58630.xlsx differ