]> source.dussan.org Git - poi.git/commitdiff
fixed compatibility issues with OpenOffice 3.0 and Excel 2008 Mac sp2, see Bugzilla...
authorYegor Kozlov <yegor@apache.org>
Fri, 24 Jul 2009 07:29:22 +0000 (07:29 +0000)
committerYegor Kozlov <yegor@apache.org>
Fri, 24 Jul 2009 07:29:22 +0000 (07:29 +0000)
git-svn-id: https://svn.apache.org/repos/asf/poi/trunk@797350 13f79535-47bb-0310-9956-ffa450edef68

src/documentation/content/xdocs/spreadsheet/quick-guide.xml
src/documentation/content/xdocs/status.xml
src/ooxml/java/org/apache/poi/openxml4j/opc/PackageRelationship.java
src/ooxml/java/org/apache/poi/openxml4j/opc/PackagingURIHelper.java
src/ooxml/java/org/apache/poi/openxml4j/opc/internal/marshallers/ZipPartMarshaller.java
src/ooxml/java/org/apache/poi/xssf/usermodel/XSSFWorkbook.java
src/ooxml/java/org/apache/poi/xwpf/usermodel/XWPFDocument.java
src/ooxml/testcases/org/apache/poi/openxml4j/opc/TestPackage.java
src/ooxml/testcases/org/apache/poi/openxml4j/opc/TestPackagingURIHelper.java
src/ooxml/testcases/org/apache/poi/xssf/usermodel/TestXSSFWorkbook.java
src/ooxml/testcases/org/apache/poi/xwpf/TestXWPFDocument.java

index d577d0974e2bc045b794af58a4eadcac2f984ebf..eeca60ebe7baa8214ea711271b7e12ad626a664f 100644 (file)
 <document>
     <header>
         <title>Busy Developers' Guide to HSSF and XSSF Features</title>
-        <authors>
-            <person email="user@poi.apache.org" name="Glen Stampoultzis" id="CO"/>
-            <person email="user@poi.apache.org" name="Yegor Kozlov" id="YK"/>
-        </authors>
     </header>
     <body>
         <section><title>Busy Developers' Guide to Features</title>
index d9045f2be54d1ad774d1193bfea16730d738d64b..26cc4a93b3a987530efc5ec9bc799cc17e6b142b 100644 (file)
@@ -33,6 +33,8 @@
 
     <changes>
         <release version="3.5-beta7" date="2009-??-??">
+           <action dev="POI-DEVELOPERS" type="fix">46419 - Fixed compatibility issue with OpenOffice 3.0</action>
+           <action dev="POI-DEVELOPERS" type="fix">47559 - Fixed compatibility issue with Excel 2008 Max sp2</action>
            <action dev="POI-DEVELOPERS" type="fix">47540 - Fix for saving custom and extended OOXML properties</action>
            <action dev="POI-DEVELOPERS" type="fix">47535 - Fixed WordExtractor to tolerate files with empty footnote block</action>
            <action dev="POI-DEVELOPERS" type="fix">47517 - Fixed ExtractorFactory to support .xltx and .dotx files</action>
index 0deb73731436a0a261fecfa65dad1c947ad0fab3..ab15fdf68714ea3d45736821c9dfa567744d22ae 100755 (executable)
@@ -136,7 +136,7 @@ public final class PackageRelationship {
 
        /* Getters */
 
-       public URI getContainerPartRelationship() {
+       public static URI getContainerPartRelationship() {
                return containerRelationshipPart;
        }
 
index b53903df9207ceb19a8443d4a37a79291a682e68..2b6dcc63f8c5b840631d188a2933db75ee72c7c8 100755 (executable)
@@ -259,11 +259,14 @@ public final class PackagingURIHelper {
         *            The source part URI.
         * @param targetURI
         *            The target part URI.
+     * @param  msCompatible if true then remove leading slash from the relativized URI.
+     *         This flag violates [M1.4]: A part name shall start with a forward slash ('/') character, but
+     *         allows generating URIs compatible with MS Office and OpenOffice.
         * @return A fully relativize part name URI ('word/media/image1.gif',
         *         '/word/document.xml' => 'media/image1.gif') else
         *         <code>null</code>.
         */
-       public static URI relativizeURI(URI sourceURI, URI targetURI) {
+       public static URI relativizeURI(URI sourceURI, URI targetURI, boolean msCompatible) {
                StringBuilder retVal = new StringBuilder();
                String[] segmentsSource = sourceURI.getPath().split("/", -1);
                String[] segmentsTarget = targetURI.getPath().split("/", -1);
@@ -283,6 +286,15 @@ public final class PackagingURIHelper {
                // If the source is the root, then the relativized
                //  form must actually be an absolute URI
                if(sourceURI.toString().equals("/")) {
+            String path = targetURI.getPath();
+            if(msCompatible && path.charAt(0) == '/') {
+                try {
+                    targetURI = new URI(path.substring(1));
+                } catch (Exception e) {
+                    System.err.println(e);
+                    return null;
+                }
+            }
                        return targetURI;
                }
 
@@ -358,7 +370,22 @@ public final class PackagingURIHelper {
                }
        }
 
-       /**
+    /**
+     * Fully relativize the source part URI against the target part URI.
+     *
+     * @param sourceURI
+     *            The source part URI.
+     * @param targetURI
+     *            The target part URI.
+     * @return A fully relativize part name URI ('word/media/image1.gif',
+     *         '/word/document.xml' => 'media/image1.gif') else
+     *         <code>null</code>.
+     */
+    public static URI relativizeURI(URI sourceURI, URI targetURI) {
+        return relativizeURI(sourceURI, targetURI, false);        
+    }
+
+    /**
         * Resolve a source uri against a target.
         *
         * @param sourcePartUri
index cfe0fb0a5d49a51ed1879c8e4c0b7f47b06ecbd4..c8bbb96af446d7fcd24d98cc82798cfa6fc1fdaf 100755 (executable)
@@ -163,7 +163,7 @@ public final class ZipPartMarshaller implements PartMarshaller {
                        } else {
                 URI targetURI = rel.getTargetURI();
                 targetValue = PackagingURIHelper.relativizeURI(
-                                               sourcePartURI, targetURI).getPath();
+                                               sourcePartURI, targetURI, true).getPath();
                 if (targetURI.getRawFragment() != null) {
                     targetValue += "#" + targetURI.getRawFragment();
                 }
index 5453b33b14519d851ece0454f963e6d6b5615b48..3ff17e456496c20ae8c46b98817174c896e85aaf 100644 (file)
@@ -30,6 +30,7 @@ import javax.xml.namespace.QName;
 import org.apache.poi.POIXMLDocument;
 import org.apache.poi.POIXMLDocumentPart;
 import org.apache.poi.POIXMLException;
+import org.apache.poi.POIXMLProperties;
 import org.apache.poi.hssf.record.formula.SheetNameFormatter;
 import org.apache.poi.openxml4j.exceptions.OpenXML4JException;
 import org.apache.poi.openxml4j.opc.OPCPackage;
@@ -228,6 +229,10 @@ public class XSSFWorkbook extends POIXMLDocument implements Workbook, Iterable<X
         bv.setActiveTab(0);
         workbook.addNewSheets();
 
+        //required by Excel 2008 Mac sp2, see Bugzilla #47559
+        POIXMLProperties.ExtendedProperties expProps = getProperties().getExtendedProperties();
+        expProps.getUnderlyingProperties().setApplication("Microsoft Excel");
+
         sharedStringSource = (SharedStringsTable)createRelationship(XSSFRelation.SHARED_STRINGS, XSSFFactory.getInstance());
         stylesSource = (StylesTable)createRelationship(XSSFRelation.STYLES, XSSFFactory.getInstance());
 
index dc08bdcce725db4a315e290328f3b63be9a6dd38..669bc4429d6e804fb14c3ae6989a9ed7fe22931a 100644 (file)
@@ -23,6 +23,7 @@ import java.util.*;
 import org.apache.poi.POIXMLDocument;
 import org.apache.poi.POIXMLException;
 import org.apache.poi.POIXMLDocumentPart;
+import org.apache.poi.POIXMLProperties;
 import org.apache.poi.util.PackageHelper;
 import org.apache.poi.xwpf.model.XWPFHeaderFooterPolicy;
 import org.apache.xmlbeans.XmlException;
@@ -187,6 +188,9 @@ public class XWPFDocument extends POIXMLDocument {
 
         ctDocument = CTDocument1.Factory.newInstance();
         ctDocument.addNewBody();
+
+        POIXMLProperties.ExtendedProperties expProps = getProperties().getExtendedProperties();
+        expProps.getUnderlyingProperties().setApplication("Microsoft Office Word");
     }
 
     /**
index 46597b78288c411066cc9bc1fe75239fa16fb51b..90e7d54458b4b9227900d7193a9d601ab7ad4121 100755 (executable)
@@ -27,6 +27,7 @@ import java.io.OutputStream;
 import java.lang.reflect.Field;
 import java.net.URI;
 import java.util.TreeMap;
+import java.util.Iterator;
 
 import junit.framework.TestCase;
 
@@ -36,11 +37,14 @@ import org.apache.poi.openxml4j.exceptions.InvalidFormatException;
 import org.apache.poi.openxml4j.opc.internal.ContentTypeManager;
 import org.apache.poi.openxml4j.opc.internal.FileHelper;
 import org.apache.poi.util.TempFile;
+import org.apache.poi.util.IOUtils;
+import org.apache.poi.util.POILogger;
 import org.dom4j.Document;
 import org.dom4j.DocumentHelper;
 import org.dom4j.Element;
 import org.dom4j.Namespace;
 import org.dom4j.QName;
+import org.dom4j.io.SAXReader;
 
 public final class TestPackage extends TestCase {
        private static Logger logger = Logger.getLogger("org.apache.poi.openxml4j.test");
@@ -185,16 +189,17 @@ public final class TestPackage extends TestCase {
         // Save and re-load
         pkg.close();
         File tmp = TempFile.createTempFile("testCreatePackageWithCoreDocument", ".zip");
-        FileOutputStream fout = new FileOutputStream(tmp);
+            FileOutputStream fout = new FileOutputStream(tmp);
         fout.write(baos.toByteArray());
         fout.close();
         pkg = OPCPackage.open(tmp.getPath());
         //tmp.delete();
-        
+
         // Check still right
         coreRels = pkg.getRelationshipsByType(PackageRelationshipTypes.CORE_DOCUMENT);
         assertEquals(1, coreRels.size());
         coreRel = coreRels.getRelationship(0);
+
         assertEquals("/", coreRel.getSourceURI().toString());
         assertEquals("/xl/workbook.xml", coreRel.getTargetURI().toString());
         corePart = pkg.getPart(coreRel);
@@ -205,10 +210,30 @@ public final class TestPackage extends TestCase {
         rel = rels.getRelationship(0);
         assertEquals("Sheet1!A1", rel.getTargetURI().getRawFragment());
 
+        assertMSCompatibility(pkg);
+    }
+
+    private void assertMSCompatibility(OPCPackage pkg) throws Exception {
+        PackagePartName relName = PackagingURIHelper.createPartName(PackageRelationship.getContainerPartRelationship());
+        PackagePart relPart = pkg.getPart(relName);
+        SAXReader reader = new SAXReader();
+        Document xmlRelationshipsDoc = reader
+                .read(relPart.getInputStream());
+
+        Element root = xmlRelationshipsDoc.getRootElement();
+        for (Iterator i = root
+                .elementIterator(PackageRelationship.RELATIONSHIP_TAG_NAME); i
+                .hasNext();) {
+            Element element = (Element) i.next();
+            String value = element.attribute(
+                    PackageRelationship.TARGET_ATTRIBUTE_NAME)
+                    .getValue();
+            assertTrue("Root target must not start with a leadng slash ('/'): " + value, value.charAt(0) != '/');
+        }
 
     }
 
-       /**
+    /**
         * Test package opening.
         */
        public void testOpenPackage() throws Exception {
index 48a4b4ecc16ee02b3422827cec74810e81bf5109..7064fc48d8cec8e7d33d7babffd524070ab9bc13 100755 (executable)
@@ -31,8 +31,6 @@ public class TestPackagingURIHelper extends TestCase {
 
        /**
         * Test relativizePartName() method.
-     *
-     * TODO: fix and unable
         */
        public void testRelativizeURI() throws Exception {
                URI uri1 = new URI("/word/document.xml");
@@ -54,23 +52,15 @@ public class TestPackagingURIHelper extends TestCase {
                URI retURI2 = PackagingURIHelper.relativizeURI(uri1, uri1);
                assertEquals("", retURI2.getPath());
 
-               // Document and root totally different
-               URI uri4 = new URI("/");
-               try {
-                       PackagingURIHelper.relativizeURI(uri1, uri4);
-                       //TODO: figure oout why the assertion fails
-            //fail("Must throw an exception ! Can't relativize with an empty URI");
-               } catch (Exception e) {
-                       // Do nothing
-               }
-               try {
-                       PackagingURIHelper.relativizeURI(uri4, uri1);
-            //TODO: figure oout why the assertion fails
-                       //fail("Must throw an exception ! Can't relativize with an empty URI");
-               } catch (Exception e) {
-                       // Do nothing
-               }
-       }
+               // relativization against root
+               URI root = new URI("/");
+        uriRes = PackagingURIHelper.relativizeURI(root, uri1);
+        assertEquals("/word/document.xml", uriRes.toString());
+
+        //URI compatible with MS Office and OpenOffice: leading slash is removed
+        uriRes = PackagingURIHelper.relativizeURI(root, uri1, true);
+        assertEquals("word/document.xml", uriRes.toString());
+    }
 
        /**
         * Test createPartName(String, y)
index 6c48e2fb164f4f693fc58763eee3ade5a8454783..2df9d8beef4f1b84a5e19cf7d513d5199cf4bb4b 100644 (file)
@@ -260,6 +260,8 @@ public final class TestXSSFWorkbook extends BaseTestWorkbook {
         XSSFWorkbook workbook = new XSSFWorkbook();
         POIXMLProperties props = workbook.getProperties();
         assertNotNull(props);
+        //the Application property must be set for new workbooks, see Bugzilla #47559
+        assertEquals("Microsoft Excel", props.getExtendedProperties().getUnderlyingProperties().getApplication());
 
         PackagePropertiesPart opcProps = props.getCoreProperties().getUnderlyingProperties();
         assertNotNull(opcProps);
@@ -269,6 +271,7 @@ public final class TestXSSFWorkbook extends BaseTestWorkbook {
         opcProps.setCreatorProperty("poi-dev@poi.apache.org");
 
         workbook = XSSFTestDataSamples.writeOutAndReadBack(workbook);
+        assertEquals("Microsoft Excel", workbook.getProperties().getExtendedProperties().getUnderlyingProperties().getApplication());
         opcProps = workbook.getProperties().getCoreProperties().getUnderlyingProperties();
         assertEquals("Testing Bugzilla #47460", opcProps.getTitleProperty().getValue());
         assertEquals("poi-dev@poi.apache.org", opcProps.getCreatorProperty().getValue());
index 68df95786cdb05d1f8bf60b07f4d1ecb1bff0175..881adf34b2d6ea86450318148f93b1f4630b1723 100644 (file)
@@ -21,6 +21,7 @@ import java.io.File;
 import junit.framework.TestCase;
 
 import org.apache.poi.POIXMLDocument;
+import org.apache.poi.POIXMLProperties;
 import org.apache.poi.openxml4j.opc.OPCPackage;
 import org.apache.poi.openxml4j.opc.PackagePart;
 import org.apache.poi.xwpf.usermodel.XWPFDocument;
@@ -119,4 +120,12 @@ public class TestXWPFDocument extends TestCase {
                assertEquals(" ", xml.getProperties().getCoreProperties().getTitle());
                assertEquals(" ", xml.getProperties().getCoreProperties().getUnderlyingProperties().getSubjectProperty().getValue());
        }
+
+    public void testWorkbookProperties() throws Exception {
+        XWPFDocument doc = new XWPFDocument();
+        POIXMLProperties props = doc.getProperties();
+        assertNotNull(props);
+        assertEquals("Microsoft Office Word", props.getExtendedProperties().getUnderlyingProperties().getApplication());
+    }
+
 }