git-svn-id: https://svn.apache.org/repos/asf/poi/trunk@755699 13f79535-47bb-0310-9956-ffa450edef68tags/REL_3_5_BETA6
@@ -22,7 +22,7 @@ import java.util.Iterator; | |||
import org.apache.poi.xssf.eventusermodel.XSSFReader; | |||
import org.apache.poi.xssf.model.SharedStringsTable; | |||
import org.apache.poi.xssf.usermodel.XSSFRichTextString; | |||
import org.apache.poi.openxml4j.opc.Package; | |||
import org.apache.poi.openxml4j.opc.OPCPackage; | |||
import org.xml.sax.Attributes; | |||
import org.xml.sax.ContentHandler; | |||
import org.xml.sax.InputSource; | |||
@@ -36,7 +36,7 @@ import org.xml.sax.helpers.XMLReaderFactory; | |||
*/ | |||
public class FromHowTo { | |||
public void processOneSheet(String filename) throws Exception { | |||
Package pkg = Package.open(filename); | |||
OPCPackage pkg = OPCPackage.open(filename); | |||
XSSFReader r = new XSSFReader( pkg ); | |||
SharedStringsTable sst = r.getSharedStringsTable(); | |||
@@ -51,7 +51,7 @@ public class FromHowTo { | |||
} | |||
public void processAllSheets(String filename) throws Exception { | |||
Package pkg = Package.open(filename); | |||
OPCPackage pkg = OPCPackage.open(filename); | |||
XSSFReader r = new XSSFReader( pkg ); | |||
SharedStringsTable sst = r.getSharedStringsTable(); | |||
@@ -41,14 +41,14 @@ public abstract class POIXMLDocument extends POIXMLDocumentPart{ | |||
public static final String PACK_OBJECT_REL_TYPE="http://schemas.openxmlformats.org/officeDocument/2006/relationships/package"; | |||
/** The OPC Package */ | |||
private Package pkg; | |||
private OPCPackage pkg; | |||
/** | |||
* The properties of the OPC package, opened as needed | |||
*/ | |||
private POIXMLProperties properties; | |||
protected POIXMLDocument(Package pkg) { | |||
protected POIXMLDocument(OPCPackage pkg) { | |||
super(pkg); | |||
this.pkg = pkg; | |||
} | |||
@@ -58,15 +58,15 @@ public abstract class POIXMLDocument extends POIXMLDocumentPart{ | |||
* in the event of a problem. | |||
* Works around shortcomings in java's this() constructor calls | |||
*/ | |||
public static Package openPackage(String path) throws IOException { | |||
public static OPCPackage openPackage(String path) throws IOException { | |||
try { | |||
return Package.open(path); | |||
return OPCPackage.open(path); | |||
} catch (InvalidFormatException e) { | |||
throw new IOException(e.toString()); | |||
} | |||
} | |||
public Package getPackage() { | |||
public OPCPackage getPackage() { | |||
return this.pkg; | |||
} | |||
@@ -92,7 +92,7 @@ public abstract class POIXMLDocument extends POIXMLDocumentPart{ | |||
* @return The target part | |||
* @throws InvalidFormatException | |||
*/ | |||
protected static PackagePart getTargetPart(Package pkg, PackageRelationship rel) throws InvalidFormatException { | |||
protected static PackagePart getTargetPart(OPCPackage pkg, PackageRelationship rel) throws InvalidFormatException { | |||
PackagePartName relName = PackagingURIHelper.createPartName(rel.getTargetURI()); | |||
PackagePart part = pkg.getPart(relName); | |||
if (part == null) { | |||
@@ -176,7 +176,7 @@ public abstract class POIXMLDocument extends POIXMLDocumentPart{ | |||
* there is no way to change or even save such an instance in a OutputStream. | |||
* The workaround is to create a copy via a temp file | |||
*/ | |||
protected static Package ensureWriteAccess(Package pkg) throws IOException { | |||
protected static OPCPackage ensureWriteAccess(OPCPackage pkg) throws IOException { | |||
if(pkg.getPackageAccess() == PackageAccess.READ){ | |||
try { | |||
return PackageHelper.clone(pkg); |
@@ -1,269 +1,265 @@ | |||
/* ==================================================================== | |||
Licensed to the Apache Software Foundation (ASF) under one or more | |||
contributor license agreements. See the NOTICE file distributed with | |||
this work for additional information regarding copyright ownership. | |||
The ASF licenses this file to You under the Apache License, Version 2.0 | |||
(the "License"); you may not use this file except in compliance with | |||
the License. You may obtain a copy of the License at | |||
http://www.apache.org/licenses/LICENSE-2.0 | |||
Unless required by applicable law or agreed to in writing, software | |||
distributed under the License is distributed on an "AS IS" BASIS, | |||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||
See the License for the specific language governing permissions and | |||
limitations under the License. | |||
==================================================================== */ | |||
package org.apache.poi; | |||
import java.io.IOException; | |||
import java.util.LinkedList; | |||
import java.util.List; | |||
import org.apache.xmlbeans.XmlOptions; | |||
import org.apache.poi.util.POILogger; | |||
import org.apache.poi.util.POILogFactory; | |||
import org.apache.poi.openxml4j.exceptions.OpenXML4JException; | |||
import org.apache.poi.openxml4j.opc.*; | |||
import org.apache.poi.openxml4j.opc.Package; | |||
/** | |||
* Represents an entry of a OOXML package. | |||
* | |||
* <p> | |||
* Each POIXMLDocumentPart keeps a reference to the underlying a {@link org.apache.poi.openxml4j.opc.PackagePart}. | |||
* </p> | |||
* | |||
* @author Yegor Kozlov | |||
*/ | |||
public class POIXMLDocumentPart { | |||
private static POILogger logger = POILogFactory.getLogger(POIXMLDocumentPart.class); | |||
public static final XmlOptions DEFAULT_XML_OPTIONS; | |||
static { | |||
DEFAULT_XML_OPTIONS = new XmlOptions(); | |||
DEFAULT_XML_OPTIONS.setSaveOuter(); | |||
DEFAULT_XML_OPTIONS.setUseDefaultNamespace(); | |||
DEFAULT_XML_OPTIONS.setSaveAggressiveNamespaces(); | |||
} | |||
private PackagePart packagePart; | |||
private PackageRelationship packageRel; | |||
private POIXMLDocumentPart parent; | |||
private List<POIXMLDocumentPart> relations; | |||
/** | |||
* Construct POIXMLDocumentPart representing a "core document" package part. | |||
*/ | |||
public POIXMLDocumentPart(Package pkg) { | |||
try { | |||
PackageRelationship coreRel = pkg.getRelationshipsByType( | |||
PackageRelationshipTypes.CORE_DOCUMENT).getRelationship(0); | |||
this.relations = new LinkedList<POIXMLDocumentPart>(); | |||
this.packagePart = pkg.getPart(coreRel); | |||
this.packageRel = coreRel; | |||
} catch (OpenXML4JException e){ | |||
throw new POIXMLException(e); | |||
} | |||
} | |||
/** | |||
* Creates new POIXMLDocumentPart - called by client code to create new parts from scratch. | |||
* | |||
* @see #createRelationship(POIXMLRelation, POIXMLFactory, int, boolean) | |||
*/ | |||
public POIXMLDocumentPart(){ | |||
this.relations = new LinkedList<POIXMLDocumentPart>(); | |||
} | |||
/** | |||
* Creates an POIXMLDocumentPart representing the given package part and relationship. | |||
* Called by {@link #read(POIXMLFactory)} when reading in an exisiting file. | |||
* | |||
* @param part - The package part that holds xml data represenring this sheet. | |||
* @param rel - the relationship of the given package part | |||
* @see #read(POIXMLFactory) | |||
*/ | |||
public POIXMLDocumentPart(PackagePart part, PackageRelationship rel){ | |||
this.relations = new LinkedList<POIXMLDocumentPart>(); | |||
this.packagePart = part; | |||
this.packageRel = rel; | |||
} | |||
/** | |||
* Provides access to the underlying PackagePart | |||
* | |||
* @return the underlying PackagePart | |||
*/ | |||
public final PackagePart getPackagePart(){ | |||
return packagePart; | |||
} | |||
/** | |||
* Provides access to the PackageRelationship that identifies this POIXMLDocumentPart | |||
* | |||
* @return the PackageRelationship that identifies this POIXMLDocumentPart | |||
*/ | |||
public final PackageRelationship getPackageRelationship(){ | |||
return packageRel; | |||
} | |||
/** | |||
* Returns the list of child relations for this POIXMLDocumentPart | |||
* | |||
* @return child relations | |||
*/ | |||
public final List<POIXMLDocumentPart> getRelations(){ | |||
return relations; | |||
} | |||
/** | |||
* Add a new child POIXMLDocumentPart | |||
* | |||
* @param part the child to add | |||
*/ | |||
protected final void addRelation(POIXMLDocumentPart part){ | |||
relations.add(part); | |||
} | |||
/** | |||
* Remove the specified part in this package. | |||
*/ | |||
public final void removeRelation(POIXMLDocumentPart part){ | |||
getPackagePart().removeRelationship(part.getPackageRelationship().getId()); | |||
getPackagePart().getPackage().removePart(part.getPackagePart()); | |||
relations.remove(part); | |||
} | |||
/** | |||
* Returns the parent POIXMLDocumentPart. All parts except root have not-null parent. | |||
* | |||
* @return the parent POIXMLDocumentPart or <code>null</code> for the root element. | |||
*/ | |||
public final POIXMLDocumentPart getParent(){ | |||
return parent; | |||
} | |||
@Override | |||
public String toString(){ | |||
return packagePart.toString(); | |||
} | |||
/** | |||
* Save the content in the underlying package part. | |||
* Default implementation is empty meaning that the package part is left unmodified. | |||
* | |||
* Sub-classes should override and add logic to marshal the "model" into Ooxml4J. | |||
* | |||
* For example, the code saving a generic XML entry may look as follows: | |||
* <pre><code> | |||
* protected void commit() throws IOException { | |||
* PackagePart part = getPackagePart(); | |||
* OutputStream out = part.getOutputStream(); | |||
* XmlObject bean = getXmlBean(); //the "model" which holds changes in memory | |||
* bean.save(out, DEFAULT_XML_OPTIONS); | |||
* out.close(); | |||
* } | |||
* </code></pre> | |||
* | |||
*/ | |||
protected void commit() throws IOException { | |||
} | |||
/** | |||
* Save changes in the underlying OOXML package. | |||
* Recursively fires {@link #commit()} for each package part | |||
*/ | |||
protected final void onSave() throws IOException{ | |||
commit(); | |||
for(POIXMLDocumentPart p : relations){ | |||
p.onSave(); | |||
} | |||
} | |||
/** | |||
* Create a new child POIXMLDocumentPart | |||
* | |||
* @param descriptor the part descriptor | |||
* @param factory the factory that will create an instance of the requested relation | |||
* @return the created child POIXMLDocumentPart | |||
*/ | |||
protected final POIXMLDocumentPart createRelationship(POIXMLRelation descriptor, POIXMLFactory factory){ | |||
return createRelationship(descriptor, factory, -1, false); | |||
} | |||
protected final POIXMLDocumentPart createRelationship(POIXMLRelation descriptor, POIXMLFactory factory, int idx){ | |||
return createRelationship(descriptor, factory, idx, false); | |||
} | |||
/** | |||
* Create a new child POIXMLDocumentPart | |||
* | |||
* @param descriptor the part descriptor | |||
* @param factory the factory that will create an instance of the requested relation | |||
* @param idx part number | |||
* @param noRelation if true, then no relationship is added. | |||
* @return the created child POIXMLDocumentPart | |||
*/ | |||
protected final POIXMLDocumentPart createRelationship(POIXMLRelation descriptor, POIXMLFactory factory, int idx, boolean noRelation){ | |||
try { | |||
PackagePartName ppName = PackagingURIHelper.createPartName(descriptor.getFileName(idx)); | |||
PackageRelationship rel = null; | |||
if(!noRelation) rel = packagePart.addRelationship(ppName, TargetMode.INTERNAL, descriptor.getRelation()); | |||
PackagePart part = packagePart.getPackage().createPart(ppName, descriptor.getContentType()); | |||
POIXMLDocumentPart doc = factory.newDocumentPart(descriptor); | |||
doc.packageRel = rel; | |||
doc.packagePart = part; | |||
doc.parent = this; | |||
addRelation(doc); | |||
return doc; | |||
} catch (Exception e){ | |||
throw new POIXMLException(e); | |||
} | |||
} | |||
/** | |||
* Iterate through the underlying PackagePart and create child POIXMLFactory instances | |||
* using the specified factory | |||
* | |||
* @param factory the factory object that creates POIXMLFactory instances | |||
*/ | |||
protected final void read(POIXMLFactory factory) throws OpenXML4JException { | |||
PackageRelationshipCollection rels = packagePart.getRelationships(); | |||
for (PackageRelationship rel : rels) { | |||
if(rel.getTargetMode() == TargetMode.INTERNAL){ | |||
PackagePartName relName = PackagingURIHelper.createPartName(rel.getTargetURI()); | |||
PackagePart p = packagePart.getPackage().getPart(relName); | |||
if(p == null) { | |||
logger.log(POILogger.ERROR, "Skipped invalid entry " + rel.getTargetURI()); | |||
continue; | |||
} | |||
POIXMLDocumentPart childPart = factory.createDocumentPart(rel, p); | |||
childPart.parent = this; | |||
addRelation(childPart); | |||
if(p.hasRelationships()) childPart.read(factory); | |||
} | |||
} | |||
} | |||
/** | |||
* Fired when a new package part is created | |||
*/ | |||
protected void onDocumentCreate() throws IOException { | |||
} | |||
/** | |||
* Fired when a package part is read | |||
*/ | |||
protected void onDocumentRead() throws IOException{ | |||
} | |||
} | |||
/* ==================================================================== | |||
Licensed to the Apache Software Foundation (ASF) under one or more | |||
contributor license agreements. See the NOTICE file distributed with | |||
this work for additional information regarding copyright ownership. | |||
The ASF licenses this file to You under the Apache License, Version 2.0 | |||
(the "License"); you may not use this file except in compliance with | |||
the License. You may obtain a copy of the License at | |||
http://www.apache.org/licenses/LICENSE-2.0 | |||
Unless required by applicable law or agreed to in writing, software | |||
distributed under the License is distributed on an "AS IS" BASIS, | |||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||
See the License for the specific language governing permissions and | |||
limitations under the License. | |||
==================================================================== */ | |||
package org.apache.poi; | |||
import java.io.IOException; | |||
import java.util.LinkedList; | |||
import java.util.List; | |||
import org.apache.xmlbeans.XmlOptions; | |||
import org.apache.poi.util.POILogger; | |||
import org.apache.poi.util.POILogFactory; | |||
import org.apache.poi.openxml4j.exceptions.OpenXML4JException; | |||
import org.apache.poi.openxml4j.opc.*; | |||
import org.apache.poi.openxml4j.opc.Package; | |||
/** | |||
* Represents an entry of a OOXML package. | |||
* | |||
* <p> | |||
* Each POIXMLDocumentPart keeps a reference to the underlying a {@link org.apache.poi.openxml4j.opc.PackagePart}. | |||
* </p> | |||
* | |||
* @author Yegor Kozlov | |||
*/ | |||
public class POIXMLDocumentPart { | |||
private static POILogger logger = POILogFactory.getLogger(POIXMLDocumentPart.class); | |||
public static final XmlOptions DEFAULT_XML_OPTIONS; | |||
static { | |||
DEFAULT_XML_OPTIONS = new XmlOptions(); | |||
DEFAULT_XML_OPTIONS.setSaveOuter(); | |||
DEFAULT_XML_OPTIONS.setUseDefaultNamespace(); | |||
DEFAULT_XML_OPTIONS.setSaveAggressiveNamespaces(); | |||
} | |||
private PackagePart packagePart; | |||
private PackageRelationship packageRel; | |||
private POIXMLDocumentPart parent; | |||
private List<POIXMLDocumentPart> relations; | |||
/** | |||
* Construct POIXMLDocumentPart representing a "core document" package part. | |||
*/ | |||
public POIXMLDocumentPart(OPCPackage pkg) { | |||
PackageRelationship coreRel = pkg.getRelationshipsByType( | |||
PackageRelationshipTypes.CORE_DOCUMENT).getRelationship(0); | |||
this.relations = new LinkedList<POIXMLDocumentPart>(); | |||
this.packagePart = pkg.getPart(coreRel); | |||
this.packageRel = coreRel; | |||
} | |||
/** | |||
* Creates new POIXMLDocumentPart - called by client code to create new parts from scratch. | |||
* | |||
* @see #createRelationship(POIXMLRelation, POIXMLFactory, int, boolean) | |||
*/ | |||
public POIXMLDocumentPart(){ | |||
this.relations = new LinkedList<POIXMLDocumentPart>(); | |||
} | |||
/** | |||
* Creates an POIXMLDocumentPart representing the given package part and relationship. | |||
* Called by {@link #read(POIXMLFactory)} when reading in an exisiting file. | |||
* | |||
* @param part - The package part that holds xml data represenring this sheet. | |||
* @param rel - the relationship of the given package part | |||
* @see #read(POIXMLFactory) | |||
*/ | |||
public POIXMLDocumentPart(PackagePart part, PackageRelationship rel){ | |||
this.relations = new LinkedList<POIXMLDocumentPart>(); | |||
this.packagePart = part; | |||
this.packageRel = rel; | |||
} | |||
/** | |||
* Provides access to the underlying PackagePart | |||
* | |||
* @return the underlying PackagePart | |||
*/ | |||
public final PackagePart getPackagePart(){ | |||
return packagePart; | |||
} | |||
/** | |||
* Provides access to the PackageRelationship that identifies this POIXMLDocumentPart | |||
* | |||
* @return the PackageRelationship that identifies this POIXMLDocumentPart | |||
*/ | |||
public final PackageRelationship getPackageRelationship(){ | |||
return packageRel; | |||
} | |||
/** | |||
* Returns the list of child relations for this POIXMLDocumentPart | |||
* | |||
* @return child relations | |||
*/ | |||
public final List<POIXMLDocumentPart> getRelations(){ | |||
return relations; | |||
} | |||
/** | |||
* Add a new child POIXMLDocumentPart | |||
* | |||
* @param part the child to add | |||
*/ | |||
protected final void addRelation(POIXMLDocumentPart part){ | |||
relations.add(part); | |||
} | |||
/** | |||
* Remove the specified part in this package. | |||
*/ | |||
public final void removeRelation(POIXMLDocumentPart part){ | |||
getPackagePart().removeRelationship(part.getPackageRelationship().getId()); | |||
getPackagePart().getPackage().removePart(part.getPackagePart()); | |||
relations.remove(part); | |||
} | |||
/** | |||
* Returns the parent POIXMLDocumentPart. All parts except root have not-null parent. | |||
* | |||
* @return the parent POIXMLDocumentPart or <code>null</code> for the root element. | |||
*/ | |||
public final POIXMLDocumentPart getParent(){ | |||
return parent; | |||
} | |||
@Override | |||
public String toString(){ | |||
return packagePart.toString(); | |||
} | |||
/** | |||
* Save the content in the underlying package part. | |||
* Default implementation is empty meaning that the package part is left unmodified. | |||
* | |||
* Sub-classes should override and add logic to marshal the "model" into Ooxml4J. | |||
* | |||
* For example, the code saving a generic XML entry may look as follows: | |||
* <pre><code> | |||
* protected void commit() throws IOException { | |||
* PackagePart part = getPackagePart(); | |||
* OutputStream out = part.getOutputStream(); | |||
* XmlObject bean = getXmlBean(); //the "model" which holds changes in memory | |||
* bean.save(out, DEFAULT_XML_OPTIONS); | |||
* out.close(); | |||
* } | |||
* </code></pre> | |||
* | |||
*/ | |||
protected void commit() throws IOException { | |||
} | |||
/** | |||
* Save changes in the underlying OOXML package. | |||
* Recursively fires {@link #commit()} for each package part | |||
*/ | |||
protected final void onSave() throws IOException{ | |||
commit(); | |||
for(POIXMLDocumentPart p : relations){ | |||
p.onSave(); | |||
} | |||
} | |||
/** | |||
* Create a new child POIXMLDocumentPart | |||
* | |||
* @param descriptor the part descriptor | |||
* @param factory the factory that will create an instance of the requested relation | |||
* @return the created child POIXMLDocumentPart | |||
*/ | |||
protected final POIXMLDocumentPart createRelationship(POIXMLRelation descriptor, POIXMLFactory factory){ | |||
return createRelationship(descriptor, factory, -1, false); | |||
} | |||
protected final POIXMLDocumentPart createRelationship(POIXMLRelation descriptor, POIXMLFactory factory, int idx){ | |||
return createRelationship(descriptor, factory, idx, false); | |||
} | |||
/** | |||
* Create a new child POIXMLDocumentPart | |||
* | |||
* @param descriptor the part descriptor | |||
* @param factory the factory that will create an instance of the requested relation | |||
* @param idx part number | |||
* @param noRelation if true, then no relationship is added. | |||
* @return the created child POIXMLDocumentPart | |||
*/ | |||
protected final POIXMLDocumentPart createRelationship(POIXMLRelation descriptor, POIXMLFactory factory, int idx, boolean noRelation){ | |||
try { | |||
PackagePartName ppName = PackagingURIHelper.createPartName(descriptor.getFileName(idx)); | |||
PackageRelationship rel = null; | |||
if(!noRelation) rel = packagePart.addRelationship(ppName, TargetMode.INTERNAL, descriptor.getRelation()); | |||
PackagePart part = packagePart.getPackage().createPart(ppName, descriptor.getContentType()); | |||
POIXMLDocumentPart doc = factory.newDocumentPart(descriptor); | |||
doc.packageRel = rel; | |||
doc.packagePart = part; | |||
doc.parent = this; | |||
addRelation(doc); | |||
return doc; | |||
} catch (Exception e){ | |||
throw new POIXMLException(e); | |||
} | |||
} | |||
/** | |||
* Iterate through the underlying PackagePart and create child POIXMLFactory instances | |||
* using the specified factory | |||
* | |||
* @param factory the factory object that creates POIXMLFactory instances | |||
*/ | |||
protected final void read(POIXMLFactory factory) throws OpenXML4JException { | |||
PackageRelationshipCollection rels = packagePart.getRelationships(); | |||
for (PackageRelationship rel : rels) { | |||
if(rel.getTargetMode() == TargetMode.INTERNAL){ | |||
PackagePartName relName = PackagingURIHelper.createPartName(rel.getTargetURI()); | |||
PackagePart p = packagePart.getPackage().getPart(relName); | |||
if(p == null) { | |||
logger.log(POILogger.ERROR, "Skipped invalid entry " + rel.getTargetURI()); | |||
continue; | |||
} | |||
POIXMLDocumentPart childPart = factory.createDocumentPart(rel, p); | |||
childPart.parent = this; | |||
addRelation(childPart); | |||
if(p.hasRelationships()) childPart.read(factory); | |||
} | |||
} | |||
} | |||
/** | |||
* Fired when a new package part is created | |||
*/ | |||
protected void onDocumentCreate() throws IOException { | |||
} | |||
/** | |||
* Fired when a package part is read | |||
*/ | |||
protected void onDocumentRead() throws IOException{ | |||
} | |||
} |
@@ -18,23 +18,23 @@ package org.apache.poi; | |||
import java.io.IOException; | |||
import org.apache.xmlbeans.XmlException; | |||
import org.apache.poi.openxml4j.exceptions.OpenXML4JException; | |||
import org.apache.poi.openxml4j.opc.Package; | |||
import org.apache.poi.openxml4j.opc.OPCPackage; | |||
import org.apache.poi.openxml4j.opc.PackageRelationshipCollection; | |||
import org.apache.poi.openxml4j.opc.internal.PackagePropertiesPart; | |||
import org.apache.xmlbeans.XmlException; | |||
/** | |||
* Wrapper around the two different kinds of OOXML properties | |||
* a document can have | |||
*/ | |||
public class POIXMLProperties { | |||
private Package pkg; | |||
private OPCPackage pkg; | |||
private CoreProperties core; | |||
private ExtendedProperties ext; | |||
private CustomProperties cust; | |||
public POIXMLProperties(Package docPackage) throws IOException, OpenXML4JException, XmlException { | |||
public POIXMLProperties(OPCPackage docPackage) throws IOException, OpenXML4JException, XmlException { | |||
this.pkg = docPackage; | |||
// Core properties | |||
@@ -97,7 +97,7 @@ public class POIXMLProperties { | |||
* Writes out the ooxml properties into the supplied, | |||
* new Package | |||
*/ | |||
public void write(Package pkg) { | |||
public void write(OPCPackage pkg) { | |||
// TODO | |||
} | |||
@@ -22,7 +22,7 @@ import java.io.InputStream; | |||
import java.io.PrintStream; | |||
import java.util.ArrayList; | |||
import org.apache.poi.openxml4j.opc.Package; | |||
import org.apache.poi.openxml4j.opc.OPCPackage; | |||
import org.apache.poi.openxml4j.opc.PackageAccess; | |||
import org.apache.poi.openxml4j.opc.PackagePart; | |||
import org.apache.poi.openxml4j.opc.PackageRelationship; | |||
@@ -34,13 +34,13 @@ import org.apache.poi.openxml4j.opc.PackageRelationshipCollection; | |||
* they're all related to each other. | |||
*/ | |||
public class OOXMLLister { | |||
private Package container; | |||
private OPCPackage container; | |||
private PrintStream disp; | |||
public OOXMLLister(Package container) { | |||
public OOXMLLister(OPCPackage container) { | |||
this(container, System.out); | |||
} | |||
public OOXMLLister(Package container, PrintStream disp) { | |||
public OOXMLLister(OPCPackage container, PrintStream disp) { | |||
this.container = container; | |||
this.disp = disp; | |||
} | |||
@@ -122,7 +122,7 @@ public class OOXMLLister { | |||
} | |||
OOXMLLister lister = new OOXMLLister( | |||
Package.open(f.toString(), PackageAccess.READ) | |||
OPCPackage.open(f.toString(), PackageAccess.READ) | |||
); | |||
lister.disp.println(f.toString() + "\n"); |
@@ -33,6 +33,11 @@ import org.apache.poi.hdgf.extractor.VisioTextExtractor; | |||
import org.apache.poi.hslf.extractor.PowerPointExtractor; | |||
import org.apache.poi.hssf.extractor.ExcelExtractor; | |||
import org.apache.poi.hwpf.extractor.WordExtractor; | |||
import org.apache.poi.openxml4j.exceptions.InvalidFormatException; | |||
import org.apache.poi.openxml4j.exceptions.OpenXML4JException; | |||
import org.apache.poi.openxml4j.opc.OPCPackage; | |||
import org.apache.poi.openxml4j.opc.PackagePart; | |||
import org.apache.poi.openxml4j.opc.PackageRelationshipCollection; | |||
import org.apache.poi.poifs.filesystem.DirectoryEntry; | |||
import org.apache.poi.poifs.filesystem.DirectoryNode; | |||
import org.apache.poi.poifs.filesystem.Entry; | |||
@@ -41,14 +46,9 @@ import org.apache.poi.xslf.XSLFSlideShow; | |||
import org.apache.poi.xslf.extractor.XSLFPowerPointExtractor; | |||
import org.apache.poi.xssf.extractor.XSSFExcelExtractor; | |||
import org.apache.poi.xssf.usermodel.XSSFRelation; | |||
import org.apache.poi.xwpf.usermodel.XWPFRelation; | |||
import org.apache.poi.xwpf.extractor.XWPFWordExtractor; | |||
import org.apache.poi.xwpf.usermodel.XWPFRelation; | |||
import org.apache.xmlbeans.XmlException; | |||
import org.apache.poi.openxml4j.exceptions.InvalidFormatException; | |||
import org.apache.poi.openxml4j.exceptions.OpenXML4JException; | |||
import org.apache.poi.openxml4j.opc.Package; | |||
import org.apache.poi.openxml4j.opc.PackagePart; | |||
import org.apache.poi.openxml4j.opc.PackageRelationshipCollection; | |||
/** | |||
* Figures out the correct POITextExtractor for your supplied | |||
@@ -67,7 +67,7 @@ public class ExtractorFactory { | |||
} | |||
if(POIXMLDocument.hasOOXMLHeader(inp)) { | |||
inp.close(); | |||
return createExtractor(Package.open(f.toString())); | |||
return createExtractor(OPCPackage.open(f.toString())); | |||
} | |||
throw new IllegalArgumentException("Your File was neither an OLE2 file, nor an OOXML file"); | |||
} | |||
@@ -83,12 +83,12 @@ public class ExtractorFactory { | |||
return createExtractor(new POIFSFileSystem(inp)); | |||
} | |||
if(POIXMLDocument.hasOOXMLHeader(inp)) { | |||
return createExtractor(Package.open(inp)); | |||
return createExtractor(OPCPackage.open(inp)); | |||
} | |||
throw new IllegalArgumentException("Your InputStream was neither an OLE2 stream, nor an OOXML stream"); | |||
} | |||
public static POIXMLTextExtractor createExtractor(Package pkg) throws IOException, OpenXML4JException, XmlException { | |||
public static POIXMLTextExtractor createExtractor(OPCPackage pkg) throws IOException, OpenXML4JException, XmlException { | |||
PackageRelationshipCollection core = | |||
pkg.getRelationshipsByType(CORE_DOCUMENT_REL); | |||
if(core.size() != 1) { |
@@ -1,227 +1,227 @@ | |||
/* ==================================================================== | |||
Licensed to the Apache Software Foundation (ASF) under one or more | |||
contributor license agreements. See the NOTICE file distributed with | |||
this work for additional information regarding copyright ownership. | |||
The ASF licenses this file to You under the Apache License, Version 2.0 | |||
(the "License"); you may not use this file except in compliance with | |||
the License. You may obtain a copy of the License at | |||
http://www.apache.org/licenses/LICENSE-2.0 | |||
Unless required by applicable law or agreed to in writing, software | |||
distributed under the License is distributed on an "AS IS" BASIS, | |||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||
See the License for the specific language governing permissions and | |||
limitations under the License. | |||
==================================================================== */ | |||
package org.apache.poi.openxml4j.opc; | |||
import java.util.Date; | |||
import org.apache.poi.openxml4j.util.Nullable; | |||
/** | |||
* Represents the core properties of an OPC package. | |||
* | |||
* @author Julien Chable | |||
* @version 1.0 | |||
* @see org.apache.poi.openxml4j.opc.Package | |||
*/ | |||
public interface PackageProperties { | |||
/** | |||
* Dublin Core Terms URI. | |||
*/ | |||
public final static String NAMESPACE_DCTERMS = "http://purl.org/dc/terms/"; | |||
/** | |||
* Dublin Core namespace URI. | |||
*/ | |||
public final static String NAMESPACE_DC = "http://purl.org/dc/elements/1.1/"; | |||
/* Getters and setters */ | |||
/** | |||
* Set the category of the content of this package. | |||
*/ | |||
public abstract Nullable<String> getCategoryProperty(); | |||
/** | |||
* Set the category of the content of this package. | |||
*/ | |||
public abstract void setCategoryProperty(String category); | |||
/** | |||
* Set the status of the content. | |||
*/ | |||
public abstract Nullable<String> getContentStatusProperty(); | |||
/** | |||
* Get the status of the content. | |||
*/ | |||
public abstract void setContentStatusProperty(String contentStatus); | |||
/** | |||
* Get the type of content represented, generally defined by a specific use | |||
* and intended audience. | |||
*/ | |||
public abstract Nullable<String> getContentTypeProperty(); | |||
/** | |||
* Set the type of content represented, generally defined by a specific use | |||
* and intended audience. | |||
*/ | |||
public abstract void setContentTypeProperty(String contentType); | |||
/** | |||
* Get the date of creation of the resource. | |||
*/ | |||
public abstract Nullable<Date> getCreatedProperty(); | |||
/** | |||
* Set the date of creation of the resource. | |||
*/ | |||
public abstract void setCreatedProperty(String created); | |||
/** | |||
* Set the date of creation of the resource. | |||
*/ | |||
public abstract void setCreatedProperty(Nullable<Date> created); | |||
/** | |||
* Get the entity primarily responsible for making the content of the | |||
* resource. | |||
*/ | |||
public abstract Nullable<String> getCreatorProperty(); | |||
/** | |||
* Set the entity primarily responsible for making the content of the | |||
* resource. | |||
*/ | |||
public abstract void setCreatorProperty(String creator); | |||
/** | |||
* Get the explanation of the content of the resource. | |||
*/ | |||
public abstract Nullable<String> getDescriptionProperty(); | |||
/** | |||
* Set the explanation of the content of the resource. | |||
*/ | |||
public abstract void setDescriptionProperty(String description); | |||
/** | |||
* Get an unambiguous reference to the resource within a given context. | |||
*/ | |||
public abstract Nullable<String> getIdentifierProperty(); | |||
/** | |||
* Set an unambiguous reference to the resource within a given context. | |||
*/ | |||
public abstract void setIdentifierProperty(String identifier); | |||
/** | |||
* Get a delimited set of keywords to support searching and indexing. This | |||
* is typically a list of terms that are not available elsewhere in the | |||
* properties | |||
*/ | |||
public abstract Nullable<String> getKeywordsProperty(); | |||
/** | |||
* Set a delimited set of keywords to support searching and indexing. This | |||
* is typically a list of terms that are not available elsewhere in the | |||
* properties | |||
*/ | |||
public abstract void setKeywordsProperty(String keywords); | |||
/** | |||
* Get the language of the intellectual content of the resource. | |||
*/ | |||
public abstract Nullable<String> getLanguageProperty(); | |||
/** | |||
* Set the language of the intellectual content of the resource. | |||
*/ | |||
public abstract void setLanguageProperty(String language); | |||
/** | |||
* Get the user who performed the last modification. | |||
*/ | |||
public abstract Nullable<String> getLastModifiedByProperty(); | |||
/** | |||
* Set the user who performed the last modification. | |||
*/ | |||
public abstract void setLastModifiedByProperty(String lastModifiedBy); | |||
/** | |||
* Get the date and time of the last printing. | |||
*/ | |||
public abstract Nullable<Date> getLastPrintedProperty(); | |||
/** | |||
* Set the date and time of the last printing. | |||
*/ | |||
public abstract void setLastPrintedProperty(String lastPrinted); | |||
/** | |||
* Set the date and time of the last printing. | |||
*/ | |||
public abstract void setLastPrintedProperty(Nullable<Date> lastPrinted); | |||
/** | |||
* Get the date on which the resource was changed. | |||
*/ | |||
public abstract Nullable<Date> getModifiedProperty(); | |||
/** | |||
* Set the date on which the resource was changed. | |||
*/ | |||
public abstract void setModifiedProperty(String modified); | |||
/** | |||
* Set the date on which the resource was changed. | |||
*/ | |||
public abstract void setModifiedProperty(Nullable<Date> modified); | |||
/** | |||
* Get the revision number. | |||
*/ | |||
public abstract Nullable<String> getRevisionProperty(); | |||
/** | |||
* Set the revision number. | |||
*/ | |||
public abstract void setRevisionProperty(String revision); | |||
/** | |||
* Get the topic of the content of the resource. | |||
*/ | |||
public abstract Nullable<String> getSubjectProperty(); | |||
/** | |||
* Set the topic of the content of the resource. | |||
*/ | |||
public abstract void setSubjectProperty(String subject); | |||
/** | |||
* Get the name given to the resource. | |||
*/ | |||
public abstract Nullable<String> getTitleProperty(); | |||
/** | |||
* Set the name given to the resource. | |||
*/ | |||
public abstract void setTitleProperty(String title); | |||
/** | |||
* Get the version number. | |||
*/ | |||
public abstract Nullable<String> getVersionProperty(); | |||
/** | |||
* Set the version number. | |||
*/ | |||
public abstract void setVersionProperty(String version); | |||
} | |||
/* ==================================================================== | |||
Licensed to the Apache Software Foundation (ASF) under one or more | |||
contributor license agreements. See the NOTICE file distributed with | |||
this work for additional information regarding copyright ownership. | |||
The ASF licenses this file to You under the Apache License, Version 2.0 | |||
(the "License"); you may not use this file except in compliance with | |||
the License. You may obtain a copy of the License at | |||
http://www.apache.org/licenses/LICENSE-2.0 | |||
Unless required by applicable law or agreed to in writing, software | |||
distributed under the License is distributed on an "AS IS" BASIS, | |||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||
See the License for the specific language governing permissions and | |||
limitations under the License. | |||
==================================================================== */ | |||
package org.apache.poi.openxml4j.opc; | |||
import java.util.Date; | |||
import org.apache.poi.openxml4j.util.Nullable; | |||
/** | |||
* Represents the core properties of an OPC package. | |||
* | |||
* @author Julien Chable | |||
* @version 1.0 | |||
* @see org.apache.poi.openxml4j.opc.OPCPackage | |||
*/ | |||
public interface PackageProperties { | |||
/** | |||
* Dublin Core Terms URI. | |||
*/ | |||
public final static String NAMESPACE_DCTERMS = "http://purl.org/dc/terms/"; | |||
/** | |||
* Dublin Core namespace URI. | |||
*/ | |||
public final static String NAMESPACE_DC = "http://purl.org/dc/elements/1.1/"; | |||
/* Getters and setters */ | |||
/** | |||
* Set the category of the content of this package. | |||
*/ | |||
public abstract Nullable<String> getCategoryProperty(); | |||
/** | |||
* Set the category of the content of this package. | |||
*/ | |||
public abstract void setCategoryProperty(String category); | |||
/** | |||
* Set the status of the content. | |||
*/ | |||
public abstract Nullable<String> getContentStatusProperty(); | |||
/** | |||
* Get the status of the content. | |||
*/ | |||
public abstract void setContentStatusProperty(String contentStatus); | |||
/** | |||
* Get the type of content represented, generally defined by a specific use | |||
* and intended audience. | |||
*/ | |||
public abstract Nullable<String> getContentTypeProperty(); | |||
/** | |||
* Set the type of content represented, generally defined by a specific use | |||
* and intended audience. | |||
*/ | |||
public abstract void setContentTypeProperty(String contentType); | |||
/** | |||
* Get the date of creation of the resource. | |||
*/ | |||
public abstract Nullable<Date> getCreatedProperty(); | |||
/** | |||
* Set the date of creation of the resource. | |||
*/ | |||
public abstract void setCreatedProperty(String created); | |||
/** | |||
* Set the date of creation of the resource. | |||
*/ | |||
public abstract void setCreatedProperty(Nullable<Date> created); | |||
/** | |||
* Get the entity primarily responsible for making the content of the | |||
* resource. | |||
*/ | |||
public abstract Nullable<String> getCreatorProperty(); | |||
/** | |||
* Set the entity primarily responsible for making the content of the | |||
* resource. | |||
*/ | |||
public abstract void setCreatorProperty(String creator); | |||
/** | |||
* Get the explanation of the content of the resource. | |||
*/ | |||
public abstract Nullable<String> getDescriptionProperty(); | |||
/** | |||
* Set the explanation of the content of the resource. | |||
*/ | |||
public abstract void setDescriptionProperty(String description); | |||
/** | |||
* Get an unambiguous reference to the resource within a given context. | |||
*/ | |||
public abstract Nullable<String> getIdentifierProperty(); | |||
/** | |||
* Set an unambiguous reference to the resource within a given context. | |||
*/ | |||
public abstract void setIdentifierProperty(String identifier); | |||
/** | |||
* Get a delimited set of keywords to support searching and indexing. This | |||
* is typically a list of terms that are not available elsewhere in the | |||
* properties | |||
*/ | |||
public abstract Nullable<String> getKeywordsProperty(); | |||
/** | |||
* Set a delimited set of keywords to support searching and indexing. This | |||
* is typically a list of terms that are not available elsewhere in the | |||
* properties | |||
*/ | |||
public abstract void setKeywordsProperty(String keywords); | |||
/** | |||
* Get the language of the intellectual content of the resource. | |||
*/ | |||
public abstract Nullable<String> getLanguageProperty(); | |||
/** | |||
* Set the language of the intellectual content of the resource. | |||
*/ | |||
public abstract void setLanguageProperty(String language); | |||
/** | |||
* Get the user who performed the last modification. | |||
*/ | |||
public abstract Nullable<String> getLastModifiedByProperty(); | |||
/** | |||
* Set the user who performed the last modification. | |||
*/ | |||
public abstract void setLastModifiedByProperty(String lastModifiedBy); | |||
/** | |||
* Get the date and time of the last printing. | |||
*/ | |||
public abstract Nullable<Date> getLastPrintedProperty(); | |||
/** | |||
* Set the date and time of the last printing. | |||
*/ | |||
public abstract void setLastPrintedProperty(String lastPrinted); | |||
/** | |||
* Set the date and time of the last printing. | |||
*/ | |||
public abstract void setLastPrintedProperty(Nullable<Date> lastPrinted); | |||
/** | |||
* Get the date on which the resource was changed. | |||
*/ | |||
public abstract Nullable<Date> getModifiedProperty(); | |||
/** | |||
* Set the date on which the resource was changed. | |||
*/ | |||
public abstract void setModifiedProperty(String modified); | |||
/** | |||
* Set the date on which the resource was changed. | |||
*/ | |||
public abstract void setModifiedProperty(Nullable<Date> modified); | |||
/** | |||
* Get the revision number. | |||
*/ | |||
public abstract Nullable<String> getRevisionProperty(); | |||
/** | |||
* Set the revision number. | |||
*/ | |||
public abstract void setRevisionProperty(String revision); | |||
/** | |||
* Get the topic of the content of the resource. | |||
*/ | |||
public abstract Nullable<String> getSubjectProperty(); | |||
/** | |||
* Set the topic of the content of the resource. | |||
*/ | |||
public abstract void setSubjectProperty(String subject); | |||
/** | |||
* Get the name given to the resource. | |||
*/ | |||
public abstract Nullable<String> getTitleProperty(); | |||
/** | |||
* Set the name given to the resource. | |||
*/ | |||
public abstract void setTitleProperty(String title); | |||
/** | |||
* Get the version number. | |||
*/ | |||
public abstract Nullable<String> getVersionProperty(); | |||
/** | |||
* Set the version number. | |||
*/ | |||
public abstract void setVersionProperty(String version); | |||
} |
@@ -1,227 +1,227 @@ | |||
/* ==================================================================== | |||
Licensed to the Apache Software Foundation (ASF) under one or more | |||
contributor license agreements. See the NOTICE file distributed with | |||
this work for additional information regarding copyright ownership. | |||
The ASF licenses this file to You under the Apache License, Version 2.0 | |||
(the "License"); you may not use this file except in compliance with | |||
the License. You may obtain a copy of the License at | |||
http://www.apache.org/licenses/LICENSE-2.0 | |||
Unless required by applicable law or agreed to in writing, software | |||
distributed under the License is distributed on an "AS IS" BASIS, | |||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||
See the License for the specific language governing permissions and | |||
limitations under the License. | |||
==================================================================== */ | |||
package org.apache.poi.openxml4j.opc; | |||
import java.net.URI; | |||
import java.net.URISyntaxException; | |||
/** | |||
* A part relationship. | |||
* | |||
* @author Julien Chable | |||
* @version 1.0 | |||
*/ | |||
public final class PackageRelationship { | |||
private static URI containerRelationshipPart; | |||
static { | |||
try { | |||
containerRelationshipPart = new URI("/_rels/.rels"); | |||
} catch (URISyntaxException e) { | |||
// Do nothing | |||
} | |||
} | |||
/* XML markup */ | |||
public static final String ID_ATTRIBUTE_NAME = "Id"; | |||
public static final String RELATIONSHIPS_TAG_NAME = "Relationships"; | |||
public static final String RELATIONSHIP_TAG_NAME = "Relationship"; | |||
public static final String TARGET_ATTRIBUTE_NAME = "Target"; | |||
public static final String TARGET_MODE_ATTRIBUTE_NAME = "TargetMode"; | |||
public static final String TYPE_ATTRIBUTE_NAME = "Type"; | |||
/* End XML markup */ | |||
/** | |||
* L'ID de la relation. | |||
*/ | |||
private String id; | |||
/** | |||
* Reference to the package. | |||
*/ | |||
private Package container; | |||
/** | |||
* Type de relation. | |||
*/ | |||
private String relationshipType; | |||
/** | |||
* Partie source de cette relation. | |||
*/ | |||
private PackagePart source; | |||
/** | |||
* Le mode de ciblage [Internal|External] | |||
*/ | |||
private TargetMode targetMode; | |||
/** | |||
* URI de la partie cible. | |||
*/ | |||
private URI targetUri; | |||
/** | |||
* Constructor. | |||
* | |||
* @param pkg | |||
* @param sourcePart | |||
* @param targetUri | |||
* @param targetMode | |||
* @param relationshipType | |||
* @param id | |||
*/ | |||
public PackageRelationship(Package pkg, PackagePart sourcePart, | |||
URI targetUri, TargetMode targetMode, String relationshipType, | |||
String id) { | |||
if (pkg == null) | |||
throw new IllegalArgumentException("pkg"); | |||
if (targetUri == null) | |||
throw new IllegalArgumentException("targetUri"); | |||
if (relationshipType == null) | |||
throw new IllegalArgumentException("relationshipType"); | |||
if (id == null) | |||
throw new IllegalArgumentException("id"); | |||
this.container = pkg; | |||
this.source = sourcePart; | |||
this.targetUri = targetUri; | |||
this.targetMode = targetMode; | |||
this.relationshipType = relationshipType; | |||
this.id = id; | |||
} | |||
@Override | |||
public boolean equals(Object obj) { | |||
if (!(obj instanceof PackageRelationship)) { | |||
return false; | |||
} | |||
PackageRelationship rel = (PackageRelationship) obj; | |||
return (this.id == rel.id | |||
&& this.relationshipType == rel.relationshipType | |||
&& (rel.source != null ? rel.source.equals(this.source) : true) | |||
&& this.targetMode == rel.targetMode && this.targetUri | |||
.equals(rel.targetUri)); | |||
} | |||
@Override | |||
public int hashCode() { | |||
return this.id.hashCode() + this.relationshipType.hashCode() | |||
+ this.source.hashCode() + this.targetMode.hashCode() | |||
+ this.targetUri.hashCode(); | |||
} | |||
/* Getters */ | |||
public URI getContainerPartRelationship() { | |||
return containerRelationshipPart; | |||
} | |||
/** | |||
* @return the container | |||
*/ | |||
public Package getPackage() { | |||
return container; | |||
} | |||
/** | |||
* @return the id | |||
*/ | |||
public String getId() { | |||
return id; | |||
} | |||
/** | |||
* @return the relationshipType | |||
*/ | |||
public String getRelationshipType() { | |||
return relationshipType; | |||
} | |||
/** | |||
* @return the source | |||
*/ | |||
public PackagePart getSource() { | |||
return source; | |||
} | |||
/** | |||
* | |||
* @return URL of the source part of this relationship | |||
*/ | |||
public URI getSourceURI() { | |||
if (source == null) { | |||
return PackagingURIHelper.PACKAGE_ROOT_URI; | |||
} | |||
return source.partName.getURI(); | |||
} | |||
/** | |||
* public URI getSourceUri(){ } | |||
* | |||
* @return the targetMode | |||
*/ | |||
public TargetMode getTargetMode() { | |||
return targetMode; | |||
} | |||
/** | |||
* @return the targetUri | |||
*/ | |||
public URI getTargetURI() { | |||
// If it's an external target, we don't | |||
// need to apply our normal validation rules | |||
if(targetMode == TargetMode.EXTERNAL) { | |||
return targetUri; | |||
} | |||
// Internal target | |||
// If it isn't absolute, resolve it relative | |||
// to ourselves | |||
if (!targetUri.toASCIIString().startsWith("/")) { | |||
// So it's a relative part name, try to resolve it | |||
return PackagingURIHelper.resolvePartUri(getSourceURI(), targetUri); | |||
} | |||
return targetUri; | |||
} | |||
@Override | |||
public String toString() { | |||
StringBuilder sb = new StringBuilder(); | |||
sb.append(id == null ? "id=null" : "id=" + id); | |||
sb.append(container == null ? " - container=null" : " - container=" | |||
+ container.toString()); | |||
sb.append(relationshipType == null ? " - relationshipType=null" | |||
: " - relationshipType=" + relationshipType.toString()); | |||
sb.append(source == null ? " - source=null" : " - source=" | |||
+ getSourceURI().toASCIIString()); | |||
sb.append(targetUri == null ? " - target=null" : " - target=" | |||
+ getTargetURI().toASCIIString()); | |||
sb.append(targetMode == null ? ",targetMode=null" : ",targetMode=" | |||
+ targetMode.toString()); | |||
return sb.toString(); | |||
} | |||
} | |||
/* ==================================================================== | |||
Licensed to the Apache Software Foundation (ASF) under one or more | |||
contributor license agreements. See the NOTICE file distributed with | |||
this work for additional information regarding copyright ownership. | |||
The ASF licenses this file to You under the Apache License, Version 2.0 | |||
(the "License"); you may not use this file except in compliance with | |||
the License. You may obtain a copy of the License at | |||
http://www.apache.org/licenses/LICENSE-2.0 | |||
Unless required by applicable law or agreed to in writing, software | |||
distributed under the License is distributed on an "AS IS" BASIS, | |||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||
See the License for the specific language governing permissions and | |||
limitations under the License. | |||
==================================================================== */ | |||
package org.apache.poi.openxml4j.opc; | |||
import java.net.URI; | |||
import java.net.URISyntaxException; | |||
/** | |||
* A part relationship. | |||
* | |||
* @author Julien Chable | |||
* @version 1.0 | |||
*/ | |||
public final class PackageRelationship { | |||
private static URI containerRelationshipPart; | |||
static { | |||
try { | |||
containerRelationshipPart = new URI("/_rels/.rels"); | |||
} catch (URISyntaxException e) { | |||
// Do nothing | |||
} | |||
} | |||
/* XML markup */ | |||
public static final String ID_ATTRIBUTE_NAME = "Id"; | |||
public static final String RELATIONSHIPS_TAG_NAME = "Relationships"; | |||
public static final String RELATIONSHIP_TAG_NAME = "Relationship"; | |||
public static final String TARGET_ATTRIBUTE_NAME = "Target"; | |||
public static final String TARGET_MODE_ATTRIBUTE_NAME = "TargetMode"; | |||
public static final String TYPE_ATTRIBUTE_NAME = "Type"; | |||
/* End XML markup */ | |||
/** | |||
* L'ID de la relation. | |||
*/ | |||
private String id; | |||
/** | |||
* Reference to the package. | |||
*/ | |||
private OPCPackage container; | |||
/** | |||
* Type de relation. | |||
*/ | |||
private String relationshipType; | |||
/** | |||
* Partie source de cette relation. | |||
*/ | |||
private PackagePart source; | |||
/** | |||
* Le mode de ciblage [Internal|External] | |||
*/ | |||
private TargetMode targetMode; | |||
/** | |||
* URI de la partie cible. | |||
*/ | |||
private URI targetUri; | |||
/** | |||
* Constructor. | |||
* | |||
* @param pkg | |||
* @param sourcePart | |||
* @param targetUri | |||
* @param targetMode | |||
* @param relationshipType | |||
* @param id | |||
*/ | |||
public PackageRelationship(OPCPackage pkg, PackagePart sourcePart, | |||
URI targetUri, TargetMode targetMode, String relationshipType, | |||
String id) { | |||
if (pkg == null) | |||
throw new IllegalArgumentException("pkg"); | |||
if (targetUri == null) | |||
throw new IllegalArgumentException("targetUri"); | |||
if (relationshipType == null) | |||
throw new IllegalArgumentException("relationshipType"); | |||
if (id == null) | |||
throw new IllegalArgumentException("id"); | |||
this.container = pkg; | |||
this.source = sourcePart; | |||
this.targetUri = targetUri; | |||
this.targetMode = targetMode; | |||
this.relationshipType = relationshipType; | |||
this.id = id; | |||
} | |||
@Override | |||
public boolean equals(Object obj) { | |||
if (!(obj instanceof PackageRelationship)) { | |||
return false; | |||
} | |||
PackageRelationship rel = (PackageRelationship) obj; | |||
return (this.id == rel.id | |||
&& this.relationshipType == rel.relationshipType | |||
&& (rel.source != null ? rel.source.equals(this.source) : true) | |||
&& this.targetMode == rel.targetMode && this.targetUri | |||
.equals(rel.targetUri)); | |||
} | |||
@Override | |||
public int hashCode() { | |||
return this.id.hashCode() + this.relationshipType.hashCode() | |||
+ this.source.hashCode() + this.targetMode.hashCode() | |||
+ this.targetUri.hashCode(); | |||
} | |||
/* Getters */ | |||
public URI getContainerPartRelationship() { | |||
return containerRelationshipPart; | |||
} | |||
/** | |||
* @return the container | |||
*/ | |||
public OPCPackage getPackage() { | |||
return container; | |||
} | |||
/** | |||
* @return the id | |||
*/ | |||
public String getId() { | |||
return id; | |||
} | |||
/** | |||
* @return the relationshipType | |||
*/ | |||
public String getRelationshipType() { | |||
return relationshipType; | |||
} | |||
/** | |||
* @return the source | |||
*/ | |||
public PackagePart getSource() { | |||
return source; | |||
} | |||
/** | |||
* | |||
* @return URL of the source part of this relationship | |||
*/ | |||
public URI getSourceURI() { | |||
if (source == null) { | |||
return PackagingURIHelper.PACKAGE_ROOT_URI; | |||
} | |||
return source.partName.getURI(); | |||
} | |||
/** | |||
* public URI getSourceUri(){ } | |||
* | |||
* @return the targetMode | |||
*/ | |||
public TargetMode getTargetMode() { | |||
return targetMode; | |||
} | |||
/** | |||
* @return the targetUri | |||
*/ | |||
public URI getTargetURI() { | |||
// If it's an external target, we don't | |||
// need to apply our normal validation rules | |||
if(targetMode == TargetMode.EXTERNAL) { | |||
return targetUri; | |||
} | |||
// Internal target | |||
// If it isn't absolute, resolve it relative | |||
// to ourselves | |||
if (!targetUri.toASCIIString().startsWith("/")) { | |||
// So it's a relative part name, try to resolve it | |||
return PackagingURIHelper.resolvePartUri(getSourceURI(), targetUri); | |||
} | |||
return targetUri; | |||
} | |||
@Override | |||
public String toString() { | |||
StringBuilder sb = new StringBuilder(); | |||
sb.append(id == null ? "id=null" : "id=" + id); | |||
sb.append(container == null ? " - container=null" : " - container=" | |||
+ container.toString()); | |||
sb.append(relationshipType == null ? " - relationshipType=null" | |||
: " - relationshipType=" + relationshipType.toString()); | |||
sb.append(source == null ? " - source=null" : " - source=" | |||
+ getSourceURI().toASCIIString()); | |||
sb.append(targetUri == null ? " - target=null" : " - target=" | |||
+ getTargetURI().toASCIIString()); | |||
sb.append(targetMode == null ? ",targetMode=null" : ",targetMode=" | |||
+ targetMode.toString()); | |||
return sb.toString(); | |||
} | |||
} |
@@ -1,451 +1,451 @@ | |||
/* ==================================================================== | |||
Licensed to the Apache Software Foundation (ASF) under one or more | |||
contributor license agreements. See the NOTICE file distributed with | |||
this work for additional information regarding copyright ownership. | |||
The ASF licenses this file to You under the Apache License, Version 2.0 | |||
(the "License"); you may not use this file except in compliance with | |||
the License. You may obtain a copy of the License at | |||
http://www.apache.org/licenses/LICENSE-2.0 | |||
Unless required by applicable law or agreed to in writing, software | |||
distributed under the License is distributed on an "AS IS" BASIS, | |||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||
See the License for the specific language governing permissions and | |||
limitations under the License. | |||
==================================================================== */ | |||
package org.apache.poi.openxml4j.opc; | |||
import java.net.URI; | |||
import java.net.URISyntaxException; | |||
import java.util.ArrayList; | |||
import java.util.Iterator; | |||
import java.util.TreeMap; | |||
import org.dom4j.Attribute; | |||
import org.dom4j.Document; | |||
import org.dom4j.Element; | |||
import org.dom4j.io.SAXReader; | |||
import org.apache.poi.openxml4j.exceptions.InvalidFormatException; | |||
import org.apache.poi.openxml4j.exceptions.InvalidOperationException; | |||
import org.apache.poi.util.POILogger; | |||
import org.apache.poi.util.POILogFactory; | |||
/** | |||
* Represents a collection of PackageRelationship elements that are owned by a | |||
* given PackagePart or the Package. | |||
* | |||
* @author Julien Chable, CDubettier | |||
* @version 0.1 | |||
*/ | |||
public final class PackageRelationshipCollection implements | |||
Iterable<PackageRelationship> { | |||
private static POILogger logger = POILogFactory.getLogger(PackageRelationshipCollection.class); | |||
/** | |||
* Package relationships ordered by ID. | |||
*/ | |||
private TreeMap<String, PackageRelationship> relationshipsByID; | |||
/** | |||
* Package relationships ordered by type. | |||
*/ | |||
private TreeMap<String, PackageRelationship> relationshipsByType; | |||
/** | |||
* This relationshipPart. | |||
*/ | |||
private PackagePart relationshipPart; | |||
/** | |||
* Source part. | |||
*/ | |||
private PackagePart sourcePart; | |||
/** | |||
* This part name. | |||
*/ | |||
private PackagePartName partName; | |||
/** | |||
* Reference to the package. | |||
*/ | |||
private Package container; | |||
/** | |||
* Constructor. | |||
*/ | |||
PackageRelationshipCollection() { | |||
relationshipsByID = new TreeMap<String, PackageRelationship>(); | |||
relationshipsByType = new TreeMap<String, PackageRelationship>(); | |||
} | |||
/** | |||
* Copy constructor. | |||
* | |||
* This collection will contain only elements from the specified collection | |||
* for which the type is compatible with the specified relationship type | |||
* filter. | |||
* | |||
* @param coll | |||
* Collection to import. | |||
* @param filter | |||
* Relationship type filter. | |||
*/ | |||
public PackageRelationshipCollection(PackageRelationshipCollection coll, | |||
String filter) { | |||
this(); | |||
for (PackageRelationship rel : coll.relationshipsByID.values()) { | |||
if (filter == null || rel.getRelationshipType().equals(filter)) | |||
addRelationship(rel); | |||
} | |||
} | |||
/** | |||
* Constructor. | |||
*/ | |||
public PackageRelationshipCollection(Package container) | |||
throws InvalidFormatException { | |||
this(container, null); | |||
} | |||
/** | |||
* Constructor. | |||
* | |||
* @throws InvalidFormatException | |||
* Throws if the format of the content part is invalid. | |||
* | |||
* @throws InvalidOperationException | |||
* Throws if the specified part is a relationship part. | |||
*/ | |||
public PackageRelationshipCollection(PackagePart part) | |||
throws InvalidFormatException { | |||
this(part.container, part); | |||
} | |||
/** | |||
* Constructor. Parse the existing package relationship part if one exists. | |||
* | |||
* @param container | |||
* The parent package. | |||
* @param part | |||
* The part that own this relationships collection. If <b>null</b> | |||
* then this part is considered as the package root. | |||
* @throws InvalidFormatException | |||
* If an error occurs during the parsing of the relatinships | |||
* part fo the specified part. | |||
*/ | |||
public PackageRelationshipCollection(Package container, PackagePart part) | |||
throws InvalidFormatException { | |||
this(); | |||
if (container == null) | |||
throw new IllegalArgumentException("container"); | |||
// Check if the specified part is not a relationship part | |||
if (part != null && part.isRelationshipPart()) | |||
throw new IllegalArgumentException("part"); | |||
this.container = container; | |||
this.sourcePart = part; | |||
this.partName = getRelationshipPartName(part); | |||
if ((container.getPackageAccess() != PackageAccess.WRITE) | |||
&& container.containPart(this.partName)) { | |||
relationshipPart = container.getPart(this.partName); | |||
parseRelationshipsPart(relationshipPart); | |||
} | |||
} | |||
/** | |||
* Get the relationship part name of the specified part. | |||
* | |||
* @param part | |||
* The part . | |||
* @return The relationship part name of the specified part. Be careful, | |||
* only the correct name is returned, this method does not check if | |||
* the part really exist in a package ! | |||
* @throws InvalidOperationException | |||
* Throws if the specified part is a relationship part. | |||
*/ | |||
private static PackagePartName getRelationshipPartName(PackagePart part) | |||
throws InvalidOperationException { | |||
PackagePartName partName; | |||
if (part == null) { | |||
partName = PackagingURIHelper.PACKAGE_ROOT_PART_NAME; | |||
} else { | |||
partName = part.getPartName(); | |||
} | |||
return PackagingURIHelper.getRelationshipPartName(partName); | |||
} | |||
/** | |||
* Add the specified relationship to the collection. | |||
* | |||
* @param relPart | |||
* The relationship to add. | |||
*/ | |||
public void addRelationship(PackageRelationship relPart) { | |||
relationshipsByID.put(relPart.getId(), relPart); | |||
relationshipsByType.put(relPart.getRelationshipType(), relPart); | |||
} | |||
/** | |||
* Add a relationship to the collection. | |||
* | |||
* @param targetUri | |||
* Target URI. | |||
* @param targetMode | |||
* The target mode : INTERNAL or EXTERNAL | |||
* @param relationshipType | |||
* Relationship type. | |||
* @param id | |||
* Relationship ID. | |||
* @return The newly created relationship. | |||
* @see PackageAccess | |||
*/ | |||
public PackageRelationship addRelationship(URI targetUri, | |||
TargetMode targetMode, String relationshipType, String id) { | |||
if (id == null) { | |||
// Generate a unique ID is id parameter is null. | |||
int i = 0; | |||
do { | |||
id = "rId" + ++i; | |||
} while (relationshipsByID.get(id) != null); | |||
} | |||
PackageRelationship rel = new PackageRelationship(container, | |||
sourcePart, targetUri, targetMode, relationshipType, id); | |||
relationshipsByID.put(rel.getId(), rel); | |||
relationshipsByType.put(rel.getRelationshipType(), rel); | |||
return rel; | |||
} | |||
/** | |||
* Remove a relationship by its ID. | |||
* | |||
* @param id | |||
* The relationship ID to remove. | |||
*/ | |||
public void removeRelationship(String id) { | |||
if (relationshipsByID != null && relationshipsByType != null) { | |||
PackageRelationship rel = relationshipsByID.get(id); | |||
if (rel != null) { | |||
relationshipsByID.remove(rel.getId()); | |||
relationshipsByType.values().remove(rel); | |||
} | |||
} | |||
} | |||
/** | |||
* Remove a relationship by its reference. | |||
* | |||
* @param rel | |||
* The relationship to delete. | |||
*/ | |||
public void removeRelationship(PackageRelationship rel) { | |||
if (rel == null) | |||
throw new IllegalArgumentException("rel"); | |||
relationshipsByID.values().remove(rel); | |||
relationshipsByType.values().remove(rel); | |||
} | |||
/** | |||
* Retrieves a relationship by its index in the collection. | |||
* | |||
* @param index | |||
* Must be a value between [0-relationships_count-1] | |||
*/ | |||
public PackageRelationship getRelationship(int index) { | |||
if (index < 0 || index > relationshipsByID.values().size()) | |||
throw new IllegalArgumentException("index"); | |||
PackageRelationship retRel = null; | |||
int i = 0; | |||
for (PackageRelationship rel : relationshipsByID.values()) { | |||
if (index == i++) | |||
return rel; | |||
} | |||
return retRel; | |||
} | |||
/** | |||
* Retrieves a package relationship based on its id. | |||
* | |||
* @param id | |||
* ID of the package relationship to retrieve. | |||
* @return The package relationship identified by the specified id. | |||
*/ | |||
public PackageRelationship getRelationshipByID(String id) { | |||
return relationshipsByID.get(id); | |||
} | |||
/** | |||
* Get the numbe rof relationships in the collection. | |||
*/ | |||
public int size() { | |||
return relationshipsByID.values().size(); | |||
} | |||
/** | |||
* Parse the relationship part and add all relationship in this collection. | |||
* | |||
* @param relPart | |||
* The package part to parse. | |||
* @throws InvalidFormatException | |||
* Throws if the relationship part is invalid. | |||
*/ | |||
private void parseRelationshipsPart(PackagePart relPart) | |||
throws InvalidFormatException { | |||
try { | |||
SAXReader reader = new SAXReader(); | |||
logger.log(POILogger.DEBUG, "Parsing relationship: " + relPart.getPartName()); | |||
Document xmlRelationshipsDoc = reader | |||
.read(relPart.getInputStream()); | |||
// Browse default types | |||
Element root = xmlRelationshipsDoc.getRootElement(); | |||
// Check OPC compliance M4.1 rule | |||
boolean fCorePropertiesRelationship = false; | |||
for (Iterator i = root | |||
.elementIterator(PackageRelationship.RELATIONSHIP_TAG_NAME); i | |||
.hasNext();) { | |||
Element element = (Element) i.next(); | |||
// Relationship ID | |||
String id = element.attribute( | |||
PackageRelationship.ID_ATTRIBUTE_NAME).getValue(); | |||
// Relationship type | |||
String type = element.attribute( | |||
PackageRelationship.TYPE_ATTRIBUTE_NAME).getValue(); | |||
/* Check OPC Compliance */ | |||
// Check Rule M4.1 | |||
if (type.equals(PackageRelationshipTypes.CORE_PROPERTIES)) | |||
if (!fCorePropertiesRelationship) | |||
fCorePropertiesRelationship = true; | |||
else | |||
throw new InvalidFormatException( | |||
"OPC Compliance error [M4.1]: there is more than one core properties relationship in the package !"); | |||
/* End OPC Compliance */ | |||
// TargetMode (default value "Internal") | |||
Attribute targetModeAttr = element | |||
.attribute(PackageRelationship.TARGET_MODE_ATTRIBUTE_NAME); | |||
TargetMode targetMode = TargetMode.INTERNAL; | |||
if (targetModeAttr != null) { | |||
targetMode = targetModeAttr.getValue().toLowerCase() | |||
.equals("internal") ? TargetMode.INTERNAL | |||
: TargetMode.EXTERNAL; | |||
} | |||
// Target converted in URI | |||
URI target; | |||
String value = ""; | |||
try { | |||
value = element.attribute( | |||
PackageRelationship.TARGET_ATTRIBUTE_NAME) | |||
.getValue(); | |||
if (value.indexOf("\\") != -1) { | |||
logger | |||
.log(POILogger.INFO, "target contains \\ therefore not a valid URI" | |||
+ value + " replaced by /"); | |||
value = value.replaceAll("\\\\", "/"); | |||
// word can save external relationship with a \ instead | |||
// of / | |||
} | |||
target = new URI(value); | |||
} catch (URISyntaxException e) { | |||
logger.log(POILogger.ERROR, "Cannot convert " + value | |||
+ " in a valid relationship URI-> ignored", e); | |||
continue; | |||
} | |||
addRelationship(target, targetMode, type, id); | |||
} | |||
} catch (Exception e) { | |||
logger.log(POILogger.ERROR, e); | |||
throw new InvalidFormatException(e.getMessage()); | |||
} | |||
} | |||
/** | |||
* Retrieves all relations with the specified type. | |||
* | |||
* @param typeFilter | |||
* Relationship type filter. If <b>null</b> then all | |||
* relationships are returned. | |||
* @return All relationships of the type specified by the filter. | |||
*/ | |||
public PackageRelationshipCollection getRelationships(String typeFilter) { | |||
PackageRelationshipCollection coll = new PackageRelationshipCollection( | |||
this, typeFilter); | |||
return coll; | |||
} | |||
/** | |||
* Get this collection's iterator. | |||
*/ | |||
public Iterator<PackageRelationship> iterator() { | |||
return relationshipsByID.values().iterator(); | |||
} | |||
/** | |||
* Get an iterator of a collection with all relationship with the specified | |||
* type. | |||
* | |||
* @param typeFilter | |||
* Type filter. | |||
* @return An iterator to a collection containing all relationships with the | |||
* specified type contain in this collection. | |||
*/ | |||
public Iterator<PackageRelationship> iterator(String typeFilter) { | |||
ArrayList<PackageRelationship> retArr = new ArrayList<PackageRelationship>(); | |||
for (PackageRelationship rel : relationshipsByID.values()) { | |||
if (rel.getRelationshipType().equals(typeFilter)) | |||
retArr.add(rel); | |||
} | |||
return retArr.iterator(); | |||
} | |||
/** | |||
* Clear all relationships. | |||
*/ | |||
public void clear() { | |||
relationshipsByID.clear(); | |||
relationshipsByType.clear(); | |||
} | |||
@Override | |||
public String toString() { | |||
String str; | |||
if (relationshipsByID == null) { | |||
str = "relationshipsByID=null"; | |||
} else { | |||
str = relationshipsByID.size() + " relationship(s) = ["; | |||
} | |||
if ((relationshipPart != null) && (relationshipPart.partName != null)) { | |||
str = str + "," + relationshipPart.partName; | |||
} else { | |||
str = str + ",relationshipPart=null"; | |||
} | |||
// Source of this relationship | |||
if ((sourcePart != null) && (sourcePart.partName != null)) { | |||
str = str + "," + sourcePart.partName; | |||
} else { | |||
str = str + ",sourcePart=null"; | |||
} | |||
if (partName != null) { | |||
str = str + "," + partName; | |||
} else { | |||
str = str + ",uri=null)"; | |||
} | |||
return str + "]"; | |||
} | |||
} | |||
/* ==================================================================== | |||
Licensed to the Apache Software Foundation (ASF) under one or more | |||
contributor license agreements. See the NOTICE file distributed with | |||
this work for additional information regarding copyright ownership. | |||
The ASF licenses this file to You under the Apache License, Version 2.0 | |||
(the "License"); you may not use this file except in compliance with | |||
the License. You may obtain a copy of the License at | |||
http://www.apache.org/licenses/LICENSE-2.0 | |||
Unless required by applicable law or agreed to in writing, software | |||
distributed under the License is distributed on an "AS IS" BASIS, | |||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||
See the License for the specific language governing permissions and | |||
limitations under the License. | |||
==================================================================== */ | |||
package org.apache.poi.openxml4j.opc; | |||
import java.net.URI; | |||
import java.net.URISyntaxException; | |||
import java.util.ArrayList; | |||
import java.util.Iterator; | |||
import java.util.TreeMap; | |||
import org.dom4j.Attribute; | |||
import org.dom4j.Document; | |||
import org.dom4j.Element; | |||
import org.dom4j.io.SAXReader; | |||
import org.apache.poi.openxml4j.exceptions.InvalidFormatException; | |||
import org.apache.poi.openxml4j.exceptions.InvalidOperationException; | |||
import org.apache.poi.util.POILogger; | |||
import org.apache.poi.util.POILogFactory; | |||
/** | |||
* Represents a collection of PackageRelationship elements that are owned by a | |||
* given PackagePart or the Package. | |||
* | |||
* @author Julien Chable, CDubettier | |||
* @version 0.1 | |||
*/ | |||
public final class PackageRelationshipCollection implements | |||
Iterable<PackageRelationship> { | |||
private static POILogger logger = POILogFactory.getLogger(PackageRelationshipCollection.class); | |||
/** | |||
* Package relationships ordered by ID. | |||
*/ | |||
private TreeMap<String, PackageRelationship> relationshipsByID; | |||
/** | |||
* Package relationships ordered by type. | |||
*/ | |||
private TreeMap<String, PackageRelationship> relationshipsByType; | |||
/** | |||
* This relationshipPart. | |||
*/ | |||
private PackagePart relationshipPart; | |||
/** | |||
* Source part. | |||
*/ | |||
private PackagePart sourcePart; | |||
/** | |||
* This part name. | |||
*/ | |||
private PackagePartName partName; | |||
/** | |||
* Reference to the package. | |||
*/ | |||
private OPCPackage container; | |||
/** | |||
* Constructor. | |||
*/ | |||
PackageRelationshipCollection() { | |||
relationshipsByID = new TreeMap<String, PackageRelationship>(); | |||
relationshipsByType = new TreeMap<String, PackageRelationship>(); | |||
} | |||
/** | |||
* Copy constructor. | |||
* | |||
* This collection will contain only elements from the specified collection | |||
* for which the type is compatible with the specified relationship type | |||
* filter. | |||
* | |||
* @param coll | |||
* Collection to import. | |||
* @param filter | |||
* Relationship type filter. | |||
*/ | |||
public PackageRelationshipCollection(PackageRelationshipCollection coll, | |||
String filter) { | |||
this(); | |||
for (PackageRelationship rel : coll.relationshipsByID.values()) { | |||
if (filter == null || rel.getRelationshipType().equals(filter)) | |||
addRelationship(rel); | |||
} | |||
} | |||
/** | |||
* Constructor. | |||
*/ | |||
public PackageRelationshipCollection(OPCPackage container) | |||
throws InvalidFormatException { | |||
this(container, null); | |||
} | |||
/** | |||
* Constructor. | |||
* | |||
* @throws InvalidFormatException | |||
* Throws if the format of the content part is invalid. | |||
* | |||
* @throws InvalidOperationException | |||
* Throws if the specified part is a relationship part. | |||
*/ | |||
public PackageRelationshipCollection(PackagePart part) | |||
throws InvalidFormatException { | |||
this(part.container, part); | |||
} | |||
/** | |||
* Constructor. Parse the existing package relationship part if one exists. | |||
* | |||
* @param container | |||
* The parent package. | |||
* @param part | |||
* The part that own this relationships collection. If <b>null</b> | |||
* then this part is considered as the package root. | |||
* @throws InvalidFormatException | |||
* If an error occurs during the parsing of the relatinships | |||
* part fo the specified part. | |||
*/ | |||
public PackageRelationshipCollection(OPCPackage container, PackagePart part) | |||
throws InvalidFormatException { | |||
this(); | |||
if (container == null) | |||
throw new IllegalArgumentException("container"); | |||
// Check if the specified part is not a relationship part | |||
if (part != null && part.isRelationshipPart()) | |||
throw new IllegalArgumentException("part"); | |||
this.container = container; | |||
this.sourcePart = part; | |||
this.partName = getRelationshipPartName(part); | |||
if ((container.getPackageAccess() != PackageAccess.WRITE) | |||
&& container.containPart(this.partName)) { | |||
relationshipPart = container.getPart(this.partName); | |||
parseRelationshipsPart(relationshipPart); | |||
} | |||
} | |||
/** | |||
* Get the relationship part name of the specified part. | |||
* | |||
* @param part | |||
* The part . | |||
* @return The relationship part name of the specified part. Be careful, | |||
* only the correct name is returned, this method does not check if | |||
* the part really exist in a package ! | |||
* @throws InvalidOperationException | |||
* Throws if the specified part is a relationship part. | |||
*/ | |||
private static PackagePartName getRelationshipPartName(PackagePart part) | |||
throws InvalidOperationException { | |||
PackagePartName partName; | |||
if (part == null) { | |||
partName = PackagingURIHelper.PACKAGE_ROOT_PART_NAME; | |||
} else { | |||
partName = part.getPartName(); | |||
} | |||
return PackagingURIHelper.getRelationshipPartName(partName); | |||
} | |||
/** | |||
* Add the specified relationship to the collection. | |||
* | |||
* @param relPart | |||
* The relationship to add. | |||
*/ | |||
public void addRelationship(PackageRelationship relPart) { | |||
relationshipsByID.put(relPart.getId(), relPart); | |||
relationshipsByType.put(relPart.getRelationshipType(), relPart); | |||
} | |||
/** | |||
* Add a relationship to the collection. | |||
* | |||
* @param targetUri | |||
* Target URI. | |||
* @param targetMode | |||
* The target mode : INTERNAL or EXTERNAL | |||
* @param relationshipType | |||
* Relationship type. | |||
* @param id | |||
* Relationship ID. | |||
* @return The newly created relationship. | |||
* @see PackageAccess | |||
*/ | |||
public PackageRelationship addRelationship(URI targetUri, | |||
TargetMode targetMode, String relationshipType, String id) { | |||
if (id == null) { | |||
// Generate a unique ID is id parameter is null. | |||
int i = 0; | |||
do { | |||
id = "rId" + ++i; | |||
} while (relationshipsByID.get(id) != null); | |||
} | |||
PackageRelationship rel = new PackageRelationship(container, | |||
sourcePart, targetUri, targetMode, relationshipType, id); | |||
relationshipsByID.put(rel.getId(), rel); | |||
relationshipsByType.put(rel.getRelationshipType(), rel); | |||
return rel; | |||
} | |||
/** | |||
* Remove a relationship by its ID. | |||
* | |||
* @param id | |||
* The relationship ID to remove. | |||
*/ | |||
public void removeRelationship(String id) { | |||
if (relationshipsByID != null && relationshipsByType != null) { | |||
PackageRelationship rel = relationshipsByID.get(id); | |||
if (rel != null) { | |||
relationshipsByID.remove(rel.getId()); | |||
relationshipsByType.values().remove(rel); | |||
} | |||
} | |||
} | |||
/** | |||
* Remove a relationship by its reference. | |||
* | |||
* @param rel | |||
* The relationship to delete. | |||
*/ | |||
public void removeRelationship(PackageRelationship rel) { | |||
if (rel == null) | |||
throw new IllegalArgumentException("rel"); | |||
relationshipsByID.values().remove(rel); | |||
relationshipsByType.values().remove(rel); | |||
} | |||
/** | |||
* Retrieves a relationship by its index in the collection. | |||
* | |||
* @param index | |||
* Must be a value between [0-relationships_count-1] | |||
*/ | |||
public PackageRelationship getRelationship(int index) { | |||
if (index < 0 || index > relationshipsByID.values().size()) | |||
throw new IllegalArgumentException("index"); | |||
PackageRelationship retRel = null; | |||
int i = 0; | |||
for (PackageRelationship rel : relationshipsByID.values()) { | |||
if (index == i++) | |||
return rel; | |||
} | |||
return retRel; | |||
} | |||
/** | |||
* Retrieves a package relationship based on its id. | |||
* | |||
* @param id | |||
* ID of the package relationship to retrieve. | |||
* @return The package relationship identified by the specified id. | |||
*/ | |||
public PackageRelationship getRelationshipByID(String id) { | |||
return relationshipsByID.get(id); | |||
} | |||
/** | |||
* Get the numbe rof relationships in the collection. | |||
*/ | |||
public int size() { | |||
return relationshipsByID.values().size(); | |||
} | |||
/** | |||
* Parse the relationship part and add all relationship in this collection. | |||
* | |||
* @param relPart | |||
* The package part to parse. | |||
* @throws InvalidFormatException | |||
* Throws if the relationship part is invalid. | |||
*/ | |||
private void parseRelationshipsPart(PackagePart relPart) | |||
throws InvalidFormatException { | |||
try { | |||
SAXReader reader = new SAXReader(); | |||
logger.log(POILogger.DEBUG, "Parsing relationship: " + relPart.getPartName()); | |||
Document xmlRelationshipsDoc = reader | |||
.read(relPart.getInputStream()); | |||
// Browse default types | |||
Element root = xmlRelationshipsDoc.getRootElement(); | |||
// Check OPC compliance M4.1 rule | |||
boolean fCorePropertiesRelationship = false; | |||
for (Iterator i = root | |||
.elementIterator(PackageRelationship.RELATIONSHIP_TAG_NAME); i | |||
.hasNext();) { | |||
Element element = (Element) i.next(); | |||
// Relationship ID | |||
String id = element.attribute( | |||
PackageRelationship.ID_ATTRIBUTE_NAME).getValue(); | |||
// Relationship type | |||
String type = element.attribute( | |||
PackageRelationship.TYPE_ATTRIBUTE_NAME).getValue(); | |||
/* Check OPC Compliance */ | |||
// Check Rule M4.1 | |||
if (type.equals(PackageRelationshipTypes.CORE_PROPERTIES)) | |||
if (!fCorePropertiesRelationship) | |||
fCorePropertiesRelationship = true; | |||
else | |||
throw new InvalidFormatException( | |||
"OPC Compliance error [M4.1]: there is more than one core properties relationship in the package !"); | |||
/* End OPC Compliance */ | |||
// TargetMode (default value "Internal") | |||
Attribute targetModeAttr = element | |||
.attribute(PackageRelationship.TARGET_MODE_ATTRIBUTE_NAME); | |||
TargetMode targetMode = TargetMode.INTERNAL; | |||
if (targetModeAttr != null) { | |||
targetMode = targetModeAttr.getValue().toLowerCase() | |||
.equals("internal") ? TargetMode.INTERNAL | |||
: TargetMode.EXTERNAL; | |||
} | |||
// Target converted in URI | |||
URI target; | |||
String value = ""; | |||
try { | |||
value = element.attribute( | |||
PackageRelationship.TARGET_ATTRIBUTE_NAME) | |||
.getValue(); | |||
if (value.indexOf("\\") != -1) { | |||
logger | |||
.log(POILogger.INFO, "target contains \\ therefore not a valid URI" | |||
+ value + " replaced by /"); | |||
value = value.replaceAll("\\\\", "/"); | |||
// word can save external relationship with a \ instead | |||
// of / | |||
} | |||
target = new URI(value); | |||
} catch (URISyntaxException e) { | |||
logger.log(POILogger.ERROR, "Cannot convert " + value | |||
+ " in a valid relationship URI-> ignored", e); | |||
continue; | |||
} | |||
addRelationship(target, targetMode, type, id); | |||
} | |||
} catch (Exception e) { | |||
logger.log(POILogger.ERROR, e); | |||
throw new InvalidFormatException(e.getMessage()); | |||
} | |||
} | |||
/** | |||
* Retrieves all relations with the specified type. | |||
* | |||
* @param typeFilter | |||
* Relationship type filter. If <b>null</b> then all | |||
* relationships are returned. | |||
* @return All relationships of the type specified by the filter. | |||
*/ | |||
public PackageRelationshipCollection getRelationships(String typeFilter) { | |||
PackageRelationshipCollection coll = new PackageRelationshipCollection( | |||
this, typeFilter); | |||
return coll; | |||
} | |||
/** | |||
* Get this collection's iterator. | |||
*/ | |||
public Iterator<PackageRelationship> iterator() { | |||
return relationshipsByID.values().iterator(); | |||
} | |||
/** | |||
* Get an iterator of a collection with all relationship with the specified | |||
* type. | |||
* | |||
* @param typeFilter | |||
* Type filter. | |||
* @return An iterator to a collection containing all relationships with the | |||
* specified type contain in this collection. | |||
*/ | |||
public Iterator<PackageRelationship> iterator(String typeFilter) { | |||
ArrayList<PackageRelationship> retArr = new ArrayList<PackageRelationship>(); | |||
for (PackageRelationship rel : relationshipsByID.values()) { | |||
if (rel.getRelationshipType().equals(typeFilter)) | |||
retArr.add(rel); | |||
} | |||
return retArr.iterator(); | |||
} | |||
/** | |||
* Clear all relationships. | |||
*/ | |||
public void clear() { | |||
relationshipsByID.clear(); | |||
relationshipsByType.clear(); | |||
} | |||
@Override | |||
public String toString() { | |||
String str; | |||
if (relationshipsByID == null) { | |||
str = "relationshipsByID=null"; | |||
} else { | |||
str = relationshipsByID.size() + " relationship(s) = ["; | |||
} | |||
if ((relationshipPart != null) && (relationshipPart.partName != null)) { | |||
str = str + "," + relationshipPart.partName; | |||
} else { | |||
str = str + ",relationshipPart=null"; | |||
} | |||
// Source of this relationship | |||
if ((sourcePart != null) && (sourcePart.partName != null)) { | |||
str = str + "," + sourcePart.partName; | |||
} else { | |||
str = str + ",sourcePart=null"; | |||
} | |||
if (partName != null) { | |||
str = str + "," + partName; | |||
} else { | |||
str = str + ",uri=null)"; | |||
} | |||
return str + "]"; | |||
} | |||
} |
@@ -1,135 +1,135 @@ | |||
/* ==================================================================== | |||
Licensed to the Apache Software Foundation (ASF) under one or more | |||
contributor license agreements. See the NOTICE file distributed with | |||
this work for additional information regarding copyright ownership. | |||
The ASF licenses this file to You under the Apache License, Version 2.0 | |||
(the "License"); you may not use this file except in compliance with | |||
the License. You may obtain a copy of the License at | |||
http://www.apache.org/licenses/LICENSE-2.0 | |||
Unless required by applicable law or agreed to in writing, software | |||
distributed under the License is distributed on an "AS IS" BASIS, | |||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||
See the License for the specific language governing permissions and | |||
limitations under the License. | |||
==================================================================== */ | |||
package org.apache.poi.openxml4j.opc; | |||
import java.io.IOException; | |||
import java.io.InputStream; | |||
import java.io.OutputStream; | |||
import java.util.zip.ZipEntry; | |||
import org.apache.poi.openxml4j.exceptions.InvalidFormatException; | |||
import org.apache.poi.openxml4j.exceptions.InvalidOperationException; | |||
import org.apache.poi.openxml4j.exceptions.OpenXML4JException; | |||
import org.apache.poi.openxml4j.opc.internal.marshallers.ZipPartMarshaller; | |||
/** | |||
* Zip implementation of a PackagePart. | |||
* | |||
* @author Julien Chable | |||
* @version 1.0 | |||
* @see PackagePart | |||
*/ | |||
public class ZipPackagePart extends PackagePart { | |||
/** | |||
* The zip entry corresponding to this part. | |||
*/ | |||
private ZipEntry zipEntry; | |||
/** | |||
* Constructor. | |||
* | |||
* @param container | |||
* The container package. | |||
* @param partName | |||
* Part name. | |||
* @param contentType | |||
* Content type. | |||
* @throws InvalidFormatException | |||
* Throws if the content of this part invalid. | |||
*/ | |||
public ZipPackagePart(Package container, PackagePartName partName, | |||
String contentType) throws InvalidFormatException { | |||
super(container, partName, contentType); | |||
} | |||
/** | |||
* Constructor. | |||
* | |||
* @param container | |||
* The container package. | |||
* @param zipEntry | |||
* The zip entry corresponding to this part. | |||
* @param partName | |||
* The part name. | |||
* @param contentType | |||
* Content type. | |||
* @throws InvalidFormatException | |||
* Throws if the content of this part is invalid. | |||
*/ | |||
public ZipPackagePart(Package container, ZipEntry zipEntry, | |||
PackagePartName partName, String contentType) | |||
throws InvalidFormatException { | |||
super(container, partName, contentType); | |||
this.zipEntry = zipEntry; | |||
} | |||
/** | |||
* Get the zip entry of this part. | |||
* | |||
* @return The zip entry in the zip structure coresponding to this part. | |||
*/ | |||
public ZipEntry getZipArchive() { | |||
return zipEntry; | |||
} | |||
/** | |||
* Implementation of the getInputStream() which return the inputStream of | |||
* this part zip entry. | |||
* | |||
* @return Input stream of this part zip entry. | |||
*/ | |||
@Override | |||
protected InputStream getInputStreamImpl() throws IOException { | |||
// We use the getInputStream() method from java.util.zip.ZipFile | |||
// class which return an InputStream to this part zip entry. | |||
return ((ZipPackage) container).getZipArchive() | |||
.getInputStream(zipEntry); | |||
} | |||
/** | |||
* Implementation of the getOutputStream(). Return <b>null</b>. Normally | |||
* will never be called since the MemoryPackage is use instead. | |||
* | |||
* @return <b>null</b> | |||
*/ | |||
@Override | |||
protected OutputStream getOutputStreamImpl() { | |||
return null; | |||
} | |||
@Override | |||
public boolean save(OutputStream os) throws OpenXML4JException { | |||
return new ZipPartMarshaller().marshall(this, os); | |||
} | |||
@Override | |||
public boolean load(InputStream ios) throws InvalidFormatException { | |||
throw new InvalidOperationException("Method not implemented !"); | |||
} | |||
@Override | |||
public void close() { | |||
throw new InvalidOperationException("Method not implemented !"); | |||
} | |||
@Override | |||
public void flush() { | |||
throw new InvalidOperationException("Method not implemented !"); | |||
} | |||
} | |||
/* ==================================================================== | |||
Licensed to the Apache Software Foundation (ASF) under one or more | |||
contributor license agreements. See the NOTICE file distributed with | |||
this work for additional information regarding copyright ownership. | |||
The ASF licenses this file to You under the Apache License, Version 2.0 | |||
(the "License"); you may not use this file except in compliance with | |||
the License. You may obtain a copy of the License at | |||
http://www.apache.org/licenses/LICENSE-2.0 | |||
Unless required by applicable law or agreed to in writing, software | |||
distributed under the License is distributed on an "AS IS" BASIS, | |||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||
See the License for the specific language governing permissions and | |||
limitations under the License. | |||
==================================================================== */ | |||
package org.apache.poi.openxml4j.opc; | |||
import java.io.IOException; | |||
import java.io.InputStream; | |||
import java.io.OutputStream; | |||
import java.util.zip.ZipEntry; | |||
import org.apache.poi.openxml4j.exceptions.InvalidFormatException; | |||
import org.apache.poi.openxml4j.exceptions.InvalidOperationException; | |||
import org.apache.poi.openxml4j.exceptions.OpenXML4JException; | |||
import org.apache.poi.openxml4j.opc.internal.marshallers.ZipPartMarshaller; | |||
/** | |||
* Zip implementation of a PackagePart. | |||
* | |||
* @author Julien Chable | |||
* @version 1.0 | |||
* @see PackagePart | |||
*/ | |||
public class ZipPackagePart extends PackagePart { | |||
/** | |||
* The zip entry corresponding to this part. | |||
*/ | |||
private ZipEntry zipEntry; | |||
/** | |||
* Constructor. | |||
* | |||
* @param container | |||
* The container package. | |||
* @param partName | |||
* Part name. | |||
* @param contentType | |||
* Content type. | |||
* @throws InvalidFormatException | |||
* Throws if the content of this part invalid. | |||
*/ | |||
public ZipPackagePart(OPCPackage container, PackagePartName partName, | |||
String contentType) throws InvalidFormatException { | |||
super(container, partName, contentType); | |||
} | |||
/** | |||
* Constructor. | |||
* | |||
* @param container | |||
* The container package. | |||
* @param zipEntry | |||
* The zip entry corresponding to this part. | |||
* @param partName | |||
* The part name. | |||
* @param contentType | |||
* Content type. | |||
* @throws InvalidFormatException | |||
* Throws if the content of this part is invalid. | |||
*/ | |||
public ZipPackagePart(OPCPackage container, ZipEntry zipEntry, | |||
PackagePartName partName, String contentType) | |||
throws InvalidFormatException { | |||
super(container, partName, contentType); | |||
this.zipEntry = zipEntry; | |||
} | |||
/** | |||
* Get the zip entry of this part. | |||
* | |||
* @return The zip entry in the zip structure coresponding to this part. | |||
*/ | |||
public ZipEntry getZipArchive() { | |||
return zipEntry; | |||
} | |||
/** | |||
* Implementation of the getInputStream() which return the inputStream of | |||
* this part zip entry. | |||
* | |||
* @return Input stream of this part zip entry. | |||
*/ | |||
@Override | |||
protected InputStream getInputStreamImpl() throws IOException { | |||
// We use the getInputStream() method from java.util.zip.ZipFile | |||
// class which return an InputStream to this part zip entry. | |||
return ((ZipPackage) container).getZipArchive() | |||
.getInputStream(zipEntry); | |||
} | |||
/** | |||
* Implementation of the getOutputStream(). Return <b>null</b>. Normally | |||
* will never be called since the MemoryPackage is use instead. | |||
* | |||
* @return <b>null</b> | |||
*/ | |||
@Override | |||
protected OutputStream getOutputStreamImpl() { | |||
return null; | |||
} | |||
@Override | |||
public boolean save(OutputStream os) throws OpenXML4JException { | |||
return new ZipPartMarshaller().marshall(this, os); | |||
} | |||
@Override | |||
public boolean load(InputStream ios) throws InvalidFormatException { | |||
throw new InvalidOperationException("Method not implemented !"); | |||
} | |||
@Override | |||
public void close() { | |||
throw new InvalidOperationException("Method not implemented !"); | |||
} | |||
@Override | |||
public void flush() { | |||
throw new InvalidOperationException("Method not implemented !"); | |||
} | |||
} |
@@ -1,496 +1,491 @@ | |||
/* ==================================================================== | |||
Licensed to the Apache Software Foundation (ASF) under one or more | |||
contributor license agreements. See the NOTICE file distributed with | |||
this work for additional information regarding copyright ownership. | |||
The ASF licenses this file to You under the Apache License, Version 2.0 | |||
(the "License"); you may not use this file except in compliance with | |||
the License. You may obtain a copy of the License at | |||
http://www.apache.org/licenses/LICENSE-2.0 | |||
Unless required by applicable law or agreed to in writing, software | |||
distributed under the License is distributed on an "AS IS" BASIS, | |||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||
See the License for the specific language governing permissions and | |||
limitations under the License. | |||
==================================================================== */ | |||
package org.apache.poi.openxml4j.opc.internal; | |||
import java.io.InputStream; | |||
import java.io.OutputStream; | |||
import java.net.URI; | |||
import java.net.URISyntaxException; | |||
import java.util.Iterator; | |||
import java.util.List; | |||
import java.util.TreeMap; | |||
import java.util.Map.Entry; | |||
import java.util.zip.ZipOutputStream; | |||
import org.dom4j.Document; | |||
import org.dom4j.DocumentException; | |||
import org.dom4j.DocumentHelper; | |||
import org.dom4j.Element; | |||
import org.dom4j.Namespace; | |||
import org.dom4j.QName; | |||
import org.dom4j.io.SAXReader; | |||
import org.apache.poi.openxml4j.exceptions.InvalidFormatException; | |||
import org.apache.poi.openxml4j.exceptions.InvalidOperationException; | |||
import org.apache.poi.openxml4j.exceptions.OpenXML4JRuntimeException; | |||
import org.apache.poi.openxml4j.opc.Package; | |||
import org.apache.poi.openxml4j.opc.PackagePart; | |||
import org.apache.poi.openxml4j.opc.PackagePartName; | |||
import org.apache.poi.openxml4j.opc.PackagingURIHelper; | |||
import org.apache.poi.util.POILogger; | |||
import org.apache.poi.util.POILogFactory; | |||
/** | |||
* Manage package content types ([Content_Types].xml part). | |||
* | |||
* @author Julien Chable | |||
* @version 1.0 | |||
*/ | |||
public abstract class ContentTypeManager { | |||
private static POILogger logger = POILogFactory.getLogger(ContentTypeManager.class); | |||
/** | |||
* Reference to the package using this content type manager. | |||
*/ | |||
protected Package container; | |||
/** | |||
* Content type part name. | |||
*/ | |||
public static final String CONTENT_TYPES_PART_NAME = "[Content_Types].xml"; | |||
/** | |||
* Content type namespace | |||
*/ | |||
public static final String TYPES_NAMESPACE_URI = "http://schemas.openxmlformats.org/package/2006/content-types"; | |||
/* Xml elements in content type part */ | |||
private static final String TYPES_TAG_NAME = "Types"; | |||
private static final String DEFAULT_TAG_NAME = "Default"; | |||
private static final String EXTENSION_ATTRIBUTE_NAME = "Extension"; | |||
private static final String CONTENT_TYPE_ATTRIBUTE_NAME = "ContentType"; | |||
private static final String OVERRIDE_TAG_NAME = "Override"; | |||
private static final String PART_NAME_ATTRIBUTE_NAME = "PartName"; | |||
/** | |||
* Default content type tree. <Extension, ContentType> | |||
*/ | |||
private TreeMap<String, String> defaultContentType; | |||
/** | |||
* Override content type tree. | |||
*/ | |||
private TreeMap<PackagePartName, String> overrideContentType; | |||
/** | |||
* Constructor. Parses the content of the specified input stream. | |||
* | |||
* @param in | |||
* If different of <i>null</i> then the content types part is | |||
* retrieve and parse. | |||
* @throws InvalidFormatException | |||
* If the content types part content is not valid. | |||
*/ | |||
public ContentTypeManager(InputStream in, Package pkg) | |||
throws InvalidFormatException { | |||
this.container = pkg; | |||
this.defaultContentType = new TreeMap<String, String>(); | |||
if (in != null) { | |||
try { | |||
parseContentTypesFile(in); | |||
} catch (InvalidFormatException e) { | |||
throw new InvalidFormatException( | |||
"Can't read content types part !"); | |||
} | |||
} | |||
} | |||
/** | |||
* Build association extention-> content type (will be stored in | |||
* [Content_Types].xml) for example ContentType="image/png" Extension="png" | |||
* <p> | |||
* [M2.8]: When adding a new part to a package, the package implementer | |||
* shall ensure that a content type for that part is specified in the | |||
* Content Types stream; the package implementer shall perform the steps | |||
* described in §9.1.2.3: | |||
* </p><p> | |||
* 1. Get the extension from the part name by taking the substring to the | |||
* right of the rightmost occurrence of the dot character (.) from the | |||
* rightmost segment. | |||
* </p><p> | |||
* 2. If a part name has no extension, a corresponding Override element | |||
* shall be added to the Content Types stream. | |||
* </p><p> | |||
* 3. Compare the resulting extension with the values specified for the | |||
* Extension attributes of the Default elements in the Content Types stream. | |||
* The comparison shall be case-insensitive ASCII. | |||
* </p><p> | |||
* 4. If there is a Default element with a matching Extension attribute, | |||
* then the content type of the new part shall be compared with the value of | |||
* the ContentType attribute. The comparison might be case-sensitive and | |||
* include every character regardless of the role it plays in the | |||
* content-type grammar of RFC 2616, or it might follow the grammar of RFC | |||
* 2616. | |||
* </p><p> | |||
* a. If the content types match, no further action is required. | |||
* </p><p> | |||
* b. If the content types do not match, a new Override element shall be | |||
* added to the Content Types stream. . | |||
* </p><p> | |||
* 5. If there is no Default element with a matching Extension attribute, a | |||
* new Default element or Override element shall be added to the Content | |||
* Types stream. | |||
* </p> | |||
*/ | |||
public void addContentType(PackagePartName partName, String contentType) { | |||
boolean defaultCTExists = false; | |||
String extension = partName.getExtension().toLowerCase(); | |||
if ((extension.length() == 0) | |||
|| (this.defaultContentType.containsKey(extension) && !(defaultCTExists = this.defaultContentType | |||
.containsValue(contentType)))) | |||
this.addOverrideContentType(partName, contentType); | |||
else if (!defaultCTExists) | |||
this.addDefaultContentType(extension, contentType); | |||
} | |||
/** | |||
* Add an override content type for a specific part. | |||
* | |||
* @param partName | |||
* Name of the part. | |||
* @param contentType | |||
* Content type of the part. | |||
*/ | |||
private void addOverrideContentType(PackagePartName partName, | |||
String contentType) { | |||
if (overrideContentType == null) | |||
overrideContentType = new TreeMap<PackagePartName, String>(); | |||
overrideContentType.put(partName, contentType); | |||
} | |||
/** | |||
* Add a content type associated with the specified extension. | |||
* | |||
* @param extension | |||
* The part name extension to bind to a content type. | |||
* @param contentType | |||
* The content type associated with the specified extension. | |||
*/ | |||
private void addDefaultContentType(String extension, String contentType) { | |||
// Remark : Originally the latest parameter was : | |||
// contentType.toLowerCase(). Change due to a request ID 1996748. | |||
defaultContentType.put(extension.toLowerCase(), contentType); | |||
} | |||
/** | |||
* <p> | |||
* Delete a content type based on the specified part name. If the specified | |||
* part name is register with an override content type, then this content | |||
* type is remove, else the content type is remove in the default content | |||
* type list if it exists and if no part is associated with it yet. | |||
* </p><p> | |||
* Check rule M2.4: The package implementer shall require that the Content | |||
* Types stream contain one of the following for every part in the package: | |||
* One matching Default element One matching Override element Both a | |||
* matching Default element and a matching Override element, in which case | |||
* the Override element takes precedence. | |||
* </p> | |||
* @param partName | |||
* The part URI associated with the override content type to | |||
* delete. | |||
* @exception InvalidOperationException | |||
* Throws if | |||
*/ | |||
public void removeContentType(PackagePartName partName) | |||
throws InvalidOperationException { | |||
if (partName == null) | |||
throw new IllegalArgumentException("partName"); | |||
/* Override content type */ | |||
if (this.overrideContentType != null | |||
&& (this.overrideContentType.get(partName) != null)) { | |||
// Remove the override definition for the specified part. | |||
this.overrideContentType.remove(partName); | |||
return; | |||
} | |||
/* Default content type */ | |||
String extensionToDelete = partName.getExtension(); | |||
boolean deleteDefaultContentTypeFlag = true; | |||
if (this.container != null) { | |||
try { | |||
for (PackagePart part : this.container.getParts()) { | |||
if (!part.getPartName().equals(partName) | |||
&& part.getPartName().getExtension() | |||
.equalsIgnoreCase(extensionToDelete)) { | |||
deleteDefaultContentTypeFlag = false; | |||
break; | |||
} | |||
} | |||
} catch (InvalidFormatException e) { | |||
throw new InvalidOperationException(e.getMessage()); | |||
} | |||
} | |||
// Remove the default content type, no other part use this content type. | |||
if (deleteDefaultContentTypeFlag) { | |||
this.defaultContentType.remove(extensionToDelete); | |||
} | |||
/* | |||
* Check rule 2.4: The package implementer shall require that the | |||
* Content Types stream contain one of the following for every part in | |||
* the package: One matching Default element One matching Override | |||
* element Both a matching Default element and a matching Override | |||
* element, in which case the Override element takes precedence. | |||
*/ | |||
if (this.container != null) { | |||
try { | |||
for (PackagePart part : this.container.getParts()) { | |||
if (!part.getPartName().equals(partName) | |||
&& this.getContentType(part.getPartName()) == null) | |||
throw new InvalidOperationException( | |||
"Rule M2.4 is not respected: Nor a default element or override element is associated with the part: " | |||
+ part.getPartName().getName()); | |||
} | |||
} catch (InvalidFormatException e) { | |||
throw new InvalidOperationException(e.getMessage()); | |||
} | |||
} | |||
} | |||
/** | |||
* Check if the specified content type is already register. | |||
* | |||
* @param contentType | |||
* The content type to check. | |||
* @return <code>true</code> if the specified content type is already | |||
* register, then <code>false</code>. | |||
*/ | |||
public boolean isContentTypeRegister(String contentType) { | |||
if (contentType == null) | |||
throw new IllegalArgumentException("contentType"); | |||
return (this.defaultContentType.values().contains(contentType) || (this.overrideContentType != null && this.overrideContentType | |||
.values().contains(contentType))); | |||
} | |||
/** | |||
* Get the content type for the specified part, if any. | |||
* <p> | |||
* Rule [M2.9]: To get the content type of a part, the package implementer | |||
* shall perform the steps described in §9.1.2.4: | |||
* </p><p> | |||
* 1. Compare the part name with the values specified for the PartName | |||
* attribute of the Override elements. The comparison shall be | |||
* case-insensitive ASCII. | |||
* </p><p> | |||
* 2. If there is an Override element with a matching PartName attribute, | |||
* return the value of its ContentType attribute. No further action is | |||
* required. | |||
* </p><p> | |||
* 3. If there is no Override element with a matching PartName attribute, | |||
* then a. Get the extension from the part name by taking the substring to | |||
* the right of the rightmost occurrence of the dot character (.) from the | |||
* rightmost segment. b. Check the Default elements of the Content Types | |||
* stream, comparing the extension with the value of the Extension | |||
* attribute. The comparison shall be case-insensitive ASCII. | |||
* </p><p> | |||
* 4. If there is a Default element with a matching Extension attribute, | |||
* return the value of its ContentType attribute. No further action is | |||
* required. | |||
* </p><p> | |||
* 5. If neither Override nor Default elements with matching attributes are | |||
* found for the specified part name, the implementation shall not map this | |||
* part name to a part. | |||
* </p> | |||
* @param partName | |||
* The URI part to check. | |||
* @return The content type associated with the URI (in case of an override | |||
* content type) or the extension (in case of default content type), | |||
* else <code>null</code>. | |||
* | |||
* @exception OpenXML4JRuntimeException | |||
* Throws if the content type manager is not able to find the | |||
* content from an existing part. | |||
*/ | |||
public String getContentType(PackagePartName partName) { | |||
if (partName == null) | |||
throw new IllegalArgumentException("partName"); | |||
if ((this.overrideContentType != null) | |||
&& this.overrideContentType.containsKey(partName)) | |||
return this.overrideContentType.get(partName); | |||
String extension = partName.getExtension().toLowerCase(); | |||
if (this.defaultContentType.containsKey(extension)) | |||
return this.defaultContentType.get(extension); | |||
/* | |||
* [M2.4] : The package implementer shall require that the Content Types | |||
* stream contain one of the following for every part in the package: | |||
* One matching Default element, One matching Override element, Both a | |||
* matching Default element and a matching Override element, in which | |||
* case the Override element takes precedence. | |||
*/ | |||
if (this.container != null && this.container.getPart(partName) != null) { | |||
throw new OpenXML4JRuntimeException( | |||
"Rule M2.4 exception : this error should NEVER happen, if so please send a mail to the developers team, thanks !"); | |||
} else { | |||
return null; | |||
} | |||
} | |||
/** | |||
* Clear all content types. | |||
*/ | |||
public void clearAll() { | |||
this.defaultContentType.clear(); | |||
if (this.overrideContentType != null) | |||
this.overrideContentType.clear(); | |||
} | |||
/** | |||
* Clear all override content types. | |||
* | |||
*/ | |||
public void clearOverrideContentTypes() { | |||
if (this.overrideContentType != null) | |||
this.overrideContentType.clear(); | |||
} | |||
/** | |||
* Parse the content types part. | |||
* | |||
* @throws InvalidFormatException | |||
* Throws if the content type doesn't exist or the XML format is | |||
* invalid. | |||
*/ | |||
private void parseContentTypesFile(InputStream in) | |||
throws InvalidFormatException { | |||
try { | |||
SAXReader xmlReader = new SAXReader(); | |||
Document xmlContentTypetDoc = xmlReader.read(in); | |||
// Default content types | |||
List defaultTypes = xmlContentTypetDoc.getRootElement().elements( | |||
DEFAULT_TAG_NAME); | |||
Iterator elementIteratorDefault = defaultTypes.iterator(); | |||
while (elementIteratorDefault.hasNext()) { | |||
Element element = (Element) elementIteratorDefault.next(); | |||
String extension = element.attribute(EXTENSION_ATTRIBUTE_NAME) | |||
.getValue(); | |||
String contentType = element.attribute( | |||
CONTENT_TYPE_ATTRIBUTE_NAME).getValue(); | |||
addDefaultContentType(extension, contentType); | |||
} | |||
// Overriden content types | |||
List overrideTypes = xmlContentTypetDoc.getRootElement().elements( | |||
OVERRIDE_TAG_NAME); | |||
Iterator elementIteratorOverride = overrideTypes.iterator(); | |||
while (elementIteratorOverride.hasNext()) { | |||
Element element = (Element) elementIteratorOverride.next(); | |||
URI uri = new URI(element.attribute(PART_NAME_ATTRIBUTE_NAME) | |||
.getValue()); | |||
PackagePartName partName = PackagingURIHelper | |||
.createPartName(uri); | |||
String contentType = element.attribute( | |||
CONTENT_TYPE_ATTRIBUTE_NAME).getValue(); | |||
addOverrideContentType(partName, contentType); | |||
} | |||
} catch (URISyntaxException urie) { | |||
throw new InvalidFormatException(urie.getMessage()); | |||
} catch (DocumentException e) { | |||
throw new InvalidFormatException(e.getMessage()); | |||
} | |||
} | |||
/** | |||
* Save the contents type part. | |||
* | |||
* @param outStream | |||
* The output stream use to save the XML content of the content | |||
* types part. | |||
* @return <b>true</b> if the operation success, else <b>false</b>. | |||
*/ | |||
public boolean save(OutputStream outStream) { | |||
Document xmlOutDoc = DocumentHelper.createDocument(); | |||
// Building namespace | |||
Namespace dfNs = Namespace.get("", TYPES_NAMESPACE_URI); | |||
Element typesElem = xmlOutDoc | |||
.addElement(new QName(TYPES_TAG_NAME, dfNs)); | |||
// Adding default types | |||
for (Entry<String, String> entry : defaultContentType.entrySet()) { | |||
appendDefaultType(typesElem, entry); | |||
} | |||
// Adding specific types if any exist | |||
if (overrideContentType != null) { | |||
for (Entry<PackagePartName, String> entry : overrideContentType | |||
.entrySet()) { | |||
appendSpecificTypes(typesElem, entry); | |||
} | |||
} | |||
xmlOutDoc.normalize(); | |||
// Save content in the specified output stream | |||
return this.saveImpl(xmlOutDoc, outStream); | |||
} | |||
/** | |||
* Use to append specific type XML elements, use by the save() method. | |||
* | |||
* @param root | |||
* XML parent element use to append this override type element. | |||
* @param entry | |||
* The values to append. | |||
* @see #save(java.io.OutputStream) | |||
*/ | |||
private void appendSpecificTypes(Element root, | |||
Entry<PackagePartName, String> entry) { | |||
root.addElement(OVERRIDE_TAG_NAME).addAttribute( | |||
PART_NAME_ATTRIBUTE_NAME, | |||
((PackagePartName) entry.getKey()).getName()).addAttribute( | |||
CONTENT_TYPE_ATTRIBUTE_NAME, (String) entry.getValue()); | |||
} | |||
/** | |||
* Use to append default types XML elements, use by the save() metid. | |||
* | |||
* @param root | |||
* XML parent element use to append this default type element. | |||
* @param entry | |||
* The values to append. | |||
* @see #save(java.io.OutputStream) | |||
*/ | |||
private void appendDefaultType(Element root, Entry<String, String> entry) { | |||
root.addElement(DEFAULT_TAG_NAME).addAttribute( | |||
EXTENSION_ATTRIBUTE_NAME, (String) entry.getKey()) | |||
.addAttribute(CONTENT_TYPE_ATTRIBUTE_NAME, | |||
(String) entry.getValue()); | |||
} | |||
/** | |||
* Specific implementation of the save method. Call by the save() method, | |||
* call before exiting. | |||
* | |||
* @param out | |||
* The output stream use to write the content type XML. | |||
*/ | |||
public abstract boolean saveImpl(Document content, OutputStream out); | |||
} | |||
/* ==================================================================== | |||
Licensed to the Apache Software Foundation (ASF) under one or more | |||
contributor license agreements. See the NOTICE file distributed with | |||
this work for additional information regarding copyright ownership. | |||
The ASF licenses this file to You under the Apache License, Version 2.0 | |||
(the "License"); you may not use this file except in compliance with | |||
the License. You may obtain a copy of the License at | |||
http://www.apache.org/licenses/LICENSE-2.0 | |||
Unless required by applicable law or agreed to in writing, software | |||
distributed under the License is distributed on an "AS IS" BASIS, | |||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||
See the License for the specific language governing permissions and | |||
limitations under the License. | |||
==================================================================== */ | |||
package org.apache.poi.openxml4j.opc.internal; | |||
import java.io.InputStream; | |||
import java.io.OutputStream; | |||
import java.net.URI; | |||
import java.net.URISyntaxException; | |||
import java.util.Iterator; | |||
import java.util.List; | |||
import java.util.TreeMap; | |||
import java.util.Map.Entry; | |||
import org.apache.poi.openxml4j.exceptions.InvalidFormatException; | |||
import org.apache.poi.openxml4j.exceptions.InvalidOperationException; | |||
import org.apache.poi.openxml4j.exceptions.OpenXML4JRuntimeException; | |||
import org.apache.poi.openxml4j.opc.OPCPackage; | |||
import org.apache.poi.openxml4j.opc.PackagePart; | |||
import org.apache.poi.openxml4j.opc.PackagePartName; | |||
import org.apache.poi.openxml4j.opc.PackagingURIHelper; | |||
import org.dom4j.Document; | |||
import org.dom4j.DocumentException; | |||
import org.dom4j.DocumentHelper; | |||
import org.dom4j.Element; | |||
import org.dom4j.Namespace; | |||
import org.dom4j.QName; | |||
import org.dom4j.io.SAXReader; | |||
/** | |||
* Manage package content types ([Content_Types].xml part). | |||
* | |||
* @author Julien Chable | |||
* @version 1.0 | |||
*/ | |||
public abstract class ContentTypeManager { | |||
/** | |||
* Content type part name. | |||
*/ | |||
public static final String CONTENT_TYPES_PART_NAME = "[Content_Types].xml"; | |||
/** | |||
* Content type namespace | |||
*/ | |||
public static final String TYPES_NAMESPACE_URI = "http://schemas.openxmlformats.org/package/2006/content-types"; | |||
/* Xml elements in content type part */ | |||
private static final String TYPES_TAG_NAME = "Types"; | |||
private static final String DEFAULT_TAG_NAME = "Default"; | |||
private static final String EXTENSION_ATTRIBUTE_NAME = "Extension"; | |||
private static final String CONTENT_TYPE_ATTRIBUTE_NAME = "ContentType"; | |||
private static final String OVERRIDE_TAG_NAME = "Override"; | |||
private static final String PART_NAME_ATTRIBUTE_NAME = "PartName"; | |||
/** | |||
* Reference to the package using this content type manager. | |||
*/ | |||
protected OPCPackage container; | |||
/** | |||
* Default content type tree. <Extension, ContentType> | |||
*/ | |||
private TreeMap<String, String> defaultContentType; | |||
/** | |||
* Override content type tree. | |||
*/ | |||
private TreeMap<PackagePartName, String> overrideContentType; | |||
/** | |||
* Constructor. Parses the content of the specified input stream. | |||
* | |||
* @param in | |||
* If different of <i>null</i> then the content types part is | |||
* retrieve and parse. | |||
* @throws InvalidFormatException | |||
* If the content types part content is not valid. | |||
*/ | |||
public ContentTypeManager(InputStream in, OPCPackage pkg) | |||
throws InvalidFormatException { | |||
this.container = pkg; | |||
this.defaultContentType = new TreeMap<String, String>(); | |||
if (in != null) { | |||
try { | |||
parseContentTypesFile(in); | |||
} catch (InvalidFormatException e) { | |||
throw new InvalidFormatException( | |||
"Can't read content types part !"); | |||
} | |||
} | |||
} | |||
/** | |||
* Build association extention-> content type (will be stored in | |||
* [Content_Types].xml) for example ContentType="image/png" Extension="png" | |||
* <p> | |||
* [M2.8]: When adding a new part to a package, the package implementer | |||
* shall ensure that a content type for that part is specified in the | |||
* Content Types stream; the package implementer shall perform the steps | |||
* described in §9.1.2.3: | |||
* </p><p> | |||
* 1. Get the extension from the part name by taking the substring to the | |||
* right of the rightmost occurrence of the dot character (.) from the | |||
* rightmost segment. | |||
* </p><p> | |||
* 2. If a part name has no extension, a corresponding Override element | |||
* shall be added to the Content Types stream. | |||
* </p><p> | |||
* 3. Compare the resulting extension with the values specified for the | |||
* Extension attributes of the Default elements in the Content Types stream. | |||
* The comparison shall be case-insensitive ASCII. | |||
* </p><p> | |||
* 4. If there is a Default element with a matching Extension attribute, | |||
* then the content type of the new part shall be compared with the value of | |||
* the ContentType attribute. The comparison might be case-sensitive and | |||
* include every character regardless of the role it plays in the | |||
* content-type grammar of RFC 2616, or it might follow the grammar of RFC | |||
* 2616. | |||
* </p><p> | |||
* a. If the content types match, no further action is required. | |||
* </p><p> | |||
* b. If the content types do not match, a new Override element shall be | |||
* added to the Content Types stream. . | |||
* </p><p> | |||
* 5. If there is no Default element with a matching Extension attribute, a | |||
* new Default element or Override element shall be added to the Content | |||
* Types stream. | |||
* </p> | |||
*/ | |||
public void addContentType(PackagePartName partName, String contentType) { | |||
boolean defaultCTExists = false; | |||
String extension = partName.getExtension().toLowerCase(); | |||
if ((extension.length() == 0) | |||
|| (this.defaultContentType.containsKey(extension) && !(defaultCTExists = this.defaultContentType | |||
.containsValue(contentType)))) | |||
this.addOverrideContentType(partName, contentType); | |||
else if (!defaultCTExists) | |||
this.addDefaultContentType(extension, contentType); | |||
} | |||
/** | |||
* Add an override content type for a specific part. | |||
* | |||
* @param partName | |||
* Name of the part. | |||
* @param contentType | |||
* Content type of the part. | |||
*/ | |||
private void addOverrideContentType(PackagePartName partName, | |||
String contentType) { | |||
if (overrideContentType == null) | |||
overrideContentType = new TreeMap<PackagePartName, String>(); | |||
overrideContentType.put(partName, contentType); | |||
} | |||
/** | |||
* Add a content type associated with the specified extension. | |||
* | |||
* @param extension | |||
* The part name extension to bind to a content type. | |||
* @param contentType | |||
* The content type associated with the specified extension. | |||
*/ | |||
private void addDefaultContentType(String extension, String contentType) { | |||
// Remark : Originally the latest parameter was : | |||
// contentType.toLowerCase(). Change due to a request ID 1996748. | |||
defaultContentType.put(extension.toLowerCase(), contentType); | |||
} | |||
/** | |||
* <p> | |||
* Delete a content type based on the specified part name. If the specified | |||
* part name is register with an override content type, then this content | |||
* type is remove, else the content type is remove in the default content | |||
* type list if it exists and if no part is associated with it yet. | |||
* </p><p> | |||
* Check rule M2.4: The package implementer shall require that the Content | |||
* Types stream contain one of the following for every part in the package: | |||
* One matching Default element One matching Override element Both a | |||
* matching Default element and a matching Override element, in which case | |||
* the Override element takes precedence. | |||
* </p> | |||
* @param partName | |||
* The part URI associated with the override content type to | |||
* delete. | |||
* @exception InvalidOperationException | |||
* Throws if | |||
*/ | |||
public void removeContentType(PackagePartName partName) | |||
throws InvalidOperationException { | |||
if (partName == null) | |||
throw new IllegalArgumentException("partName"); | |||
/* Override content type */ | |||
if (this.overrideContentType != null | |||
&& (this.overrideContentType.get(partName) != null)) { | |||
// Remove the override definition for the specified part. | |||
this.overrideContentType.remove(partName); | |||
return; | |||
} | |||
/* Default content type */ | |||
String extensionToDelete = partName.getExtension(); | |||
boolean deleteDefaultContentTypeFlag = true; | |||
if (this.container != null) { | |||
try { | |||
for (PackagePart part : this.container.getParts()) { | |||
if (!part.getPartName().equals(partName) | |||
&& part.getPartName().getExtension() | |||
.equalsIgnoreCase(extensionToDelete)) { | |||
deleteDefaultContentTypeFlag = false; | |||
break; | |||
} | |||
} | |||
} catch (InvalidFormatException e) { | |||
throw new InvalidOperationException(e.getMessage()); | |||
} | |||
} | |||
// Remove the default content type, no other part use this content type. | |||
if (deleteDefaultContentTypeFlag) { | |||
this.defaultContentType.remove(extensionToDelete); | |||
} | |||
/* | |||
* Check rule 2.4: The package implementer shall require that the | |||
* Content Types stream contain one of the following for every part in | |||
* the package: One matching Default element One matching Override | |||
* element Both a matching Default element and a matching Override | |||
* element, in which case the Override element takes precedence. | |||
*/ | |||
if (this.container != null) { | |||
try { | |||
for (PackagePart part : this.container.getParts()) { | |||
if (!part.getPartName().equals(partName) | |||
&& this.getContentType(part.getPartName()) == null) | |||
throw new InvalidOperationException( | |||
"Rule M2.4 is not respected: Nor a default element or override element is associated with the part: " | |||
+ part.getPartName().getName()); | |||
} | |||
} catch (InvalidFormatException e) { | |||
throw new InvalidOperationException(e.getMessage()); | |||
} | |||
} | |||
} | |||
/** | |||
* Check if the specified content type is already register. | |||
* | |||
* @param contentType | |||
* The content type to check. | |||
* @return <code>true</code> if the specified content type is already | |||
* register, then <code>false</code>. | |||
*/ | |||
public boolean isContentTypeRegister(String contentType) { | |||
if (contentType == null) | |||
throw new IllegalArgumentException("contentType"); | |||
return (this.defaultContentType.values().contains(contentType) || (this.overrideContentType != null && this.overrideContentType | |||
.values().contains(contentType))); | |||
} | |||
/** | |||
* Get the content type for the specified part, if any. | |||
* <p> | |||
* Rule [M2.9]: To get the content type of a part, the package implementer | |||
* shall perform the steps described in §9.1.2.4: | |||
* </p><p> | |||
* 1. Compare the part name with the values specified for the PartName | |||
* attribute of the Override elements. The comparison shall be | |||
* case-insensitive ASCII. | |||
* </p><p> | |||
* 2. If there is an Override element with a matching PartName attribute, | |||
* return the value of its ContentType attribute. No further action is | |||
* required. | |||
* </p><p> | |||
* 3. If there is no Override element with a matching PartName attribute, | |||
* then a. Get the extension from the part name by taking the substring to | |||
* the right of the rightmost occurrence of the dot character (.) from the | |||
* rightmost segment. b. Check the Default elements of the Content Types | |||
* stream, comparing the extension with the value of the Extension | |||
* attribute. The comparison shall be case-insensitive ASCII. | |||
* </p><p> | |||
* 4. If there is a Default element with a matching Extension attribute, | |||
* return the value of its ContentType attribute. No further action is | |||
* required. | |||
* </p><p> | |||
* 5. If neither Override nor Default elements with matching attributes are | |||
* found for the specified part name, the implementation shall not map this | |||
* part name to a part. | |||
* </p> | |||
* @param partName | |||
* The URI part to check. | |||
* @return The content type associated with the URI (in case of an override | |||
* content type) or the extension (in case of default content type), | |||
* else <code>null</code>. | |||
* | |||
* @exception OpenXML4JRuntimeException | |||
* Throws if the content type manager is not able to find the | |||
* content from an existing part. | |||
*/ | |||
public String getContentType(PackagePartName partName) { | |||
if (partName == null) | |||
throw new IllegalArgumentException("partName"); | |||
if ((this.overrideContentType != null) | |||
&& this.overrideContentType.containsKey(partName)) | |||
return this.overrideContentType.get(partName); | |||
String extension = partName.getExtension().toLowerCase(); | |||
if (this.defaultContentType.containsKey(extension)) | |||
return this.defaultContentType.get(extension); | |||
/* | |||
* [M2.4] : The package implementer shall require that the Content Types | |||
* stream contain one of the following for every part in the package: | |||
* One matching Default element, One matching Override element, Both a | |||
* matching Default element and a matching Override element, in which | |||
* case the Override element takes precedence. | |||
*/ | |||
if (this.container != null && this.container.getPart(partName) != null) { | |||
throw new OpenXML4JRuntimeException( | |||
"Rule M2.4 exception : this error should NEVER happen, if so please send a mail to the developers team, thanks !"); | |||
} else { | |||
return null; | |||
} | |||
} | |||
/** | |||
* Clear all content types. | |||
*/ | |||
public void clearAll() { | |||
this.defaultContentType.clear(); | |||
if (this.overrideContentType != null) | |||
this.overrideContentType.clear(); | |||
} | |||
/** | |||
* Clear all override content types. | |||
* | |||
*/ | |||
public void clearOverrideContentTypes() { | |||
if (this.overrideContentType != null) | |||
this.overrideContentType.clear(); | |||
} | |||
/** | |||
* Parse the content types part. | |||
* | |||
* @throws InvalidFormatException | |||
* Throws if the content type doesn't exist or the XML format is | |||
* invalid. | |||
*/ | |||
private void parseContentTypesFile(InputStream in) | |||
throws InvalidFormatException { | |||
try { | |||
SAXReader xmlReader = new SAXReader(); | |||
Document xmlContentTypetDoc = xmlReader.read(in); | |||
// Default content types | |||
List defaultTypes = xmlContentTypetDoc.getRootElement().elements( | |||
DEFAULT_TAG_NAME); | |||
Iterator elementIteratorDefault = defaultTypes.iterator(); | |||
while (elementIteratorDefault.hasNext()) { | |||
Element element = (Element) elementIteratorDefault.next(); | |||
String extension = element.attribute(EXTENSION_ATTRIBUTE_NAME) | |||
.getValue(); | |||
String contentType = element.attribute( | |||
CONTENT_TYPE_ATTRIBUTE_NAME).getValue(); | |||
addDefaultContentType(extension, contentType); | |||
} | |||
// Overriden content types | |||
List overrideTypes = xmlContentTypetDoc.getRootElement().elements( | |||
OVERRIDE_TAG_NAME); | |||
Iterator elementIteratorOverride = overrideTypes.iterator(); | |||
while (elementIteratorOverride.hasNext()) { | |||
Element element = (Element) elementIteratorOverride.next(); | |||
URI uri = new URI(element.attribute(PART_NAME_ATTRIBUTE_NAME) | |||
.getValue()); | |||
PackagePartName partName = PackagingURIHelper | |||
.createPartName(uri); | |||
String contentType = element.attribute( | |||
CONTENT_TYPE_ATTRIBUTE_NAME).getValue(); | |||
addOverrideContentType(partName, contentType); | |||
} | |||
} catch (URISyntaxException urie) { | |||
throw new InvalidFormatException(urie.getMessage()); | |||
} catch (DocumentException e) { | |||
throw new InvalidFormatException(e.getMessage()); | |||
} | |||
} | |||
/** | |||
* Save the contents type part. | |||
* | |||
* @param outStream | |||
* The output stream use to save the XML content of the content | |||
* types part. | |||
* @return <b>true</b> if the operation success, else <b>false</b>. | |||
*/ | |||
public boolean save(OutputStream outStream) { | |||
Document xmlOutDoc = DocumentHelper.createDocument(); | |||
// Building namespace | |||
Namespace dfNs = Namespace.get("", TYPES_NAMESPACE_URI); | |||
Element typesElem = xmlOutDoc | |||
.addElement(new QName(TYPES_TAG_NAME, dfNs)); | |||
// Adding default types | |||
for (Entry<String, String> entry : defaultContentType.entrySet()) { | |||
appendDefaultType(typesElem, entry); | |||
} | |||
// Adding specific types if any exist | |||
if (overrideContentType != null) { | |||
for (Entry<PackagePartName, String> entry : overrideContentType | |||
.entrySet()) { | |||
appendSpecificTypes(typesElem, entry); | |||
} | |||
} | |||
xmlOutDoc.normalize(); | |||
// Save content in the specified output stream | |||
return this.saveImpl(xmlOutDoc, outStream); | |||
} | |||
/** | |||
* Use to append specific type XML elements, use by the save() method. | |||
* | |||
* @param root | |||
* XML parent element use to append this override type element. | |||
* @param entry | |||
* The values to append. | |||
* @see #save(java.io.OutputStream) | |||
*/ | |||
private void appendSpecificTypes(Element root, | |||
Entry<PackagePartName, String> entry) { | |||
root.addElement(OVERRIDE_TAG_NAME).addAttribute( | |||
PART_NAME_ATTRIBUTE_NAME, | |||
((PackagePartName) entry.getKey()).getName()).addAttribute( | |||
CONTENT_TYPE_ATTRIBUTE_NAME, (String) entry.getValue()); | |||
} | |||
/** | |||
* Use to append default types XML elements, use by the save() metid. | |||
* | |||
* @param root | |||
* XML parent element use to append this default type element. | |||
* @param entry | |||
* The values to append. | |||
* @see #save(java.io.OutputStream) | |||
*/ | |||
private void appendDefaultType(Element root, Entry<String, String> entry) { | |||
root.addElement(DEFAULT_TAG_NAME).addAttribute( | |||
EXTENSION_ATTRIBUTE_NAME, (String) entry.getKey()) | |||
.addAttribute(CONTENT_TYPE_ATTRIBUTE_NAME, | |||
(String) entry.getValue()); | |||
} | |||
/** | |||
* Specific implementation of the save method. Call by the save() method, | |||
* call before exiting. | |||
* | |||
* @param out | |||
* The output stream use to write the content type XML. | |||
*/ | |||
public abstract boolean saveImpl(Document content, OutputStream out); | |||
} |
@@ -1,126 +1,126 @@ | |||
/* ==================================================================== | |||
Licensed to the Apache Software Foundation (ASF) under one or more | |||
contributor license agreements. See the NOTICE file distributed with | |||
this work for additional information regarding copyright ownership. | |||
The ASF licenses this file to You under the Apache License, Version 2.0 | |||
(the "License"); you may not use this file except in compliance with | |||
the License. You may obtain a copy of the License at | |||
http://www.apache.org/licenses/LICENSE-2.0 | |||
Unless required by applicable law or agreed to in writing, software | |||
distributed under the License is distributed on an "AS IS" BASIS, | |||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||
See the License for the specific language governing permissions and | |||
limitations under the License. | |||
==================================================================== */ | |||
package org.apache.poi.openxml4j.opc.internal; | |||
import java.io.ByteArrayInputStream; | |||
import java.io.InputStream; | |||
import java.io.OutputStream; | |||
import org.apache.poi.openxml4j.exceptions.InvalidFormatException; | |||
import org.apache.poi.openxml4j.exceptions.OpenXML4JException; | |||
import org.apache.poi.openxml4j.opc.Package; | |||
import org.apache.poi.openxml4j.opc.PackagePart; | |||
import org.apache.poi.openxml4j.opc.PackagePartName; | |||
import org.apache.poi.openxml4j.opc.internal.marshallers.ZipPartMarshaller; | |||
/** | |||
* Memory version of a package part. Use to | |||
* | |||
* @author Julien Chable | |||
* @version 1.0 | |||
*/ | |||
public final class MemoryPackagePart extends PackagePart { | |||
/** | |||
* Storage for the part data. | |||
*/ | |||
protected byte[] data; | |||
/** | |||
* Size of data. | |||
*/ | |||
protected int length; | |||
/** | |||
* Constructor. | |||
* | |||
* @param pack | |||
* The owner package. | |||
* @param partName | |||
* The part name. | |||
* @param contentType | |||
* The content type. | |||
* @throws InvalidFormatException | |||
* If the specified URI is not OPC compliant. | |||
*/ | |||
public MemoryPackagePart(Package pack, PackagePartName partName, | |||
String contentType) throws InvalidFormatException { | |||
super(pack, partName, contentType); | |||
} | |||
/** | |||
* Constructor. | |||
* | |||
* @param pack | |||
* The owner package. | |||
* @param partName | |||
* The part name. | |||
* @param contentType | |||
* The content type. | |||
* @param loadRelationships | |||
* Specify if the relationships will be loaded. | |||
* @throws InvalidFormatException | |||
* If the specified URI is not OPC compliant. | |||
*/ | |||
public MemoryPackagePart(Package pack, PackagePartName partName, | |||
String contentType, boolean loadRelationships) | |||
throws InvalidFormatException { | |||
super(pack, partName, new ContentType(contentType), loadRelationships); | |||
} | |||
@Override | |||
protected InputStream getInputStreamImpl() { | |||
// If this part has been created from scratch and/or the data buffer is | |||
// not | |||
// initialize, so we do it now. | |||
if (data == null) { | |||
data = new byte[0]; | |||
} | |||
return new ByteArrayInputStream(data); | |||
} | |||
@Override | |||
protected OutputStream getOutputStreamImpl() { | |||
return new MemoryPackagePartOutputStream(this); | |||
} | |||
public void clear() { | |||
data = null; | |||
length = 0; | |||
} | |||
@Override | |||
public boolean save(OutputStream os) throws OpenXML4JException { | |||
return new ZipPartMarshaller().marshall(this, os); | |||
} | |||
@Override | |||
public boolean load(InputStream ios) throws InvalidFormatException { | |||
throw new InvalidFormatException("Method not implemented"); | |||
} | |||
@Override | |||
public void close() { | |||
// Do nothing | |||
} | |||
@Override | |||
public void flush() { | |||
// Do nothing | |||
} | |||
} | |||
/* ==================================================================== | |||
Licensed to the Apache Software Foundation (ASF) under one or more | |||
contributor license agreements. See the NOTICE file distributed with | |||
this work for additional information regarding copyright ownership. | |||
The ASF licenses this file to You under the Apache License, Version 2.0 | |||
(the "License"); you may not use this file except in compliance with | |||
the License. You may obtain a copy of the License at | |||
http://www.apache.org/licenses/LICENSE-2.0 | |||
Unless required by applicable law or agreed to in writing, software | |||
distributed under the License is distributed on an "AS IS" BASIS, | |||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||
See the License for the specific language governing permissions and | |||
limitations under the License. | |||
==================================================================== */ | |||
package org.apache.poi.openxml4j.opc.internal; | |||
import java.io.ByteArrayInputStream; | |||
import java.io.InputStream; | |||
import java.io.OutputStream; | |||
import org.apache.poi.openxml4j.exceptions.InvalidFormatException; | |||
import org.apache.poi.openxml4j.exceptions.OpenXML4JException; | |||
import org.apache.poi.openxml4j.opc.OPCPackage; | |||
import org.apache.poi.openxml4j.opc.PackagePart; | |||
import org.apache.poi.openxml4j.opc.PackagePartName; | |||
import org.apache.poi.openxml4j.opc.internal.marshallers.ZipPartMarshaller; | |||
/** | |||
* Memory version of a package part. Use to | |||
* | |||
* @author Julien Chable | |||
* @version 1.0 | |||
*/ | |||
public final class MemoryPackagePart extends PackagePart { | |||
/** | |||
* Storage for the part data. | |||
*/ | |||
protected byte[] data; | |||
/** | |||
* Size of data. | |||
*/ | |||
protected int length; | |||
/** | |||
* Constructor. | |||
* | |||
* @param pack | |||
* The owner package. | |||
* @param partName | |||
* The part name. | |||
* @param contentType | |||
* The content type. | |||
* @throws InvalidFormatException | |||
* If the specified URI is not OPC compliant. | |||
*/ | |||
public MemoryPackagePart(OPCPackage pack, PackagePartName partName, | |||
String contentType) throws InvalidFormatException { | |||
super(pack, partName, contentType); | |||
} | |||
/** | |||
* Constructor. | |||
* | |||
* @param pack | |||
* The owner package. | |||
* @param partName | |||
* The part name. | |||
* @param contentType | |||
* The content type. | |||
* @param loadRelationships | |||
* Specify if the relationships will be loaded. | |||
* @throws InvalidFormatException | |||
* If the specified URI is not OPC compliant. | |||
*/ | |||
public MemoryPackagePart(OPCPackage pack, PackagePartName partName, | |||
String contentType, boolean loadRelationships) | |||
throws InvalidFormatException { | |||
super(pack, partName, new ContentType(contentType), loadRelationships); | |||
} | |||
@Override | |||
protected InputStream getInputStreamImpl() { | |||
// If this part has been created from scratch and/or the data buffer is | |||
// not | |||
// initialize, so we do it now. | |||
if (data == null) { | |||
data = new byte[0]; | |||
} | |||
return new ByteArrayInputStream(data); | |||
} | |||
@Override | |||
protected OutputStream getOutputStreamImpl() { | |||
return new MemoryPackagePartOutputStream(this); | |||
} | |||
public void clear() { | |||
data = null; | |||
length = 0; | |||
} | |||
@Override | |||
public boolean save(OutputStream os) throws OpenXML4JException { | |||
return new ZipPartMarshaller().marshall(this, os); | |||
} | |||
@Override | |||
public boolean load(InputStream ios) throws InvalidFormatException { | |||
throw new InvalidFormatException("Method not implemented"); | |||
} | |||
@Override | |||
public void close() { | |||
// Do nothing | |||
} | |||
@Override | |||
public void flush() { | |||
// Do nothing | |||
} | |||
} |
@@ -1,93 +1,93 @@ | |||
/* ==================================================================== | |||
Licensed to the Apache Software Foundation (ASF) under one or more | |||
contributor license agreements. See the NOTICE file distributed with | |||
this work for additional information regarding copyright ownership. | |||
The ASF licenses this file to You under the Apache License, Version 2.0 | |||
(the "License"); you may not use this file except in compliance with | |||
the License. You may obtain a copy of the License at | |||
http://www.apache.org/licenses/LICENSE-2.0 | |||
Unless required by applicable law or agreed to in writing, software | |||
distributed under the License is distributed on an "AS IS" BASIS, | |||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||
See the License for the specific language governing permissions and | |||
limitations under the License. | |||
==================================================================== */ | |||
package org.apache.poi.openxml4j.opc.internal; | |||
import java.io.ByteArrayInputStream; | |||
import java.io.ByteArrayOutputStream; | |||
import java.io.IOException; | |||
import java.io.InputStream; | |||
import java.io.OutputStream; | |||
import java.util.zip.ZipEntry; | |||
import java.util.zip.ZipOutputStream; | |||
import org.dom4j.Document; | |||
import org.apache.poi.openxml4j.exceptions.InvalidFormatException; | |||
import org.apache.poi.openxml4j.opc.Package; | |||
import org.apache.poi.openxml4j.opc.StreamHelper; | |||
import org.apache.poi.util.POILogger; | |||
import org.apache.poi.util.POILogFactory; | |||
/** | |||
* Zip implementation of the ContentTypeManager. | |||
* | |||
* @author Julien Chable | |||
* @version 1.0 | |||
* @see ContentTypeManager | |||
*/ | |||
public class ZipContentTypeManager extends ContentTypeManager { | |||
private static POILogger logger = POILogFactory.getLogger(ZipContentTypeManager.class); | |||
/** | |||
* Delegate constructor to the super constructor. | |||
* | |||
* @param in | |||
* The input stream to parse to fill internal content type | |||
* collections. | |||
* @throws InvalidFormatException | |||
* If the content types part content is not valid. | |||
*/ | |||
public ZipContentTypeManager(InputStream in, Package pkg) | |||
throws InvalidFormatException { | |||
super(in, pkg); | |||
} | |||
@Override | |||
public boolean saveImpl(Document content, OutputStream out) { | |||
ZipOutputStream zos = null; | |||
if (out instanceof ZipOutputStream) | |||
zos = (ZipOutputStream) out; | |||
else | |||
zos = new ZipOutputStream(out); | |||
ZipEntry partEntry = new ZipEntry(CONTENT_TYPES_PART_NAME); | |||
try { | |||
// Referenced in ZIP | |||
zos.putNextEntry(partEntry); | |||
// Saving data in the ZIP file | |||
ByteArrayOutputStream outTemp = new ByteArrayOutputStream(); | |||
StreamHelper.saveXmlInStream(content, out); | |||
InputStream ins = new ByteArrayInputStream(outTemp.toByteArray()); | |||
byte[] buff = new byte[ZipHelper.READ_WRITE_FILE_BUFFER_SIZE]; | |||
while (ins.available() > 0) { | |||
int resultRead = ins.read(buff); | |||
if (resultRead == -1) { | |||
// end of file reached | |||
break; | |||
} else { | |||
zos.write(buff, 0, resultRead); | |||
} | |||
} | |||
zos.closeEntry(); | |||
} catch (IOException ioe) { | |||
logger.log(POILogger.ERROR, "Cannot write: " + CONTENT_TYPES_PART_NAME | |||
+ " in Zip !", ioe); | |||
return false; | |||
} | |||
return true; | |||
} | |||
} | |||
/* ==================================================================== | |||
Licensed to the Apache Software Foundation (ASF) under one or more | |||
contributor license agreements. See the NOTICE file distributed with | |||
this work for additional information regarding copyright ownership. | |||
The ASF licenses this file to You under the Apache License, Version 2.0 | |||
(the "License"); you may not use this file except in compliance with | |||
the License. You may obtain a copy of the License at | |||
http://www.apache.org/licenses/LICENSE-2.0 | |||
Unless required by applicable law or agreed to in writing, software | |||
distributed under the License is distributed on an "AS IS" BASIS, | |||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||
See the License for the specific language governing permissions and | |||
limitations under the License. | |||
==================================================================== */ | |||
package org.apache.poi.openxml4j.opc.internal; | |||
import java.io.ByteArrayInputStream; | |||
import java.io.ByteArrayOutputStream; | |||
import java.io.IOException; | |||
import java.io.InputStream; | |||
import java.io.OutputStream; | |||
import java.util.zip.ZipEntry; | |||
import java.util.zip.ZipOutputStream; | |||
import org.apache.poi.openxml4j.exceptions.InvalidFormatException; | |||
import org.apache.poi.openxml4j.opc.OPCPackage; | |||
import org.apache.poi.openxml4j.opc.StreamHelper; | |||
import org.apache.poi.util.POILogFactory; | |||
import org.apache.poi.util.POILogger; | |||
import org.dom4j.Document; | |||
/** | |||
* Zip implementation of the ContentTypeManager. | |||
* | |||
* @author Julien Chable | |||
* @version 1.0 | |||
* @see ContentTypeManager | |||
*/ | |||
public class ZipContentTypeManager extends ContentTypeManager { | |||
private static POILogger logger = POILogFactory.getLogger(ZipContentTypeManager.class); | |||
/** | |||
* Delegate constructor to the super constructor. | |||
* | |||
* @param in | |||
* The input stream to parse to fill internal content type | |||
* collections. | |||
* @throws InvalidFormatException | |||
* If the content types part content is not valid. | |||
*/ | |||
public ZipContentTypeManager(InputStream in, OPCPackage pkg) | |||
throws InvalidFormatException { | |||
super(in, pkg); | |||
} | |||
@Override | |||
public boolean saveImpl(Document content, OutputStream out) { | |||
ZipOutputStream zos = null; | |||
if (out instanceof ZipOutputStream) | |||
zos = (ZipOutputStream) out; | |||
else | |||
zos = new ZipOutputStream(out); | |||
ZipEntry partEntry = new ZipEntry(CONTENT_TYPES_PART_NAME); | |||
try { | |||
// Referenced in ZIP | |||
zos.putNextEntry(partEntry); | |||
// Saving data in the ZIP file | |||
ByteArrayOutputStream outTemp = new ByteArrayOutputStream(); | |||
StreamHelper.saveXmlInStream(content, out); | |||
InputStream ins = new ByteArrayInputStream(outTemp.toByteArray()); | |||
byte[] buff = new byte[ZipHelper.READ_WRITE_FILE_BUFFER_SIZE]; | |||
while (ins.available() > 0) { | |||
int resultRead = ins.read(buff); | |||
if (resultRead == -1) { | |||
// end of file reached | |||
break; | |||
} else { | |||
zos.write(buff, 0, resultRead); | |||
} | |||
} | |||
zos.closeEntry(); | |||
} catch (IOException ioe) { | |||
logger.log(POILogger.ERROR, "Cannot write: " + CONTENT_TYPES_PART_NAME | |||
+ " in Zip !", ioe); | |||
return false; | |||
} | |||
return true; | |||
} | |||
} |
@@ -1,96 +1,96 @@ | |||
/* ==================================================================== | |||
Licensed to the Apache Software Foundation (ASF) under one or more | |||
contributor license agreements. See the NOTICE file distributed with | |||
this work for additional information regarding copyright ownership. | |||
The ASF licenses this file to You under the Apache License, Version 2.0 | |||
(the "License"); you may not use this file except in compliance with | |||
the License. You may obtain a copy of the License at | |||
http://www.apache.org/licenses/LICENSE-2.0 | |||
Unless required by applicable law or agreed to in writing, software | |||
distributed under the License is distributed on an "AS IS" BASIS, | |||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||
See the License for the specific language governing permissions and | |||
limitations under the License. | |||
==================================================================== */ | |||
package org.apache.poi.openxml4j.opc.internal.unmarshallers; | |||
import java.util.zip.ZipEntry; | |||
import org.apache.poi.openxml4j.opc.Package; | |||
import org.apache.poi.openxml4j.opc.PackagePartName; | |||
/** | |||
* Context needed for the unmarshall process of a part. This class is immutable. | |||
* | |||
* @author Julien Chable | |||
* @version 1.0 | |||
*/ | |||
public final class UnmarshallContext { | |||
private Package _package; | |||
private PackagePartName partName; | |||
private ZipEntry zipEntry; | |||
/** | |||
* Constructor. | |||
* | |||
* @param targetPackage | |||
* Container. | |||
* @param partName | |||
* Name of the part to unmarshall. | |||
*/ | |||
public UnmarshallContext(Package targetPackage, PackagePartName partName) { | |||
this._package = targetPackage; | |||
this.partName = partName; | |||
} | |||
/** | |||
* @return the container | |||
*/ | |||
Package getPackage() { | |||
return _package; | |||
} | |||
/** | |||
* @param container | |||
* the container to set | |||
*/ | |||
public void setPackage(Package container) { | |||
this._package = container; | |||
} | |||
/** | |||
* @return the partName | |||
*/ | |||
PackagePartName getPartName() { | |||
return partName; | |||
} | |||
/** | |||
* @param partName | |||
* the partName to set | |||
*/ | |||
public void setPartName(PackagePartName partName) { | |||
this.partName = partName; | |||
} | |||
/** | |||
* @return the zipEntry | |||
*/ | |||
ZipEntry getZipEntry() { | |||
return zipEntry; | |||
} | |||
/** | |||
* @param zipEntry | |||
* the zipEntry to set | |||
*/ | |||
public void setZipEntry(ZipEntry zipEntry) { | |||
this.zipEntry = zipEntry; | |||
} | |||
} | |||
/* ==================================================================== | |||
Licensed to the Apache Software Foundation (ASF) under one or more | |||
contributor license agreements. See the NOTICE file distributed with | |||
this work for additional information regarding copyright ownership. | |||
The ASF licenses this file to You under the Apache License, Version 2.0 | |||
(the "License"); you may not use this file except in compliance with | |||
the License. You may obtain a copy of the License at | |||
http://www.apache.org/licenses/LICENSE-2.0 | |||
Unless required by applicable law or agreed to in writing, software | |||
distributed under the License is distributed on an "AS IS" BASIS, | |||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||
See the License for the specific language governing permissions and | |||
limitations under the License. | |||
==================================================================== */ | |||
package org.apache.poi.openxml4j.opc.internal.unmarshallers; | |||
import java.util.zip.ZipEntry; | |||
import org.apache.poi.openxml4j.opc.OPCPackage; | |||
import org.apache.poi.openxml4j.opc.PackagePartName; | |||
/** | |||
* Context needed for the unmarshall process of a part. This class is immutable. | |||
* | |||
* @author Julien Chable | |||
* @version 1.0 | |||
*/ | |||
public final class UnmarshallContext { | |||
private OPCPackage _package; | |||
private PackagePartName partName; | |||
private ZipEntry zipEntry; | |||
/** | |||
* Constructor. | |||
* | |||
* @param targetPackage | |||
* Container. | |||
* @param partName | |||
* Name of the part to unmarshall. | |||
*/ | |||
public UnmarshallContext(OPCPackage targetPackage, PackagePartName partName) { | |||
this._package = targetPackage; | |||
this.partName = partName; | |||
} | |||
/** | |||
* @return the container | |||
*/ | |||
OPCPackage getPackage() { | |||
return _package; | |||
} | |||
/** | |||
* @param container | |||
* the container to set | |||
*/ | |||
public void setPackage(OPCPackage container) { | |||
this._package = container; | |||
} | |||
/** | |||
* @return the partName | |||
*/ | |||
PackagePartName getPartName() { | |||
return partName; | |||
} | |||
/** | |||
* @param partName | |||
* the partName to set | |||
*/ | |||
public void setPartName(PackagePartName partName) { | |||
this.partName = partName; | |||
} | |||
/** | |||
* @return the zipEntry | |||
*/ | |||
ZipEntry getZipEntry() { | |||
return zipEntry; | |||
} | |||
/** | |||
* @param zipEntry | |||
* the zipEntry to set | |||
*/ | |||
public void setZipEntry(ZipEntry zipEntry) { | |||
this.zipEntry = zipEntry; | |||
} | |||
} |
@@ -22,10 +22,10 @@ import java.io.PushbackInputStream; | |||
import org.apache.poi.POIXMLDocument; | |||
import org.apache.poi.hssf.usermodel.HSSFWorkbook; | |||
import org.apache.poi.openxml4j.exceptions.InvalidFormatException; | |||
import org.apache.poi.openxml4j.opc.OPCPackage; | |||
import org.apache.poi.poifs.filesystem.POIFSFileSystem; | |||
import org.apache.poi.xssf.usermodel.XSSFWorkbook; | |||
import org.apache.poi.openxml4j.exceptions.InvalidFormatException; | |||
import org.apache.poi.openxml4j.opc.Package; | |||
/** | |||
* Factory for creating the appropriate kind of Workbook | |||
@@ -41,7 +41,7 @@ public class WorkbookFactory { | |||
/** | |||
* Creates an XSSFWorkbook from the given OOXML Package | |||
*/ | |||
public static Workbook create(Package pkg) throws IOException { | |||
public static Workbook create(OPCPackage pkg) throws IOException { | |||
return new XSSFWorkbook(pkg); | |||
} | |||
/** | |||
@@ -60,7 +60,7 @@ public class WorkbookFactory { | |||
return new HSSFWorkbook(inp); | |||
} | |||
if(POIXMLDocument.hasOOXMLHeader(inp)) { | |||
return new XSSFWorkbook( Package.open(inp) ); | |||
return new XSSFWorkbook(OPCPackage.open(inp)); | |||
} | |||
throw new IllegalArgumentException("Your InputStream was neither an OLE2 stream, nor an OOXML stream"); | |||
} |
@@ -1,144 +1,144 @@ | |||
/* ==================================================================== | |||
Licensed to the Apache Software Foundation (ASF) under one or more | |||
contributor license agreements. See the NOTICE file distributed with | |||
this work for additional information regarding copyright ownership. | |||
The ASF licenses this file to You under the Apache License, Version 2.0 | |||
(the "License"); you may not use this file except in compliance with | |||
the License. You may obtain a copy of the License at | |||
http://www.apache.org/licenses/LICENSE-2.0 | |||
Unless required by applicable law or agreed to in writing, software | |||
distributed under the License is distributed on an "AS IS" BASIS, | |||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||
See the License for the specific language governing permissions and | |||
limitations under the License. | |||
==================================================================== */ | |||
package org.apache.poi.util; | |||
import org.apache.poi.openxml4j.opc.*; | |||
import org.apache.poi.openxml4j.opc.Package; | |||
import org.apache.poi.openxml4j.exceptions.OpenXML4JException; | |||
import org.apache.poi.util.IOUtils; | |||
import java.io.*; | |||
/** | |||
* Provides handy methods to work with OOXML packages | |||
* | |||
* @author Yegor Kozlov | |||
*/ | |||
public class PackageHelper { | |||
/** | |||
* Clone the specified package. | |||
* | |||
* @param pkg the package to clone | |||
* @return the cloned package | |||
*/ | |||
public static Package clone(Package pkg) throws OpenXML4JException, IOException { | |||
return clone(pkg, createTempFile()); | |||
} | |||
/** | |||
* Clone the specified package. | |||
* | |||
* @param pkg the package to clone | |||
* @param file the destination file | |||
* @return the cloned package | |||
*/ | |||
public static Package clone(Package pkg, File file) throws OpenXML4JException, IOException { | |||
String path = file.getAbsolutePath(); | |||
Package dest = Package.create(path); | |||
PackageRelationshipCollection rels = pkg.getRelationships(); | |||
for (PackageRelationship rel : rels) { | |||
PackagePart part = pkg.getPart(rel); | |||
PackagePart part_tgt; | |||
if (rel.getRelationshipType().equals(PackageRelationshipTypes.CORE_PROPERTIES)) { | |||
copyProperties(pkg.getPackageProperties(), dest.getPackageProperties()); | |||
continue; | |||
} else { | |||
dest.addRelationship(part.getPartName(), rel.getTargetMode(), rel.getRelationshipType()); | |||
part_tgt = dest.createPart(part.getPartName(), part.getContentType()); | |||
} | |||
OutputStream out = part_tgt.getOutputStream(); | |||
IOUtils.copy(part.getInputStream(), out); | |||
out.close(); | |||
if(part.hasRelationships()) { | |||
copy(pkg, part, dest, part_tgt); | |||
} | |||
} | |||
dest.close(); | |||
//the temp file will be deleted when JVM terminates | |||
new File(path).deleteOnExit(); | |||
return Package.open(path); | |||
} | |||
/** | |||
* Creates an empty file in the default temporary-file directory, | |||
*/ | |||
public static File createTempFile() throws IOException { | |||
File file = File.createTempFile("poi-ooxml-", ".tmp"); | |||
//there is no way to pass an existing file to Package.create(file), | |||
//delete first, the file will be re-created in Packe.create(file) | |||
file.delete(); | |||
file.deleteOnExit(); | |||
return file; | |||
} | |||
/** | |||
* Recursively copy package parts to the destination package | |||
*/ | |||
private static void copy(Package pkg, PackagePart part, Package tgt, PackagePart part_tgt) throws OpenXML4JException, IOException { | |||
PackageRelationshipCollection rels = part.getRelationships(); | |||
if(rels != null) for (PackageRelationship rel : rels) { | |||
PackagePart p; | |||
if(rel.getTargetMode() == TargetMode.EXTERNAL){ | |||
part_tgt.addExternalRelationship(rel.getTargetURI().toString(), rel.getRelationshipType(), rel.getId()); | |||
//external relations don't have associated package parts | |||
continue; | |||
} else { | |||
PackagePartName relName = PackagingURIHelper.createPartName(rel.getTargetURI()); | |||
p = pkg.getPart(relName); | |||
} | |||
part_tgt.addRelationship(p.getPartName(), rel.getTargetMode(), rel.getRelationshipType(), rel.getId()); | |||
PackagePart dest; | |||
if(!tgt.containPart(p.getPartName())){ | |||
dest = tgt.createPart(p.getPartName(), p.getContentType()); | |||
OutputStream out = dest.getOutputStream(); | |||
IOUtils.copy(p.getInputStream(), out); | |||
out.close(); | |||
copy(pkg, p, tgt, dest); | |||
} | |||
} | |||
} | |||
/** | |||
* Copy core package properties | |||
* | |||
* @param src source properties | |||
* @param tgt target properties | |||
*/ | |||
private static void copyProperties(PackageProperties src, PackageProperties tgt){ | |||
tgt.setCategoryProperty(src.getCategoryProperty().getValue()); | |||
tgt.setContentStatusProperty(src.getContentStatusProperty().getValue()); | |||
tgt.setContentTypeProperty(src.getContentTypeProperty().getValue()); | |||
tgt.setCreatorProperty(src.getCreatorProperty().getValue()); | |||
tgt.setDescriptionProperty(src.getDescriptionProperty().getValue()); | |||
tgt.setIdentifierProperty(src.getIdentifierProperty().getValue()); | |||
tgt.setKeywordsProperty(src.getKeywordsProperty().getValue()); | |||
tgt.setLanguageProperty(src.getLanguageProperty().getValue()); | |||
tgt.setRevisionProperty(src.getRevisionProperty().getValue()); | |||
tgt.setSubjectProperty(src.getSubjectProperty().getValue()); | |||
tgt.setTitleProperty(src.getTitleProperty().getValue()); | |||
tgt.setVersionProperty(src.getVersionProperty().getValue()); | |||
} | |||
} | |||
/* ==================================================================== | |||
Licensed to the Apache Software Foundation (ASF) under one or more | |||
contributor license agreements. See the NOTICE file distributed with | |||
this work for additional information regarding copyright ownership. | |||
The ASF licenses this file to You under the Apache License, Version 2.0 | |||
(the "License"); you may not use this file except in compliance with | |||
the License. You may obtain a copy of the License at | |||
http://www.apache.org/licenses/LICENSE-2.0 | |||
Unless required by applicable law or agreed to in writing, software | |||
distributed under the License is distributed on an "AS IS" BASIS, | |||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||
See the License for the specific language governing permissions and | |||
limitations under the License. | |||
==================================================================== */ | |||
package org.apache.poi.util; | |||
import org.apache.poi.openxml4j.opc.*; | |||
import org.apache.poi.openxml4j.opc.OPCPackage; | |||
import org.apache.poi.openxml4j.exceptions.OpenXML4JException; | |||
import org.apache.poi.util.IOUtils; | |||
import java.io.*; | |||
/** | |||
* Provides handy methods to work with OOXML packages | |||
* | |||
* @author Yegor Kozlov | |||
*/ | |||
public class PackageHelper { | |||
/** | |||
* Clone the specified package. | |||
* | |||
* @param pkg the package to clone | |||
* @return the cloned package | |||
*/ | |||
public static OPCPackage clone(OPCPackage pkg) throws OpenXML4JException, IOException { | |||
return clone(pkg, createTempFile()); | |||
} | |||
/** | |||
* Clone the specified package. | |||
* | |||
* @param pkg the package to clone | |||
* @param file the destination file | |||
* @return the cloned package | |||
*/ | |||
public static OPCPackage clone(OPCPackage pkg, File file) throws OpenXML4JException, IOException { | |||
String path = file.getAbsolutePath(); | |||
OPCPackage dest = OPCPackage.create(path); | |||
PackageRelationshipCollection rels = pkg.getRelationships(); | |||
for (PackageRelationship rel : rels) { | |||
PackagePart part = pkg.getPart(rel); | |||
PackagePart part_tgt; | |||
if (rel.getRelationshipType().equals(PackageRelationshipTypes.CORE_PROPERTIES)) { | |||
copyProperties(pkg.getPackageProperties(), dest.getPackageProperties()); | |||
continue; | |||
} else { | |||
dest.addRelationship(part.getPartName(), rel.getTargetMode(), rel.getRelationshipType()); | |||
part_tgt = dest.createPart(part.getPartName(), part.getContentType()); | |||
} | |||
OutputStream out = part_tgt.getOutputStream(); | |||
IOUtils.copy(part.getInputStream(), out); | |||
out.close(); | |||
if(part.hasRelationships()) { | |||
copy(pkg, part, dest, part_tgt); | |||
} | |||
} | |||
dest.close(); | |||
//the temp file will be deleted when JVM terminates | |||
new File(path).deleteOnExit(); | |||
return OPCPackage.open(path); | |||
} | |||
/** | |||
* Creates an empty file in the default temporary-file directory, | |||
*/ | |||
public static File createTempFile() throws IOException { | |||
File file = File.createTempFile("poi-ooxml-", ".tmp"); | |||
//there is no way to pass an existing file to Package.create(file), | |||
//delete first, the file will be re-created in Packe.create(file) | |||
file.delete(); | |||
file.deleteOnExit(); | |||
return file; | |||
} | |||
/** | |||
* Recursively copy package parts to the destination package | |||
*/ | |||
private static void copy(OPCPackage pkg, PackagePart part, OPCPackage tgt, PackagePart part_tgt) throws OpenXML4JException, IOException { | |||
PackageRelationshipCollection rels = part.getRelationships(); | |||
if(rels != null) for (PackageRelationship rel : rels) { | |||
PackagePart p; | |||
if(rel.getTargetMode() == TargetMode.EXTERNAL){ | |||
part_tgt.addExternalRelationship(rel.getTargetURI().toString(), rel.getRelationshipType(), rel.getId()); | |||
//external relations don't have associated package parts | |||
continue; | |||
} else { | |||
PackagePartName relName = PackagingURIHelper.createPartName(rel.getTargetURI()); | |||
p = pkg.getPart(relName); | |||
} | |||
part_tgt.addRelationship(p.getPartName(), rel.getTargetMode(), rel.getRelationshipType(), rel.getId()); | |||
PackagePart dest; | |||
if(!tgt.containPart(p.getPartName())){ | |||
dest = tgt.createPart(p.getPartName(), p.getContentType()); | |||
OutputStream out = dest.getOutputStream(); | |||
IOUtils.copy(p.getInputStream(), out); | |||
out.close(); | |||
copy(pkg, p, tgt, dest); | |||
} | |||
} | |||
} | |||
/** | |||
* Copy core package properties | |||
* | |||
* @param src source properties | |||
* @param tgt target properties | |||
*/ | |||
private static void copyProperties(PackageProperties src, PackageProperties tgt){ | |||
tgt.setCategoryProperty(src.getCategoryProperty().getValue()); | |||
tgt.setContentStatusProperty(src.getContentStatusProperty().getValue()); | |||
tgt.setContentTypeProperty(src.getContentTypeProperty().getValue()); | |||
tgt.setCreatorProperty(src.getCreatorProperty().getValue()); | |||
tgt.setDescriptionProperty(src.getDescriptionProperty().getValue()); | |||
tgt.setIdentifierProperty(src.getIdentifierProperty().getValue()); | |||
tgt.setKeywordsProperty(src.getKeywordsProperty().getValue()); | |||
tgt.setLanguageProperty(src.getLanguageProperty().getValue()); | |||
tgt.setRevisionProperty(src.getRevisionProperty().getValue()); | |||
tgt.setSubjectProperty(src.getSubjectProperty().getValue()); | |||
tgt.setTitleProperty(src.getTitleProperty().getValue()); | |||
tgt.setVersionProperty(src.getVersionProperty().getValue()); | |||
} | |||
} |
@@ -17,17 +17,17 @@ | |||
package org.apache.poi.xslf; | |||
import java.io.IOException; | |||
import java.util.List; | |||
import java.util.LinkedList; | |||
import java.util.List; | |||
import org.apache.poi.POIXMLDocument; | |||
import org.apache.xmlbeans.XmlException; | |||
import org.apache.poi.openxml4j.exceptions.InvalidFormatException; | |||
import org.apache.poi.openxml4j.exceptions.OpenXML4JException; | |||
import org.apache.poi.openxml4j.opc.Package; | |||
import org.apache.poi.openxml4j.opc.OPCPackage; | |||
import org.apache.poi.openxml4j.opc.PackagePart; | |||
import org.apache.poi.openxml4j.opc.PackageRelationship; | |||
import org.apache.poi.openxml4j.opc.PackageRelationshipCollection; | |||
import org.apache.xmlbeans.XmlException; | |||
import org.openxmlformats.schemas.presentationml.x2006.main.CTCommentList; | |||
import org.openxmlformats.schemas.presentationml.x2006.main.CTNotesSlide; | |||
import org.openxmlformats.schemas.presentationml.x2006.main.CTPresentation; | |||
@@ -68,7 +68,7 @@ public class XSLFSlideShow extends POIXMLDocument { | |||
*/ | |||
private List<PackagePart> embedds; | |||
public XSLFSlideShow(Package container) throws OpenXML4JException, IOException, XmlException { | |||
public XSLFSlideShow(OPCPackage container) throws OpenXML4JException, IOException, XmlException { | |||
super(container); | |||
presentationDoc = |
@@ -19,12 +19,12 @@ package org.apache.poi.xslf.extractor; | |||
import java.io.IOException; | |||
import org.apache.poi.POIXMLTextExtractor; | |||
import org.apache.poi.openxml4j.exceptions.OpenXML4JException; | |||
import org.apache.poi.openxml4j.opc.OPCPackage; | |||
import org.apache.poi.xslf.XSLFSlideShow; | |||
import org.apache.poi.xslf.usermodel.XMLSlideShow; | |||
import org.apache.poi.xslf.usermodel.XSLFSlide; | |||
import org.apache.xmlbeans.XmlException; | |||
import org.apache.poi.openxml4j.exceptions.OpenXML4JException; | |||
import org.apache.poi.openxml4j.opc.Package; | |||
import org.openxmlformats.schemas.drawingml.x2006.main.CTRegularTextRun; | |||
import org.openxmlformats.schemas.drawingml.x2006.main.CTTextBody; | |||
import org.openxmlformats.schemas.drawingml.x2006.main.CTTextParagraph; | |||
@@ -48,7 +48,7 @@ public class XSLFPowerPointExtractor extends POIXMLTextExtractor { | |||
public XSLFPowerPointExtractor(XSLFSlideShow slideshow) throws XmlException, IOException { | |||
this(new XMLSlideShow(slideshow)); | |||
} | |||
public XSLFPowerPointExtractor(Package container) throws XmlException, OpenXML4JException, IOException { | |||
public XSLFPowerPointExtractor(OPCPackage container) throws XmlException, OpenXML4JException, IOException { | |||
this(new XSLFSlideShow(container)); | |||
} | |||
@@ -18,24 +18,28 @@ package org.apache.poi.xssf.eventusermodel; | |||
import java.io.IOException; | |||
import java.io.InputStream; | |||
import java.util.*; | |||
import java.util.ArrayList; | |||
import java.util.Arrays; | |||
import java.util.HashMap; | |||
import java.util.Iterator; | |||
import java.util.Map; | |||
import org.apache.poi.xssf.model.SharedStringsTable; | |||
import org.apache.poi.xssf.model.StylesTable; | |||
import org.apache.poi.xssf.usermodel.XSSFRelation; | |||
import org.apache.poi.POIXMLException; | |||
import org.apache.xmlbeans.XmlException; | |||
import org.apache.poi.openxml4j.exceptions.InvalidFormatException; | |||
import org.apache.poi.openxml4j.exceptions.OpenXML4JException; | |||
import org.apache.poi.openxml4j.opc.Package; | |||
import org.apache.poi.openxml4j.opc.OPCPackage; | |||
import org.apache.poi.openxml4j.opc.PackagePart; | |||
import org.apache.poi.openxml4j.opc.PackagePartName; | |||
import org.apache.poi.openxml4j.opc.PackageRelationship; | |||
import org.apache.poi.openxml4j.opc.PackageRelationshipTypes; | |||
import org.apache.poi.openxml4j.opc.PackagingURIHelper; | |||
import org.apache.poi.xssf.model.SharedStringsTable; | |||
import org.apache.poi.xssf.model.StylesTable; | |||
import org.apache.poi.xssf.usermodel.XSSFRelation; | |||
import org.apache.xmlbeans.XmlException; | |||
import org.openxmlformats.schemas.spreadsheetml.x2006.main.CTSheet; | |||
import org.openxmlformats.schemas.spreadsheetml.x2006.main.CTWorkbook; | |||
import org.openxmlformats.schemas.spreadsheetml.x2006.main.WorkbookDocument; | |||
import org.openxmlformats.schemas.spreadsheetml.x2006.main.CTSheet; | |||
/** | |||
* This class makes it easy to get at individual parts | |||
@@ -45,13 +49,13 @@ import org.openxmlformats.schemas.spreadsheetml.x2006.main.CTSheet; | |||
* for XSSF. | |||
*/ | |||
public class XSSFReader { | |||
private Package pkg; | |||
private OPCPackage pkg; | |||
private PackagePart workbookPart; | |||
/** | |||
* Creates a new XSSFReader, for the given package | |||
*/ | |||
public XSSFReader(Package pkg) throws IOException, OpenXML4JException { | |||
public XSSFReader(OPCPackage pkg) throws IOException, OpenXML4JException { | |||
this.pkg = pkg; | |||
PackageRelationship coreDocRelationship = this.pkg.getRelationshipsByType( |
@@ -21,6 +21,8 @@ import java.util.Iterator; | |||
import org.apache.poi.POIXMLTextExtractor; | |||
import org.apache.poi.hssf.extractor.ExcelExtractor; | |||
import org.apache.poi.openxml4j.exceptions.OpenXML4JException; | |||
import org.apache.poi.openxml4j.opc.OPCPackage; | |||
import org.apache.poi.ss.usermodel.Cell; | |||
import org.apache.poi.ss.usermodel.Comment; | |||
import org.apache.poi.ss.usermodel.HeaderFooter; | |||
@@ -29,8 +31,6 @@ import org.apache.poi.xssf.usermodel.XSSFCell; | |||
import org.apache.poi.xssf.usermodel.XSSFSheet; | |||
import org.apache.poi.xssf.usermodel.XSSFWorkbook; | |||
import org.apache.xmlbeans.XmlException; | |||
import org.apache.poi.openxml4j.exceptions.OpenXML4JException; | |||
import org.apache.poi.openxml4j.opc.Package; | |||
/** | |||
* Helper class to extract text from an OOXML Excel file | |||
@@ -44,7 +44,7 @@ public class XSSFExcelExtractor extends POIXMLTextExtractor implements org.apach | |||
public XSSFExcelExtractor(String path) throws XmlException, OpenXML4JException, IOException { | |||
this(new XSSFWorkbook(path)); | |||
} | |||
public XSSFExcelExtractor(Package container) throws XmlException, OpenXML4JException, IOException { | |||
public XSSFExcelExtractor(OPCPackage container) throws XmlException, OpenXML4JException, IOException { | |||
this(new XSSFWorkbook(container)); | |||
} | |||
public XSSFExcelExtractor(XSSFWorkbook workbook) { |
@@ -36,6 +36,14 @@ import org.apache.poi.POIXMLDocument; | |||
import org.apache.poi.POIXMLDocumentPart; | |||
import org.apache.poi.POIXMLException; | |||
import org.apache.poi.hssf.record.formula.SheetNameFormatter; | |||
import org.apache.poi.openxml4j.exceptions.OpenXML4JException; | |||
import org.apache.poi.openxml4j.opc.OPCPackage; | |||
import org.apache.poi.openxml4j.opc.PackagePart; | |||
import org.apache.poi.openxml4j.opc.PackagePartName; | |||
import org.apache.poi.openxml4j.opc.PackageRelationship; | |||
import org.apache.poi.openxml4j.opc.PackageRelationshipTypes; | |||
import org.apache.poi.openxml4j.opc.PackagingURIHelper; | |||
import org.apache.poi.openxml4j.opc.TargetMode; | |||
import org.apache.poi.ss.usermodel.Row; | |||
import org.apache.poi.ss.usermodel.Sheet; | |||
import org.apache.poi.ss.usermodel.Workbook; | |||
@@ -45,20 +53,12 @@ import org.apache.poi.util.IOUtils; | |||
import org.apache.poi.util.POILogFactory; | |||
import org.apache.poi.util.POILogger; | |||
import org.apache.poi.util.PackageHelper; | |||
import org.apache.poi.xssf.model.CalculationChain; | |||
import org.apache.poi.xssf.model.SharedStringsTable; | |||
import org.apache.poi.xssf.model.StylesTable; | |||
import org.apache.poi.xssf.model.CalculationChain; | |||
import org.apache.xmlbeans.XmlException; | |||
import org.apache.xmlbeans.XmlObject; | |||
import org.apache.xmlbeans.XmlOptions; | |||
import org.apache.poi.openxml4j.exceptions.OpenXML4JException; | |||
import org.apache.poi.openxml4j.opc.Package; | |||
import org.apache.poi.openxml4j.opc.PackagePart; | |||
import org.apache.poi.openxml4j.opc.PackagePartName; | |||
import org.apache.poi.openxml4j.opc.PackageRelationship; | |||
import org.apache.poi.openxml4j.opc.PackageRelationshipTypes; | |||
import org.apache.poi.openxml4j.opc.PackagingURIHelper; | |||
import org.apache.poi.openxml4j.opc.TargetMode; | |||
import org.openxmlformats.schemas.officeDocument.x2006.relationships.STRelationshipId; | |||
import org.openxmlformats.schemas.spreadsheetml.x2006.main.CTBookView; | |||
import org.openxmlformats.schemas.spreadsheetml.x2006.main.CTBookViews; | |||
@@ -152,7 +152,7 @@ public class XSSFWorkbook extends POIXMLDocument implements Workbook, Iterable<X | |||
* | |||
* @param pkg the OpenXML4J <code>Package</code> object. | |||
*/ | |||
public XSSFWorkbook(Package pkg) throws IOException { | |||
public XSSFWorkbook(OPCPackage pkg) throws IOException { | |||
super(ensureWriteAccess(pkg)); | |||
//build a tree of POIXMLDocumentParts, this workbook being the root | |||
@@ -240,9 +240,9 @@ public class XSSFWorkbook extends POIXMLDocument implements Workbook, Iterable<X | |||
/** | |||
* Create a new SpreadsheetML package and setup the default minimal content | |||
*/ | |||
protected static Package newPackage() { | |||
protected static OPCPackage newPackage() { | |||
try { | |||
Package pkg = Package.create(PackageHelper.createTempFile()); | |||
OPCPackage pkg = OPCPackage.create(PackageHelper.createTempFile()); | |||
// Main part | |||
PackagePartName corePartName = PackagingURIHelper.createPartName(XSSFRelation.WORKBOOK.getDefaultFileName()); | |||
// Create main part relationship |
@@ -21,16 +21,16 @@ import java.util.Iterator; | |||
import org.apache.poi.POIXMLDocument; | |||
import org.apache.poi.POIXMLTextExtractor; | |||
import org.apache.poi.xwpf.usermodel.XWPFDocument; | |||
import org.apache.poi.openxml4j.exceptions.OpenXML4JException; | |||
import org.apache.poi.openxml4j.opc.OPCPackage; | |||
import org.apache.poi.xwpf.model.XWPFCommentsDecorator; | |||
import org.apache.poi.xwpf.model.XWPFHeaderFooterPolicy; | |||
import org.apache.poi.xwpf.model.XWPFHyperlinkDecorator; | |||
import org.apache.poi.xwpf.model.XWPFParagraphDecorator; | |||
import org.apache.poi.xwpf.usermodel.XWPFDocument; | |||
import org.apache.poi.xwpf.usermodel.XWPFParagraph; | |||
import org.apache.poi.xwpf.usermodel.XWPFTable; | |||
import org.apache.xmlbeans.XmlException; | |||
import org.apache.poi.openxml4j.exceptions.OpenXML4JException; | |||
import org.apache.poi.openxml4j.opc.Package; | |||
/** | |||
* Helper class to extract text from an OOXML Word file | |||
@@ -39,7 +39,7 @@ public class XWPFWordExtractor extends POIXMLTextExtractor { | |||
private XWPFDocument document; | |||
private boolean fetchHyperlinks = false; | |||
public XWPFWordExtractor(Package container) throws XmlException, OpenXML4JException, IOException { | |||
public XWPFWordExtractor(OPCPackage container) throws XmlException, OpenXML4JException, IOException { | |||
this(new XWPFDocument(container)); | |||
} | |||
public XWPFWordExtractor(XWPFDocument document) { |
@@ -30,7 +30,6 @@ import org.apache.xmlbeans.XmlOptions; | |||
import org.apache.poi.openxml4j.exceptions.InvalidFormatException; | |||
import org.apache.poi.openxml4j.exceptions.OpenXML4JException; | |||
import org.apache.poi.openxml4j.opc.*; | |||
import org.apache.poi.openxml4j.opc.Package; | |||
import org.openxmlformats.schemas.wordprocessingml.x2006.main.CTBody; | |||
import org.openxmlformats.schemas.wordprocessingml.x2006.main.CTComment; | |||
import org.openxmlformats.schemas.wordprocessingml.x2006.main.CTDocument1; | |||
@@ -65,7 +64,7 @@ public class XWPFDocument extends POIXMLDocument { | |||
/** Handles the joy of different headers/footers for different pages */ | |||
private XWPFHeaderFooterPolicy headerFooterPolicy; | |||
public XWPFDocument(Package pkg) throws IOException { | |||
public XWPFDocument(OPCPackage pkg) throws IOException { | |||
super(ensureWriteAccess(pkg)); | |||
//build a tree of POIXMLDocumentParts, this document being the root | |||
@@ -143,9 +142,9 @@ public class XWPFDocument extends POIXMLDocument { | |||
/** | |||
* Create a new SpreadsheetML package and setup the default minimal content | |||
*/ | |||
protected static Package newPackage() { | |||
protected static OPCPackage newPackage() { | |||
try { | |||
Package pkg = Package.create(PackageHelper.createTempFile()); | |||
OPCPackage pkg = OPCPackage.create(PackageHelper.createTempFile()); | |||
// Main part | |||
PackagePartName corePartName = PackagingURIHelper.createPartName(XWPFRelation.DOCUMENT.getDefaultFileName()); | |||
// Create main part relationship |
@@ -25,7 +25,7 @@ import org.apache.poi.util.IOUtils; | |||
import org.apache.poi.xslf.XSLFSlideShow; | |||
import org.apache.poi.xssf.usermodel.XSSFWorkbook; | |||
import org.apache.poi.xwpf.usermodel.XWPFDocument; | |||
import org.apache.poi.openxml4j.opc.Package; | |||
import org.apache.poi.openxml4j.opc.OPCPackage; | |||
import org.apache.poi.openxml4j.opc.PackagePart; | |||
import junit.framework.TestCase; | |||
@@ -47,7 +47,7 @@ public class TestEmbeded extends TestCase | |||
File f = new File(dirname, "ExcelWithAttachments.xlsx"); | |||
assertTrue(f.exists()); | |||
POIXMLDocument doc = new XSSFWorkbook(Package.open(f.toString())); | |||
POIXMLDocument doc = new XSSFWorkbook(OPCPackage.open(f.toString())); | |||
test(doc, 4); | |||
} | |||
@@ -55,7 +55,7 @@ public class TestEmbeded extends TestCase | |||
File f = new File(dirname, "WordWithAttachments.docx"); | |||
assertTrue(f.exists()); | |||
POIXMLDocument doc = new XWPFDocument(Package.open(f.toString())); | |||
POIXMLDocument doc = new XWPFDocument(OPCPackage.open(f.toString())); | |||
test(doc, 5); | |||
} | |||
@@ -63,7 +63,7 @@ public class TestEmbeded extends TestCase | |||
File f = new File(dirname, "PPTWithAttachments.pptx"); | |||
assertTrue(f.exists()); | |||
POIXMLDocument doc = new XSLFSlideShow(Package.open(f.toString())); | |||
POIXMLDocument doc = new XSLFSlideShow(OPCPackage.open(f.toString())); | |||
test(doc, 4); | |||
} | |||
@@ -20,7 +20,7 @@ import java.io.File; | |||
import org.apache.poi.xssf.extractor.XSSFExcelExtractor; | |||
import org.apache.poi.xssf.usermodel.XSSFWorkbook; | |||
import org.apache.poi.openxml4j.opc.Package; | |||
import org.apache.poi.openxml4j.opc.OPCPackage; | |||
import junit.framework.TestCase; | |||
@@ -33,7 +33,7 @@ public class TestXMLPropertiesTextExtractor extends TestCase { | |||
} | |||
public void testGetFromMainExtractor() throws Exception { | |||
org.apache.poi.openxml4j.opc.Package pkg = Package.open( | |||
OPCPackage pkg = OPCPackage.open( | |||
(new File(dirname, "ExcelWithAttachments.xlsx")).toString() | |||
); | |||
XSSFWorkbook wb = new XSSFWorkbook(pkg); | |||
@@ -54,7 +54,7 @@ public class TestXMLPropertiesTextExtractor extends TestCase { | |||
} | |||
public void testCore() throws Exception { | |||
org.apache.poi.openxml4j.opc.Package pkg = Package.open( | |||
OPCPackage pkg = OPCPackage.open( | |||
(new File(dirname, "ExcelWithAttachments.xlsx")).toString() | |||
); | |||
XSSFWorkbook wb = new XSSFWorkbook(pkg); | |||
@@ -71,7 +71,7 @@ public class TestXMLPropertiesTextExtractor extends TestCase { | |||
} | |||
public void testExtended() throws Exception { | |||
org.apache.poi.openxml4j.opc.Package pkg = Package.open( | |||
OPCPackage pkg = OPCPackage.open( | |||
(new File(dirname, "ExcelWithAttachments.xlsx")).toString() | |||
); | |||
XSSFWorkbook wb = new XSSFWorkbook(pkg); |
@@ -34,7 +34,7 @@ import org.apache.poi.xwpf.extractor.XWPFWordExtractor; | |||
import junit.framework.TestCase; | |||
import org.apache.poi.openxml4j.exceptions.InvalidOperationException; | |||
import org.apache.poi.openxml4j.opc.Package; | |||
import org.apache.poi.openxml4j.opc.OPCPackage; | |||
/** | |||
* Test that the extractor factory plays nicely | |||
@@ -276,34 +276,34 @@ public class TestExtractorFactory extends TestCase { | |||
public void testPackage() throws Exception { | |||
// Excel | |||
assertTrue( | |||
ExtractorFactory.createExtractor(Package.open(xlsx.toString())) | |||
ExtractorFactory.createExtractor(OPCPackage.open(xlsx.toString())) | |||
instanceof XSSFExcelExtractor | |||
); | |||
assertTrue( | |||
ExtractorFactory.createExtractor(Package.open(xlsx.toString())).getText().length() > 200 | |||
ExtractorFactory.createExtractor(OPCPackage.open(xlsx.toString())).getText().length() > 200 | |||
); | |||
// Word | |||
assertTrue( | |||
ExtractorFactory.createExtractor(Package.open(docx.toString())) | |||
ExtractorFactory.createExtractor(OPCPackage.open(docx.toString())) | |||
instanceof XWPFWordExtractor | |||
); | |||
assertTrue( | |||
ExtractorFactory.createExtractor(Package.open(docx.toString())).getText().length() > 120 | |||
ExtractorFactory.createExtractor(OPCPackage.open(docx.toString())).getText().length() > 120 | |||
); | |||
// PowerPoint | |||
assertTrue( | |||
ExtractorFactory.createExtractor(Package.open(pptx.toString())) | |||
ExtractorFactory.createExtractor(OPCPackage.open(pptx.toString())) | |||
instanceof XSLFPowerPointExtractor | |||
); | |||
assertTrue( | |||
ExtractorFactory.createExtractor(Package.open(pptx.toString())).getText().length() > 120 | |||
ExtractorFactory.createExtractor(OPCPackage.open(pptx.toString())).getText().length() > 120 | |||
); | |||
// Text | |||
try { | |||
ExtractorFactory.createExtractor(Package.open(txt.toString())); | |||
ExtractorFactory.createExtractor(OPCPackage.open(txt.toString())); | |||
fail(); | |||
} catch(InvalidOperationException e) { | |||
// Good |
@@ -1,103 +1,103 @@ | |||
/* ==================================================================== | |||
Licensed to the Apache Software Foundation (ASF) under one or more | |||
contributor license agreements. See the NOTICE file distributed with | |||
this work for additional information regarding copyright ownership. | |||
The ASF licenses this file to You under the Apache License, Version 2.0 | |||
(the "License"); you may not use this file except in compliance with | |||
the License. You may obtain a copy of the License at | |||
http://www.apache.org/licenses/LICENSE-2.0 | |||
Unless required by applicable law or agreed to in writing, software | |||
distributed under the License is distributed on an "AS IS" BASIS, | |||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||
See the License for the specific language governing permissions and | |||
limitations under the License. | |||
==================================================================== */ | |||
package org.apache.poi.openxml4j.opc; | |||
import java.io.IOException; | |||
import java.io.InputStream; | |||
import java.util.TreeMap; | |||
import junit.framework.TestCase; | |||
import org.apache.log4j.Logger; | |||
import org.apache.poi.openxml4j.OpenXML4JTestDataSamples; | |||
import org.apache.poi.openxml4j.exceptions.InvalidFormatException; | |||
public final class TestListParts extends TestCase { | |||
private static Logger logger = Logger.getLogger("org.apache.poi.openxml4j.test"); | |||
private TreeMap<PackagePartName, String> expectedValues; | |||
private TreeMap<PackagePartName, String> values; | |||
@Override | |||
protected void setUp() throws Exception { | |||
values = new TreeMap<PackagePartName, String>(); | |||
// Expected values | |||
expectedValues = new TreeMap<PackagePartName, String>(); | |||
expectedValues.put(PackagingURIHelper.createPartName("/_rels/.rels"), | |||
"application/vnd.openxmlformats-package.relationships+xml"); | |||
expectedValues | |||
.put(PackagingURIHelper.createPartName("/docProps/app.xml"), | |||
"application/vnd.openxmlformats-officedocument.extended-properties+xml"); | |||
expectedValues.put(PackagingURIHelper | |||
.createPartName("/docProps/core.xml"), | |||
"application/vnd.openxmlformats-package.core-properties+xml"); | |||
expectedValues.put(PackagingURIHelper | |||
.createPartName("/word/_rels/document.xml.rels"), | |||
"application/vnd.openxmlformats-package.relationships+xml"); | |||
expectedValues | |||
.put( | |||
PackagingURIHelper.createPartName("/word/document.xml"), | |||
"application/vnd.openxmlformats-officedocument.wordprocessingml.document.main+xml"); | |||
expectedValues | |||
.put(PackagingURIHelper.createPartName("/word/fontTable.xml"), | |||
"application/vnd.openxmlformats-officedocument.wordprocessingml.fontTable+xml"); | |||
expectedValues.put(PackagingURIHelper | |||
.createPartName("/word/media/image1.gif"), "image/gif"); | |||
expectedValues | |||
.put(PackagingURIHelper.createPartName("/word/settings.xml"), | |||
"application/vnd.openxmlformats-officedocument.wordprocessingml.settings+xml"); | |||
expectedValues | |||
.put(PackagingURIHelper.createPartName("/word/styles.xml"), | |||
"application/vnd.openxmlformats-officedocument.wordprocessingml.styles+xml"); | |||
expectedValues.put(PackagingURIHelper | |||
.createPartName("/word/theme/theme1.xml"), | |||
"application/vnd.openxmlformats-officedocument.theme+xml"); | |||
expectedValues | |||
.put( | |||
PackagingURIHelper | |||
.createPartName("/word/webSettings.xml"), | |||
"application/vnd.openxmlformats-officedocument.wordprocessingml.webSettings+xml"); | |||
} | |||
/** | |||
* List all parts of a package. | |||
*/ | |||
public void testListParts() throws InvalidFormatException { | |||
InputStream is = OpenXML4JTestDataSamples.openSampleStream("sample.docx"); | |||
Package p; | |||
try { | |||
p = Package.open(is); | |||
} catch (IOException e) { | |||
throw new RuntimeException(e); | |||
} | |||
for (PackagePart part : p.getParts()) { | |||
values.put(part.getPartName(), part.getContentType()); | |||
logger.debug(part.getPartName()); | |||
} | |||
// Compare expected values with values return by the package | |||
for (PackagePartName partName : expectedValues.keySet()) { | |||
assertNotNull(values.get(partName)); | |||
assertEquals(expectedValues.get(partName), values.get(partName)); | |||
} | |||
} | |||
} | |||
/* ==================================================================== | |||
Licensed to the Apache Software Foundation (ASF) under one or more | |||
contributor license agreements. See the NOTICE file distributed with | |||
this work for additional information regarding copyright ownership. | |||
The ASF licenses this file to You under the Apache License, Version 2.0 | |||
(the "License"); you may not use this file except in compliance with | |||
the License. You may obtain a copy of the License at | |||
http://www.apache.org/licenses/LICENSE-2.0 | |||
Unless required by applicable law or agreed to in writing, software | |||
distributed under the License is distributed on an "AS IS" BASIS, | |||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||
See the License for the specific language governing permissions and | |||
limitations under the License. | |||
==================================================================== */ | |||
package org.apache.poi.openxml4j.opc; | |||
import java.io.IOException; | |||
import java.io.InputStream; | |||
import java.util.TreeMap; | |||
import junit.framework.TestCase; | |||
import org.apache.log4j.Logger; | |||
import org.apache.poi.openxml4j.OpenXML4JTestDataSamples; | |||
import org.apache.poi.openxml4j.exceptions.InvalidFormatException; | |||
public final class TestListParts extends TestCase { | |||
private static Logger logger = Logger.getLogger("org.apache.poi.openxml4j.test"); | |||
private TreeMap<PackagePartName, String> expectedValues; | |||
private TreeMap<PackagePartName, String> values; | |||
@Override | |||
protected void setUp() throws Exception { | |||
values = new TreeMap<PackagePartName, String>(); | |||
// Expected values | |||
expectedValues = new TreeMap<PackagePartName, String>(); | |||
expectedValues.put(PackagingURIHelper.createPartName("/_rels/.rels"), | |||
"application/vnd.openxmlformats-package.relationships+xml"); | |||
expectedValues | |||
.put(PackagingURIHelper.createPartName("/docProps/app.xml"), | |||
"application/vnd.openxmlformats-officedocument.extended-properties+xml"); | |||
expectedValues.put(PackagingURIHelper | |||
.createPartName("/docProps/core.xml"), | |||
"application/vnd.openxmlformats-package.core-properties+xml"); | |||
expectedValues.put(PackagingURIHelper | |||
.createPartName("/word/_rels/document.xml.rels"), | |||
"application/vnd.openxmlformats-package.relationships+xml"); | |||
expectedValues | |||
.put( | |||
PackagingURIHelper.createPartName("/word/document.xml"), | |||
"application/vnd.openxmlformats-officedocument.wordprocessingml.document.main+xml"); | |||
expectedValues | |||
.put(PackagingURIHelper.createPartName("/word/fontTable.xml"), | |||
"application/vnd.openxmlformats-officedocument.wordprocessingml.fontTable+xml"); | |||
expectedValues.put(PackagingURIHelper | |||
.createPartName("/word/media/image1.gif"), "image/gif"); | |||
expectedValues | |||
.put(PackagingURIHelper.createPartName("/word/settings.xml"), | |||
"application/vnd.openxmlformats-officedocument.wordprocessingml.settings+xml"); | |||
expectedValues | |||
.put(PackagingURIHelper.createPartName("/word/styles.xml"), | |||
"application/vnd.openxmlformats-officedocument.wordprocessingml.styles+xml"); | |||
expectedValues.put(PackagingURIHelper | |||
.createPartName("/word/theme/theme1.xml"), | |||
"application/vnd.openxmlformats-officedocument.theme+xml"); | |||
expectedValues | |||
.put( | |||
PackagingURIHelper | |||
.createPartName("/word/webSettings.xml"), | |||
"application/vnd.openxmlformats-officedocument.wordprocessingml.webSettings+xml"); | |||
} | |||
/** | |||
* List all parts of a package. | |||
*/ | |||
public void testListParts() throws InvalidFormatException { | |||
InputStream is = OpenXML4JTestDataSamples.openSampleStream("sample.docx"); | |||
OPCPackage p; | |||
try { | |||
p = OPCPackage.open(is); | |||
} catch (IOException e) { | |||
throw new RuntimeException(e); | |||
} | |||
for (PackagePart part : p.getParts()) { | |||
values.put(part.getPartName(), part.getContentType()); | |||
logger.debug(part.getPartName()); | |||
} | |||
// Compare expected values with values return by the package | |||
for (PackagePartName partName : expectedValues.keySet()) { | |||
assertNotNull(values.get(partName)); | |||
assertEquals(expectedValues.get(partName), values.get(partName)); | |||
} | |||
} | |||
} |
@@ -1,417 +1,417 @@ | |||
/* ==================================================================== | |||
Licensed to the Apache Software Foundation (ASF) under one or more | |||
contributor license agreements. See the NOTICE file distributed with | |||
this work for additional information regarding copyright ownership. | |||
The ASF licenses this file to You under the Apache License, Version 2.0 | |||
(the "License"); you may not use this file except in compliance with | |||
the License. You may obtain a copy of the License at | |||
http://www.apache.org/licenses/LICENSE-2.0 | |||
Unless required by applicable law or agreed to in writing, software | |||
distributed under the License is distributed on an "AS IS" BASIS, | |||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||
See the License for the specific language governing permissions and | |||
limitations under the License. | |||
==================================================================== */ | |||
package org.apache.poi.openxml4j.opc; | |||
import java.io.ByteArrayInputStream; | |||
import java.io.ByteArrayOutputStream; | |||
import java.io.File; | |||
import java.io.FileInputStream; | |||
import java.io.FileOutputStream; | |||
import java.io.IOException; | |||
import java.io.OutputStream; | |||
import java.lang.reflect.Field; | |||
import java.net.URI; | |||
import java.util.TreeMap; | |||
import junit.framework.TestCase; | |||
import org.apache.log4j.Logger; | |||
import org.apache.poi.openxml4j.OpenXML4JTestDataSamples; | |||
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.dom4j.Document; | |||
import org.dom4j.DocumentHelper; | |||
import org.dom4j.Element; | |||
import org.dom4j.Namespace; | |||
import org.dom4j.QName; | |||
public final class TestPackage extends TestCase { | |||
private static Logger logger = Logger.getLogger("org.apache.poi.openxml4j.test"); | |||
/** | |||
* Test that just opening and closing the file doesn't alter the document. | |||
*/ | |||
public void testOpenSave() throws Exception { | |||
String originalFile = OpenXML4JTestDataSamples.getSampleFileName("TestPackageCommon.docx"); | |||
File targetFile = OpenXML4JTestDataSamples.getOutputFile("TestPackageOpenSaveTMP.docx"); | |||
Package p = Package.open(originalFile, PackageAccess.READ_WRITE); | |||
p.save(targetFile.getAbsoluteFile()); | |||
// Compare the original and newly saved document | |||
assertTrue(targetFile.exists()); | |||
//ZipFileAssert.assertEquals(originalFile, targetFile); | |||
assertTrue(targetFile.delete()); | |||
} | |||
/** | |||
* Test that when we create a new Package, we give it | |||
* the correct default content types | |||
*/ | |||
public void testCreateGetsContentTypes() throws Exception { | |||
File targetFile = OpenXML4JTestDataSamples.getOutputFile("TestCreatePackageTMP.docx"); | |||
// Zap the target file, in case of an earlier run | |||
if(targetFile.exists()) targetFile.delete(); | |||
Package pkg = Package.create(targetFile); | |||
// Check it has content types for rels and xml | |||
ContentTypeManager ctm = getContentTypeManager(pkg); | |||
assertEquals( | |||
"application/xml", | |||
ctm.getContentType( | |||
PackagingURIHelper.createPartName("/foo.xml") | |||
) | |||
); | |||
assertEquals( | |||
ContentTypes.RELATIONSHIPS_PART, | |||
ctm.getContentType( | |||
PackagingURIHelper.createPartName("/foo.rels") | |||
) | |||
); | |||
assertNull( | |||
ctm.getContentType( | |||
PackagingURIHelper.createPartName("/foo.txt") | |||
) | |||
); | |||
} | |||
/** | |||
* Test package creation. | |||
*/ | |||
public void testCreatePackageAddPart() throws Exception { | |||
File targetFile = OpenXML4JTestDataSamples.getOutputFile("TestCreatePackageTMP.docx"); | |||
File expectedFileFile = OpenXML4JTestDataSamples.getOutputFile("TestCreatePackageOUTPUT.docx"); | |||
// Zap the target file, in case of an earlier run | |||
if(targetFile.exists()) targetFile.delete(); | |||
// Create a package | |||
Package pkg = Package.create(targetFile); | |||
PackagePartName corePartName = PackagingURIHelper | |||
.createPartName("/word/document.xml"); | |||
pkg.addRelationship(corePartName, TargetMode.INTERNAL, | |||
PackageRelationshipTypes.CORE_DOCUMENT, "rId1"); | |||
PackagePart corePart = pkg | |||
.createPart( | |||
corePartName, | |||
"application/vnd.openxmlformats-officedocument.wordprocessingml.document.main+xml"); | |||
Document doc = DocumentHelper.createDocument(); | |||
Namespace nsWordprocessinML = new Namespace("w", | |||
"http://schemas.openxmlformats.org/wordprocessingml/2006/main"); | |||
Element elDocument = doc.addElement(new QName("document", | |||
nsWordprocessinML)); | |||
Element elBody = elDocument.addElement(new QName("body", | |||
nsWordprocessinML)); | |||
Element elParagraph = elBody.addElement(new QName("p", | |||
nsWordprocessinML)); | |||
Element elRun = elParagraph | |||
.addElement(new QName("r", nsWordprocessinML)); | |||
Element elText = elRun.addElement(new QName("t", nsWordprocessinML)); | |||
elText.setText("Hello Open XML !"); | |||
StreamHelper.saveXmlInStream(doc, corePart.getOutputStream()); | |||
pkg.close(); | |||
//ZipFileAssert.assertEquals(expectedFile, targetFile); | |||
assertTrue(targetFile.delete()); | |||
} | |||
/** | |||
* Tests that we can create a new package, add a core | |||
* document and another part, save and re-load and | |||
* have everything setup as expected | |||
*/ | |||
public void testCreatePackageWithCoreDocument() throws Exception { | |||
ByteArrayOutputStream baos = new ByteArrayOutputStream(); | |||
Package pkg = Package.create(baos); | |||
// Add a core document | |||
PackagePartName corePartName = PackagingURIHelper.createPartName("/xl/workbook.xml"); | |||
// Create main part relationship | |||
pkg.addRelationship(corePartName, TargetMode.INTERNAL, PackageRelationshipTypes.CORE_DOCUMENT, "rId1"); | |||
// Create main document part | |||
PackagePart corePart = pkg.createPart(corePartName, "application/vnd.openxmlformats-officedocument.spreadsheetml.sheet.main+xml"); | |||
// Put in some dummy content | |||
OutputStream coreOut = corePart.getOutputStream(); | |||
coreOut.write("<dummy-xml />".getBytes()); | |||
coreOut.close(); | |||
// And another bit | |||
PackagePartName sheetPartName = PackagingURIHelper.createPartName("/xl/worksheets/sheet1.xml"); | |||
PackageRelationship rel = | |||
corePart.addRelationship(sheetPartName, TargetMode.INTERNAL, "http://schemas.openxmlformats.org/officeDocument/2006/relationships/worksheet", "rSheet1"); | |||
PackagePart part = pkg.createPart(sheetPartName, "application/vnd.openxmlformats-officedocument.spreadsheetml.worksheet+xml"); | |||
// Dummy content again | |||
coreOut = corePart.getOutputStream(); | |||
coreOut.write("<dummy-xml2 />".getBytes()); | |||
coreOut.close(); | |||
// Check things are as expected | |||
PackageRelationshipCollection coreRels = | |||
pkg.getRelationshipsByType(PackageRelationshipTypes.CORE_DOCUMENT); | |||
assertEquals(1, coreRels.size()); | |||
PackageRelationship coreRel = coreRels.getRelationship(0); | |||
assertEquals("/", coreRel.getSourceURI().toString()); | |||
assertEquals("/xl/workbook.xml", coreRel.getTargetURI().toString()); | |||
assertNotNull(pkg.getPart(coreRel)); | |||
// Save and re-load | |||
pkg.close(); | |||
FileOutputStream fout = new FileOutputStream(File.createTempFile("testCreatePackageWithCoreDocument", ".zip")); | |||
fout.write(baos.toByteArray()); | |||
fout.close(); | |||
pkg = Package.open(new ByteArrayInputStream(baos.toByteArray())); | |||
// 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()); | |||
assertNotNull(pkg.getPart(coreRel)); | |||
} | |||
/** | |||
* Test package opening. | |||
*/ | |||
public void testOpenPackage() throws Exception { | |||
File targetFile = OpenXML4JTestDataSamples.getOutputFile("TestOpenPackageTMP.docx"); | |||
File inputFile = OpenXML4JTestDataSamples.getSampleFile("TestOpenPackageINPUT.docx"); | |||
File expectedFile = OpenXML4JTestDataSamples.getOutputFile("TestOpenPackageOUTPUT.docx"); | |||
// Copy the input file in the output directory | |||
FileHelper.copyFile(inputFile, targetFile); | |||
// Create a package | |||
Package pkg = Package.open(targetFile.getAbsolutePath()); | |||
// Modify core part | |||
PackagePartName corePartName = PackagingURIHelper | |||
.createPartName("/word/document.xml"); | |||
PackagePart corePart = pkg.getPart(corePartName); | |||
// Delete some part to have a valid document | |||
for (PackageRelationship rel : corePart.getRelationships()) { | |||
corePart.removeRelationship(rel.getId()); | |||
pkg.removePart(PackagingURIHelper.createPartName(PackagingURIHelper | |||
.resolvePartUri(corePart.getPartName().getURI(), rel | |||
.getTargetURI()))); | |||
} | |||
// Create a content | |||
Document doc = DocumentHelper.createDocument(); | |||
Namespace nsWordprocessinML = new Namespace("w", | |||
"http://schemas.openxmlformats.org/wordprocessingml/2006/main"); | |||
Element elDocument = doc.addElement(new QName("document", | |||
nsWordprocessinML)); | |||
Element elBody = elDocument.addElement(new QName("body", | |||
nsWordprocessinML)); | |||
Element elParagraph = elBody.addElement(new QName("p", | |||
nsWordprocessinML)); | |||
Element elRun = elParagraph | |||
.addElement(new QName("r", nsWordprocessinML)); | |||
Element elText = elRun.addElement(new QName("t", nsWordprocessinML)); | |||
elText.setText("Hello Open XML !"); | |||
StreamHelper.saveXmlInStream(doc, corePart.getOutputStream()); | |||
// Save and close | |||
try { | |||
pkg.close(); | |||
} catch (IOException e) { | |||
fail(); | |||
} | |||
//ZipFileAssert.assertEquals(expectedFile, targetFile); | |||
assertTrue(targetFile.delete()); | |||
} | |||
/** | |||
* Checks that we can write a package to a simple | |||
* OutputStream, in addition to the normal writing | |||
* to a file | |||
*/ | |||
public void testSaveToOutputStream() throws Exception { | |||
String originalFile = OpenXML4JTestDataSamples.getSampleFileName("TestPackageCommon.docx"); | |||
File targetFile = OpenXML4JTestDataSamples.getOutputFile("TestPackageOpenSaveTMP.docx"); | |||
Package p = Package.open(originalFile, PackageAccess.READ_WRITE); | |||
FileOutputStream fout = new FileOutputStream(targetFile); | |||
p.save(fout); | |||
fout.close(); | |||
// Compare the original and newly saved document | |||
assertTrue(targetFile.exists()); | |||
//ZipFileAssert.assertEquals(originalFile, targetFile); | |||
assertTrue(targetFile.delete()); | |||
} | |||
/** | |||
* Checks that we can open+read a package from a | |||
* simple InputStream, in addition to the normal | |||
* reading from a file | |||
*/ | |||
public void testOpenFromInputStream() throws Exception { | |||
String originalFile = OpenXML4JTestDataSamples.getSampleFileName("TestPackageCommon.docx"); | |||
FileInputStream finp = new FileInputStream(originalFile); | |||
Package p = Package.open(finp); | |||
assertNotNull(p); | |||
assertNotNull(p.getRelationships()); | |||
assertEquals(12, p.getParts().size()); | |||
// Check it has the usual bits | |||
assertTrue(p.hasRelationships()); | |||
assertTrue(p.containPart(PackagingURIHelper.createPartName("/_rels/.rels"))); | |||
} | |||
/** | |||
* TODO: fix and enable | |||
*/ | |||
public void disabled_testRemovePartRecursive() throws Exception { | |||
String originalFile = OpenXML4JTestDataSamples.getSampleFileName("TestPackageCommon.docx"); | |||
File targetFile = OpenXML4JTestDataSamples.getOutputFile("TestPackageRemovePartRecursiveOUTPUT.docx"); | |||
File tempFile = OpenXML4JTestDataSamples.getOutputFile("TestPackageRemovePartRecursiveTMP.docx"); | |||
Package p = Package.open(originalFile, PackageAccess.READ_WRITE); | |||
p.removePartRecursive(PackagingURIHelper.createPartName(new URI( | |||
"/word/document.xml"))); | |||
p.save(tempFile.getAbsoluteFile()); | |||
// Compare the original and newly saved document | |||
assertTrue(targetFile.exists()); | |||
//ZipFileAssert.assertEquals(targetFile, tempFile); | |||
assertTrue(targetFile.delete()); | |||
} | |||
public void testDeletePart() throws InvalidFormatException { | |||
TreeMap<PackagePartName, String> expectedValues; | |||
TreeMap<PackagePartName, String> values; | |||
values = new TreeMap<PackagePartName, String>(); | |||
// Expected values | |||
expectedValues = new TreeMap<PackagePartName, String>(); | |||
expectedValues.put(PackagingURIHelper.createPartName("/_rels/.rels"), | |||
"application/vnd.openxmlformats-package.relationships+xml"); | |||
expectedValues | |||
.put(PackagingURIHelper.createPartName("/docProps/app.xml"), | |||
"application/vnd.openxmlformats-officedocument.extended-properties+xml"); | |||
expectedValues.put(PackagingURIHelper | |||
.createPartName("/docProps/core.xml"), | |||
"application/vnd.openxmlformats-package.core-properties+xml"); | |||
expectedValues | |||
.put(PackagingURIHelper.createPartName("/word/fontTable.xml"), | |||
"application/vnd.openxmlformats-officedocument.wordprocessingml.fontTable+xml"); | |||
expectedValues.put(PackagingURIHelper | |||
.createPartName("/word/media/image1.gif"), "image/gif"); | |||
expectedValues | |||
.put(PackagingURIHelper.createPartName("/word/settings.xml"), | |||
"application/vnd.openxmlformats-officedocument.wordprocessingml.settings+xml"); | |||
expectedValues | |||
.put(PackagingURIHelper.createPartName("/word/styles.xml"), | |||
"application/vnd.openxmlformats-officedocument.wordprocessingml.styles+xml"); | |||
expectedValues.put(PackagingURIHelper | |||
.createPartName("/word/theme/theme1.xml"), | |||
"application/vnd.openxmlformats-officedocument.theme+xml"); | |||
expectedValues | |||
.put( | |||
PackagingURIHelper | |||
.createPartName("/word/webSettings.xml"), | |||
"application/vnd.openxmlformats-officedocument.wordprocessingml.webSettings+xml"); | |||
String filepath = OpenXML4JTestDataSamples.getSampleFileName("sample.docx"); | |||
Package p = Package.open(filepath, PackageAccess.READ_WRITE); | |||
// Remove the core part | |||
p.deletePart(PackagingURIHelper.createPartName("/word/document.xml")); | |||
for (PackagePart part : p.getParts()) { | |||
values.put(part.getPartName(), part.getContentType()); | |||
logger.debug(part.getPartName()); | |||
} | |||
// Compare expected values with values return by the package | |||
for (PackagePartName partName : expectedValues.keySet()) { | |||
assertNotNull(values.get(partName)); | |||
assertEquals(expectedValues.get(partName), values.get(partName)); | |||
} | |||
// Don't save modifications | |||
p.revert(); | |||
} | |||
public void testDeletePartRecursive() throws InvalidFormatException { | |||
TreeMap<PackagePartName, String> expectedValues; | |||
TreeMap<PackagePartName, String> values; | |||
values = new TreeMap<PackagePartName, String>(); | |||
// Expected values | |||
expectedValues = new TreeMap<PackagePartName, String>(); | |||
expectedValues.put(PackagingURIHelper.createPartName("/_rels/.rels"), | |||
"application/vnd.openxmlformats-package.relationships+xml"); | |||
expectedValues | |||
.put(PackagingURIHelper.createPartName("/docProps/app.xml"), | |||
"application/vnd.openxmlformats-officedocument.extended-properties+xml"); | |||
expectedValues.put(PackagingURIHelper | |||
.createPartName("/docProps/core.xml"), | |||
"application/vnd.openxmlformats-package.core-properties+xml"); | |||
String filepath = OpenXML4JTestDataSamples.getSampleFileName("sample.docx"); | |||
Package p = Package.open(filepath, PackageAccess.READ_WRITE); | |||
// Remove the core part | |||
p.deletePartRecursive(PackagingURIHelper.createPartName("/word/document.xml")); | |||
for (PackagePart part : p.getParts()) { | |||
values.put(part.getPartName(), part.getContentType()); | |||
logger.debug(part.getPartName()); | |||
} | |||
// Compare expected values with values return by the package | |||
for (PackagePartName partName : expectedValues.keySet()) { | |||
assertNotNull(values.get(partName)); | |||
assertEquals(expectedValues.get(partName), values.get(partName)); | |||
} | |||
// Don't save modifications | |||
p.revert(); | |||
} | |||
private static ContentTypeManager getContentTypeManager(Package pkg) throws Exception { | |||
Field f = Package.class.getDeclaredField("contentTypeManager"); | |||
f.setAccessible(true); | |||
return (ContentTypeManager)f.get(pkg); | |||
} | |||
} | |||
/* ==================================================================== | |||
Licensed to the Apache Software Foundation (ASF) under one or more | |||
contributor license agreements. See the NOTICE file distributed with | |||
this work for additional information regarding copyright ownership. | |||
The ASF licenses this file to You under the Apache License, Version 2.0 | |||
(the "License"); you may not use this file except in compliance with | |||
the License. You may obtain a copy of the License at | |||
http://www.apache.org/licenses/LICENSE-2.0 | |||
Unless required by applicable law or agreed to in writing, software | |||
distributed under the License is distributed on an "AS IS" BASIS, | |||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||
See the License for the specific language governing permissions and | |||
limitations under the License. | |||
==================================================================== */ | |||
package org.apache.poi.openxml4j.opc; | |||
import java.io.ByteArrayInputStream; | |||
import java.io.ByteArrayOutputStream; | |||
import java.io.File; | |||
import java.io.FileInputStream; | |||
import java.io.FileOutputStream; | |||
import java.io.IOException; | |||
import java.io.OutputStream; | |||
import java.lang.reflect.Field; | |||
import java.net.URI; | |||
import java.util.TreeMap; | |||
import junit.framework.TestCase; | |||
import org.apache.log4j.Logger; | |||
import org.apache.poi.openxml4j.OpenXML4JTestDataSamples; | |||
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.dom4j.Document; | |||
import org.dom4j.DocumentHelper; | |||
import org.dom4j.Element; | |||
import org.dom4j.Namespace; | |||
import org.dom4j.QName; | |||
public final class TestPackage extends TestCase { | |||
private static Logger logger = Logger.getLogger("org.apache.poi.openxml4j.test"); | |||
/** | |||
* Test that just opening and closing the file doesn't alter the document. | |||
*/ | |||
public void testOpenSave() throws Exception { | |||
String originalFile = OpenXML4JTestDataSamples.getSampleFileName("TestPackageCommon.docx"); | |||
File targetFile = OpenXML4JTestDataSamples.getOutputFile("TestPackageOpenSaveTMP.docx"); | |||
OPCPackage p = OPCPackage.open(originalFile, PackageAccess.READ_WRITE); | |||
p.save(targetFile.getAbsoluteFile()); | |||
// Compare the original and newly saved document | |||
assertTrue(targetFile.exists()); | |||
//ZipFileAssert.assertEquals(originalFile, targetFile); | |||
assertTrue(targetFile.delete()); | |||
} | |||
/** | |||
* Test that when we create a new Package, we give it | |||
* the correct default content types | |||
*/ | |||
public void testCreateGetsContentTypes() throws Exception { | |||
File targetFile = OpenXML4JTestDataSamples.getOutputFile("TestCreatePackageTMP.docx"); | |||
// Zap the target file, in case of an earlier run | |||
if(targetFile.exists()) targetFile.delete(); | |||
OPCPackage pkg = OPCPackage.create(targetFile); | |||
// Check it has content types for rels and xml | |||
ContentTypeManager ctm = getContentTypeManager(pkg); | |||
assertEquals( | |||
"application/xml", | |||
ctm.getContentType( | |||
PackagingURIHelper.createPartName("/foo.xml") | |||
) | |||
); | |||
assertEquals( | |||
ContentTypes.RELATIONSHIPS_PART, | |||
ctm.getContentType( | |||
PackagingURIHelper.createPartName("/foo.rels") | |||
) | |||
); | |||
assertNull( | |||
ctm.getContentType( | |||
PackagingURIHelper.createPartName("/foo.txt") | |||
) | |||
); | |||
} | |||
/** | |||
* Test package creation. | |||
*/ | |||
public void testCreatePackageAddPart() throws Exception { | |||
File targetFile = OpenXML4JTestDataSamples.getOutputFile("TestCreatePackageTMP.docx"); | |||
File expectedFileFile = OpenXML4JTestDataSamples.getOutputFile("TestCreatePackageOUTPUT.docx"); | |||
// Zap the target file, in case of an earlier run | |||
if(targetFile.exists()) targetFile.delete(); | |||
// Create a package | |||
OPCPackage pkg = OPCPackage.create(targetFile); | |||
PackagePartName corePartName = PackagingURIHelper | |||
.createPartName("/word/document.xml"); | |||
pkg.addRelationship(corePartName, TargetMode.INTERNAL, | |||
PackageRelationshipTypes.CORE_DOCUMENT, "rId1"); | |||
PackagePart corePart = pkg | |||
.createPart( | |||
corePartName, | |||
"application/vnd.openxmlformats-officedocument.wordprocessingml.document.main+xml"); | |||
Document doc = DocumentHelper.createDocument(); | |||
Namespace nsWordprocessinML = new Namespace("w", | |||
"http://schemas.openxmlformats.org/wordprocessingml/2006/main"); | |||
Element elDocument = doc.addElement(new QName("document", | |||
nsWordprocessinML)); | |||
Element elBody = elDocument.addElement(new QName("body", | |||
nsWordprocessinML)); | |||
Element elParagraph = elBody.addElement(new QName("p", | |||
nsWordprocessinML)); | |||
Element elRun = elParagraph | |||
.addElement(new QName("r", nsWordprocessinML)); | |||
Element elText = elRun.addElement(new QName("t", nsWordprocessinML)); | |||
elText.setText("Hello Open XML !"); | |||
StreamHelper.saveXmlInStream(doc, corePart.getOutputStream()); | |||
pkg.close(); | |||
//ZipFileAssert.assertEquals(expectedFile, targetFile); | |||
assertTrue(targetFile.delete()); | |||
} | |||
/** | |||
* Tests that we can create a new package, add a core | |||
* document and another part, save and re-load and | |||
* have everything setup as expected | |||
*/ | |||
public void testCreatePackageWithCoreDocument() throws Exception { | |||
ByteArrayOutputStream baos = new ByteArrayOutputStream(); | |||
OPCPackage pkg = OPCPackage.create(baos); | |||
// Add a core document | |||
PackagePartName corePartName = PackagingURIHelper.createPartName("/xl/workbook.xml"); | |||
// Create main part relationship | |||
pkg.addRelationship(corePartName, TargetMode.INTERNAL, PackageRelationshipTypes.CORE_DOCUMENT, "rId1"); | |||
// Create main document part | |||
PackagePart corePart = pkg.createPart(corePartName, "application/vnd.openxmlformats-officedocument.spreadsheetml.sheet.main+xml"); | |||
// Put in some dummy content | |||
OutputStream coreOut = corePart.getOutputStream(); | |||
coreOut.write("<dummy-xml />".getBytes()); | |||
coreOut.close(); | |||
// And another bit | |||
PackagePartName sheetPartName = PackagingURIHelper.createPartName("/xl/worksheets/sheet1.xml"); | |||
PackageRelationship rel = | |||
corePart.addRelationship(sheetPartName, TargetMode.INTERNAL, "http://schemas.openxmlformats.org/officeDocument/2006/relationships/worksheet", "rSheet1"); | |||
PackagePart part = pkg.createPart(sheetPartName, "application/vnd.openxmlformats-officedocument.spreadsheetml.worksheet+xml"); | |||
// Dummy content again | |||
coreOut = corePart.getOutputStream(); | |||
coreOut.write("<dummy-xml2 />".getBytes()); | |||
coreOut.close(); | |||
// Check things are as expected | |||
PackageRelationshipCollection coreRels = | |||
pkg.getRelationshipsByType(PackageRelationshipTypes.CORE_DOCUMENT); | |||
assertEquals(1, coreRels.size()); | |||
PackageRelationship coreRel = coreRels.getRelationship(0); | |||
assertEquals("/", coreRel.getSourceURI().toString()); | |||
assertEquals("/xl/workbook.xml", coreRel.getTargetURI().toString()); | |||
assertNotNull(pkg.getPart(coreRel)); | |||
// Save and re-load | |||
pkg.close(); | |||
FileOutputStream fout = new FileOutputStream(File.createTempFile("testCreatePackageWithCoreDocument", ".zip")); | |||
fout.write(baos.toByteArray()); | |||
fout.close(); | |||
pkg = OPCPackage.open(new ByteArrayInputStream(baos.toByteArray())); | |||
// 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()); | |||
assertNotNull(pkg.getPart(coreRel)); | |||
} | |||
/** | |||
* Test package opening. | |||
*/ | |||
public void testOpenPackage() throws Exception { | |||
File targetFile = OpenXML4JTestDataSamples.getOutputFile("TestOpenPackageTMP.docx"); | |||
File inputFile = OpenXML4JTestDataSamples.getSampleFile("TestOpenPackageINPUT.docx"); | |||
File expectedFile = OpenXML4JTestDataSamples.getOutputFile("TestOpenPackageOUTPUT.docx"); | |||
// Copy the input file in the output directory | |||
FileHelper.copyFile(inputFile, targetFile); | |||
// Create a package | |||
OPCPackage pkg = OPCPackage.open(targetFile.getAbsolutePath()); | |||
// Modify core part | |||
PackagePartName corePartName = PackagingURIHelper | |||
.createPartName("/word/document.xml"); | |||
PackagePart corePart = pkg.getPart(corePartName); | |||
// Delete some part to have a valid document | |||
for (PackageRelationship rel : corePart.getRelationships()) { | |||
corePart.removeRelationship(rel.getId()); | |||
pkg.removePart(PackagingURIHelper.createPartName(PackagingURIHelper | |||
.resolvePartUri(corePart.getPartName().getURI(), rel | |||
.getTargetURI()))); | |||
} | |||
// Create a content | |||
Document doc = DocumentHelper.createDocument(); | |||
Namespace nsWordprocessinML = new Namespace("w", | |||
"http://schemas.openxmlformats.org/wordprocessingml/2006/main"); | |||
Element elDocument = doc.addElement(new QName("document", | |||
nsWordprocessinML)); | |||
Element elBody = elDocument.addElement(new QName("body", | |||
nsWordprocessinML)); | |||
Element elParagraph = elBody.addElement(new QName("p", | |||
nsWordprocessinML)); | |||
Element elRun = elParagraph | |||
.addElement(new QName("r", nsWordprocessinML)); | |||
Element elText = elRun.addElement(new QName("t", nsWordprocessinML)); | |||
elText.setText("Hello Open XML !"); | |||
StreamHelper.saveXmlInStream(doc, corePart.getOutputStream()); | |||
// Save and close | |||
try { | |||
pkg.close(); | |||
} catch (IOException e) { | |||
fail(); | |||
} | |||
//ZipFileAssert.assertEquals(expectedFile, targetFile); | |||
assertTrue(targetFile.delete()); | |||
} | |||
/** | |||
* Checks that we can write a package to a simple | |||
* OutputStream, in addition to the normal writing | |||
* to a file | |||
*/ | |||
public void testSaveToOutputStream() throws Exception { | |||
String originalFile = OpenXML4JTestDataSamples.getSampleFileName("TestPackageCommon.docx"); | |||
File targetFile = OpenXML4JTestDataSamples.getOutputFile("TestPackageOpenSaveTMP.docx"); | |||
OPCPackage p = OPCPackage.open(originalFile, PackageAccess.READ_WRITE); | |||
FileOutputStream fout = new FileOutputStream(targetFile); | |||
p.save(fout); | |||
fout.close(); | |||
// Compare the original and newly saved document | |||
assertTrue(targetFile.exists()); | |||
//ZipFileAssert.assertEquals(originalFile, targetFile); | |||
assertTrue(targetFile.delete()); | |||
} | |||
/** | |||
* Checks that we can open+read a package from a | |||
* simple InputStream, in addition to the normal | |||
* reading from a file | |||
*/ | |||
public void testOpenFromInputStream() throws Exception { | |||
String originalFile = OpenXML4JTestDataSamples.getSampleFileName("TestPackageCommon.docx"); | |||
FileInputStream finp = new FileInputStream(originalFile); | |||
OPCPackage p = OPCPackage.open(finp); | |||
assertNotNull(p); | |||
assertNotNull(p.getRelationships()); | |||
assertEquals(12, p.getParts().size()); | |||
// Check it has the usual bits | |||
assertTrue(p.hasRelationships()); | |||
assertTrue(p.containPart(PackagingURIHelper.createPartName("/_rels/.rels"))); | |||
} | |||
/** | |||
* TODO: fix and enable | |||
*/ | |||
public void disabled_testRemovePartRecursive() throws Exception { | |||
String originalFile = OpenXML4JTestDataSamples.getSampleFileName("TestPackageCommon.docx"); | |||
File targetFile = OpenXML4JTestDataSamples.getOutputFile("TestPackageRemovePartRecursiveOUTPUT.docx"); | |||
File tempFile = OpenXML4JTestDataSamples.getOutputFile("TestPackageRemovePartRecursiveTMP.docx"); | |||
OPCPackage p = OPCPackage.open(originalFile, PackageAccess.READ_WRITE); | |||
p.removePartRecursive(PackagingURIHelper.createPartName(new URI( | |||
"/word/document.xml"))); | |||
p.save(tempFile.getAbsoluteFile()); | |||
// Compare the original and newly saved document | |||
assertTrue(targetFile.exists()); | |||
//ZipFileAssert.assertEquals(targetFile, tempFile); | |||
assertTrue(targetFile.delete()); | |||
} | |||
public void testDeletePart() throws InvalidFormatException { | |||
TreeMap<PackagePartName, String> expectedValues; | |||
TreeMap<PackagePartName, String> values; | |||
values = new TreeMap<PackagePartName, String>(); | |||
// Expected values | |||
expectedValues = new TreeMap<PackagePartName, String>(); | |||
expectedValues.put(PackagingURIHelper.createPartName("/_rels/.rels"), | |||
"application/vnd.openxmlformats-package.relationships+xml"); | |||
expectedValues | |||
.put(PackagingURIHelper.createPartName("/docProps/app.xml"), | |||
"application/vnd.openxmlformats-officedocument.extended-properties+xml"); | |||
expectedValues.put(PackagingURIHelper | |||
.createPartName("/docProps/core.xml"), | |||
"application/vnd.openxmlformats-package.core-properties+xml"); | |||
expectedValues | |||
.put(PackagingURIHelper.createPartName("/word/fontTable.xml"), | |||
"application/vnd.openxmlformats-officedocument.wordprocessingml.fontTable+xml"); | |||
expectedValues.put(PackagingURIHelper | |||
.createPartName("/word/media/image1.gif"), "image/gif"); | |||
expectedValues | |||
.put(PackagingURIHelper.createPartName("/word/settings.xml"), | |||
"application/vnd.openxmlformats-officedocument.wordprocessingml.settings+xml"); | |||
expectedValues | |||
.put(PackagingURIHelper.createPartName("/word/styles.xml"), | |||
"application/vnd.openxmlformats-officedocument.wordprocessingml.styles+xml"); | |||
expectedValues.put(PackagingURIHelper | |||
.createPartName("/word/theme/theme1.xml"), | |||
"application/vnd.openxmlformats-officedocument.theme+xml"); | |||
expectedValues | |||
.put( | |||
PackagingURIHelper | |||
.createPartName("/word/webSettings.xml"), | |||
"application/vnd.openxmlformats-officedocument.wordprocessingml.webSettings+xml"); | |||
String filepath = OpenXML4JTestDataSamples.getSampleFileName("sample.docx"); | |||
OPCPackage p = OPCPackage.open(filepath, PackageAccess.READ_WRITE); | |||
// Remove the core part | |||
p.deletePart(PackagingURIHelper.createPartName("/word/document.xml")); | |||
for (PackagePart part : p.getParts()) { | |||
values.put(part.getPartName(), part.getContentType()); | |||
logger.debug(part.getPartName()); | |||
} | |||
// Compare expected values with values return by the package | |||
for (PackagePartName partName : expectedValues.keySet()) { | |||
assertNotNull(values.get(partName)); | |||
assertEquals(expectedValues.get(partName), values.get(partName)); | |||
} | |||
// Don't save modifications | |||
p.revert(); | |||
} | |||
public void testDeletePartRecursive() throws InvalidFormatException { | |||
TreeMap<PackagePartName, String> expectedValues; | |||
TreeMap<PackagePartName, String> values; | |||
values = new TreeMap<PackagePartName, String>(); | |||
// Expected values | |||
expectedValues = new TreeMap<PackagePartName, String>(); | |||
expectedValues.put(PackagingURIHelper.createPartName("/_rels/.rels"), | |||
"application/vnd.openxmlformats-package.relationships+xml"); | |||
expectedValues | |||
.put(PackagingURIHelper.createPartName("/docProps/app.xml"), | |||
"application/vnd.openxmlformats-officedocument.extended-properties+xml"); | |||
expectedValues.put(PackagingURIHelper | |||
.createPartName("/docProps/core.xml"), | |||
"application/vnd.openxmlformats-package.core-properties+xml"); | |||
String filepath = OpenXML4JTestDataSamples.getSampleFileName("sample.docx"); | |||
OPCPackage p = OPCPackage.open(filepath, PackageAccess.READ_WRITE); | |||
// Remove the core part | |||
p.deletePartRecursive(PackagingURIHelper.createPartName("/word/document.xml")); | |||
for (PackagePart part : p.getParts()) { | |||
values.put(part.getPartName(), part.getContentType()); | |||
logger.debug(part.getPartName()); | |||
} | |||
// Compare expected values with values return by the package | |||
for (PackagePartName partName : expectedValues.keySet()) { | |||
assertNotNull(values.get(partName)); | |||
assertEquals(expectedValues.get(partName), values.get(partName)); | |||
} | |||
// Don't save modifications | |||
p.revert(); | |||
} | |||
private static ContentTypeManager getContentTypeManager(OPCPackage pkg) throws Exception { | |||
Field f = OPCPackage.class.getDeclaredField("contentTypeManager"); | |||
f.setAccessible(true); | |||
return (ContentTypeManager)f.get(pkg); | |||
} | |||
} |
@@ -1,121 +1,121 @@ | |||
/* ==================================================================== | |||
Licensed to the Apache Software Foundation (ASF) under one or more | |||
contributor license agreements. See the NOTICE file distributed with | |||
this work for additional information regarding copyright ownership. | |||
The ASF licenses this file to You under the Apache License, Version 2.0 | |||
(the "License"); you may not use this file except in compliance with | |||
the License. You may obtain a copy of the License at | |||
http://www.apache.org/licenses/LICENSE-2.0 | |||
Unless required by applicable law or agreed to in writing, software | |||
distributed under the License is distributed on an "AS IS" BASIS, | |||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||
See the License for the specific language governing permissions and | |||
limitations under the License. | |||
==================================================================== */ | |||
package org.apache.poi.openxml4j.opc; | |||
import java.io.File; | |||
import java.io.IOException; | |||
import java.text.ParsePosition; | |||
import java.text.SimpleDateFormat; | |||
import java.util.Date; | |||
import junit.framework.TestCase; | |||
import org.apache.log4j.Logger; | |||
import org.apache.poi.openxml4j.OpenXML4JTestDataSamples; | |||
import org.apache.poi.openxml4j.exceptions.InvalidFormatException; | |||
import org.apache.poi.openxml4j.exceptions.OpenXML4JException; | |||
import org.apache.poi.openxml4j.util.Nullable; | |||
public final class TestPackageCoreProperties extends TestCase { | |||
/** | |||
* Test package core properties getters. | |||
*/ | |||
public void testGetProperties() { | |||
try { | |||
// Open the package | |||
Package p = Package.open(OpenXML4JTestDataSamples.openSampleStream("TestPackageCoreProperiesGetters.docx")); | |||
compareProperties(p); | |||
p.revert(); | |||
} catch (OpenXML4JException e) { | |||
Logger.getLogger("org.apache.poi.openxml4j.demo").debug(e.getMessage()); | |||
throw new RuntimeException(e); | |||
} catch (IOException e) { | |||
throw new RuntimeException(e); | |||
} | |||
} | |||
/** | |||
* Test package core properties setters. | |||
*/ | |||
public void testSetProperties() throws Exception { | |||
String inputPath = OpenXML4JTestDataSamples.getSampleFileName("TestPackageCoreProperiesSetters.docx"); | |||
File outputFile = OpenXML4JTestDataSamples.getOutputFile("TestPackageCoreProperiesSettersOUTPUT.docx"); | |||
// Open package | |||
Package p = Package.open(inputPath, PackageAccess.READ_WRITE); | |||
SimpleDateFormat df = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss'Z'"); | |||
Date dateToInsert = df.parse("2007-05-12T08:00:00Z", new ParsePosition( | |||
0)); | |||
PackageProperties props = p.getPackageProperties(); | |||
props.setCategoryProperty("MyCategory"); | |||
props.setContentStatusProperty("MyContentStatus"); | |||
props.setContentTypeProperty("MyContentType"); | |||
props.setCreatedProperty(new Nullable<Date>(dateToInsert)); | |||
props.setCreatorProperty("MyCreator"); | |||
props.setDescriptionProperty("MyDescription"); | |||
props.setIdentifierProperty("MyIdentifier"); | |||
props.setKeywordsProperty("MyKeywords"); | |||
props.setLanguageProperty("MyLanguage"); | |||
props.setLastModifiedByProperty("Julien Chable"); | |||
props.setLastPrintedProperty(new Nullable<Date>(dateToInsert)); | |||
props.setModifiedProperty(new Nullable<Date>(dateToInsert)); | |||
props.setRevisionProperty("2"); | |||
props.setTitleProperty("MyTitle"); | |||
props.setSubjectProperty("MySubject"); | |||
props.setVersionProperty("2"); | |||
// Save the package in the output directory | |||
p.save(outputFile); | |||
// Open the newly created file to check core properties saved values. | |||
Package p2 = Package.open(outputFile.getAbsolutePath(), PackageAccess.READ); | |||
compareProperties(p2); | |||
p2.revert(); | |||
outputFile.delete(); | |||
} | |||
private void compareProperties(Package p) throws InvalidFormatException { | |||
SimpleDateFormat df = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss'Z'"); | |||
Date expectedDate = df.parse("2007-05-12T08:00:00Z", new ParsePosition( | |||
0)); | |||
// Gets the core properties | |||
PackageProperties props = p.getPackageProperties(); | |||
assertEquals("MyCategory", props.getCategoryProperty().getValue()); | |||
assertEquals("MyContentStatus", props.getContentStatusProperty() | |||
.getValue()); | |||
assertEquals("MyContentType", props.getContentTypeProperty().getValue()); | |||
assertEquals(expectedDate, props.getCreatedProperty().getValue()); | |||
assertEquals("MyCreator", props.getCreatorProperty().getValue()); | |||
assertEquals("MyDescription", props.getDescriptionProperty().getValue()); | |||
assertEquals("MyIdentifier", props.getIdentifierProperty().getValue()); | |||
assertEquals("MyKeywords", props.getKeywordsProperty().getValue()); | |||
assertEquals("MyLanguage", props.getLanguageProperty().getValue()); | |||
assertEquals("Julien Chable", props.getLastModifiedByProperty() | |||
.getValue()); | |||
assertEquals(expectedDate, props.getLastPrintedProperty().getValue()); | |||
assertEquals(expectedDate, props.getModifiedProperty().getValue()); | |||
assertEquals("2", props.getRevisionProperty().getValue()); | |||
assertEquals("MySubject", props.getSubjectProperty().getValue()); | |||
assertEquals("MyTitle", props.getTitleProperty().getValue()); | |||
assertEquals("2", props.getVersionProperty().getValue()); | |||
} | |||
} | |||
/* ==================================================================== | |||
Licensed to the Apache Software Foundation (ASF) under one or more | |||
contributor license agreements. See the NOTICE file distributed with | |||
this work for additional information regarding copyright ownership. | |||
The ASF licenses this file to You under the Apache License, Version 2.0 | |||
(the "License"); you may not use this file except in compliance with | |||
the License. You may obtain a copy of the License at | |||
http://www.apache.org/licenses/LICENSE-2.0 | |||
Unless required by applicable law or agreed to in writing, software | |||
distributed under the License is distributed on an "AS IS" BASIS, | |||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||
See the License for the specific language governing permissions and | |||
limitations under the License. | |||
==================================================================== */ | |||
package org.apache.poi.openxml4j.opc; | |||
import java.io.File; | |||
import java.io.IOException; | |||
import java.text.ParsePosition; | |||
import java.text.SimpleDateFormat; | |||
import java.util.Date; | |||
import junit.framework.TestCase; | |||
import org.apache.log4j.Logger; | |||
import org.apache.poi.openxml4j.OpenXML4JTestDataSamples; | |||
import org.apache.poi.openxml4j.exceptions.InvalidFormatException; | |||
import org.apache.poi.openxml4j.exceptions.OpenXML4JException; | |||
import org.apache.poi.openxml4j.util.Nullable; | |||
public final class TestPackageCoreProperties extends TestCase { | |||
/** | |||
* Test package core properties getters. | |||
*/ | |||
public void testGetProperties() { | |||
try { | |||
// Open the package | |||
OPCPackage p = OPCPackage.open(OpenXML4JTestDataSamples.openSampleStream("TestPackageCoreProperiesGetters.docx")); | |||
compareProperties(p); | |||
p.revert(); | |||
} catch (OpenXML4JException e) { | |||
Logger.getLogger("org.apache.poi.openxml4j.demo").debug(e.getMessage()); | |||
throw new RuntimeException(e); | |||
} catch (IOException e) { | |||
throw new RuntimeException(e); | |||
} | |||
} | |||
/** | |||
* Test package core properties setters. | |||
*/ | |||
public void testSetProperties() throws Exception { | |||
String inputPath = OpenXML4JTestDataSamples.getSampleFileName("TestPackageCoreProperiesSetters.docx"); | |||
File outputFile = OpenXML4JTestDataSamples.getOutputFile("TestPackageCoreProperiesSettersOUTPUT.docx"); | |||
// Open package | |||
OPCPackage p = OPCPackage.open(inputPath, PackageAccess.READ_WRITE); | |||
SimpleDateFormat df = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss'Z'"); | |||
Date dateToInsert = df.parse("2007-05-12T08:00:00Z", new ParsePosition( | |||
0)); | |||
PackageProperties props = p.getPackageProperties(); | |||
props.setCategoryProperty("MyCategory"); | |||
props.setContentStatusProperty("MyContentStatus"); | |||
props.setContentTypeProperty("MyContentType"); | |||
props.setCreatedProperty(new Nullable<Date>(dateToInsert)); | |||
props.setCreatorProperty("MyCreator"); | |||
props.setDescriptionProperty("MyDescription"); | |||
props.setIdentifierProperty("MyIdentifier"); | |||
props.setKeywordsProperty("MyKeywords"); | |||
props.setLanguageProperty("MyLanguage"); | |||
props.setLastModifiedByProperty("Julien Chable"); | |||
props.setLastPrintedProperty(new Nullable<Date>(dateToInsert)); | |||
props.setModifiedProperty(new Nullable<Date>(dateToInsert)); | |||
props.setRevisionProperty("2"); | |||
props.setTitleProperty("MyTitle"); | |||
props.setSubjectProperty("MySubject"); | |||
props.setVersionProperty("2"); | |||
// Save the package in the output directory | |||
p.save(outputFile); | |||
// Open the newly created file to check core properties saved values. | |||
OPCPackage p2 = OPCPackage.open(outputFile.getAbsolutePath(), PackageAccess.READ); | |||
compareProperties(p2); | |||
p2.revert(); | |||
outputFile.delete(); | |||
} | |||
private void compareProperties(OPCPackage p) throws InvalidFormatException { | |||
SimpleDateFormat df = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss'Z'"); | |||
Date expectedDate = df.parse("2007-05-12T08:00:00Z", new ParsePosition( | |||
0)); | |||
// Gets the core properties | |||
PackageProperties props = p.getPackageProperties(); | |||
assertEquals("MyCategory", props.getCategoryProperty().getValue()); | |||
assertEquals("MyContentStatus", props.getContentStatusProperty() | |||
.getValue()); | |||
assertEquals("MyContentType", props.getContentTypeProperty().getValue()); | |||
assertEquals(expectedDate, props.getCreatedProperty().getValue()); | |||
assertEquals("MyCreator", props.getCreatorProperty().getValue()); | |||
assertEquals("MyDescription", props.getDescriptionProperty().getValue()); | |||
assertEquals("MyIdentifier", props.getIdentifierProperty().getValue()); | |||
assertEquals("MyKeywords", props.getKeywordsProperty().getValue()); | |||
assertEquals("MyLanguage", props.getLanguageProperty().getValue()); | |||
assertEquals("Julien Chable", props.getLastModifiedByProperty() | |||
.getValue()); | |||
assertEquals(expectedDate, props.getLastPrintedProperty().getValue()); | |||
assertEquals(expectedDate, props.getModifiedProperty().getValue()); | |||
assertEquals("2", props.getRevisionProperty().getValue()); | |||
assertEquals("MySubject", props.getSubjectProperty().getValue()); | |||
assertEquals("MyTitle", props.getTitleProperty().getValue()); | |||
assertEquals("2", props.getVersionProperty().getValue()); | |||
} | |||
} |
@@ -1,57 +1,57 @@ | |||
/* ==================================================================== | |||
Licensed to the Apache Software Foundation (ASF) under one or more | |||
contributor license agreements. See the NOTICE file distributed with | |||
this work for additional information regarding copyright ownership. | |||
The ASF licenses this file to You under the Apache License, Version 2.0 | |||
(the "License"); you may not use this file except in compliance with | |||
the License. You may obtain a copy of the License at | |||
http://www.apache.org/licenses/LICENSE-2.0 | |||
Unless required by applicable law or agreed to in writing, software | |||
distributed under the License is distributed on an "AS IS" BASIS, | |||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||
See the License for the specific language governing permissions and | |||
limitations under the License. | |||
==================================================================== */ | |||
package org.apache.poi.openxml4j.opc; | |||
import java.io.File; | |||
import junit.framework.TestCase; | |||
import org.apache.poi.openxml4j.OpenXML4JTestDataSamples; | |||
/** | |||
* Test the addition of thumbnail in a package. | |||
* | |||
* @author Julien Chable | |||
*/ | |||
public final class TestPackageThumbnail extends TestCase { | |||
/** | |||
* Test package addThumbnail() method. | |||
*/ | |||
public void testSetProperties() throws Exception { | |||
String inputPath = OpenXML4JTestDataSamples.getSampleFileName("TestPackageThumbnail.docx"); | |||
String imagePath = OpenXML4JTestDataSamples.getSampleFileName("thumbnail.jpg"); | |||
File outputFile = OpenXML4JTestDataSamples.getOutputFile("TestPackageThumbnailOUTPUT.docx"); | |||
// Open package | |||
Package p = Package.open(inputPath, PackageAccess.READ_WRITE); | |||
p.addThumbnail(imagePath); | |||
// Save the package in the output directory | |||
p.save(outputFile); | |||
// Open the newly created file to check core properties saved values. | |||
Package p2 = Package.open(outputFile.getAbsolutePath(), PackageAccess.READ); | |||
if (p2.getRelationshipsByType(PackageRelationshipTypes.THUMBNAIL) | |||
.size() == 0) | |||
fail("Thumbnail not added to the package !"); | |||
p2.revert(); | |||
outputFile.delete(); | |||
} | |||
} | |||
/* ==================================================================== | |||
Licensed to the Apache Software Foundation (ASF) under one or more | |||
contributor license agreements. See the NOTICE file distributed with | |||
this work for additional information regarding copyright ownership. | |||
The ASF licenses this file to You under the Apache License, Version 2.0 | |||
(the "License"); you may not use this file except in compliance with | |||
the License. You may obtain a copy of the License at | |||
http://www.apache.org/licenses/LICENSE-2.0 | |||
Unless required by applicable law or agreed to in writing, software | |||
distributed under the License is distributed on an "AS IS" BASIS, | |||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||
See the License for the specific language governing permissions and | |||
limitations under the License. | |||
==================================================================== */ | |||
package org.apache.poi.openxml4j.opc; | |||
import java.io.File; | |||
import junit.framework.TestCase; | |||
import org.apache.poi.openxml4j.OpenXML4JTestDataSamples; | |||
/** | |||
* Test the addition of thumbnail in a package. | |||
* | |||
* @author Julien Chable | |||
*/ | |||
public final class TestPackageThumbnail extends TestCase { | |||
/** | |||
* Test package addThumbnail() method. | |||
*/ | |||
public void testSetProperties() throws Exception { | |||
String inputPath = OpenXML4JTestDataSamples.getSampleFileName("TestPackageThumbnail.docx"); | |||
String imagePath = OpenXML4JTestDataSamples.getSampleFileName("thumbnail.jpg"); | |||
File outputFile = OpenXML4JTestDataSamples.getOutputFile("TestPackageThumbnailOUTPUT.docx"); | |||
// Open package | |||
OPCPackage p = OPCPackage.open(inputPath, PackageAccess.READ_WRITE); | |||
p.addThumbnail(imagePath); | |||
// Save the package in the output directory | |||
p.save(outputFile); | |||
// Open the newly created file to check core properties saved values. | |||
OPCPackage p2 = OPCPackage.open(outputFile.getAbsolutePath(), PackageAccess.READ); | |||
if (p2.getRelationshipsByType(PackageRelationshipTypes.THUMBNAIL) | |||
.size() == 0) | |||
fail("Thumbnail not added to the package !"); | |||
p2.revert(); | |||
outputFile.delete(); | |||
} | |||
} |
@@ -1,117 +1,117 @@ | |||
/* ==================================================================== | |||
Licensed to the Apache Software Foundation (ASF) under one or more | |||
contributor license agreements. See the NOTICE file distributed with | |||
this work for additional information regarding copyright ownership. | |||
The ASF licenses this file to You under the Apache License, Version 2.0 | |||
(the "License"); you may not use this file except in compliance with | |||
the License. You may obtain a copy of the License at | |||
http://www.apache.org/licenses/LICENSE-2.0 | |||
Unless required by applicable law or agreed to in writing, software | |||
distributed under the License is distributed on an "AS IS" BASIS, | |||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||
See the License for the specific language governing permissions and | |||
limitations under the License. | |||
==================================================================== */ | |||
package org.apache.poi.openxml4j.opc; | |||
import java.net.URI; | |||
import junit.framework.TestCase; | |||
import org.apache.poi.openxml4j.exceptions.InvalidFormatException; | |||
import org.apache.poi.openxml4j.opc.ContentTypes; | |||
import org.apache.poi.openxml4j.opc.Package; | |||
import org.apache.poi.openxml4j.opc.PackagePart; | |||
import org.apache.poi.openxml4j.opc.PackagePartName; | |||
import org.apache.poi.openxml4j.opc.PackagingURIHelper; | |||
public class TestPackagingURIHelper extends TestCase { | |||
/** | |||
* Test relativizePartName() method. | |||
* | |||
* TODO: fix and unable | |||
*/ | |||
public void testRelativizeURI() throws Exception { | |||
URI uri1 = new URI("/word/document.xml"); | |||
URI uri2 = new URI("/word/media/image1.gif"); | |||
// Document to image is down a directory | |||
URI retURI1to2 = PackagingURIHelper.relativizeURI(uri1, uri2); | |||
assertEquals("media/image1.gif", retURI1to2.getPath()); | |||
// Image to document is up a directory | |||
URI retURI2to1 = PackagingURIHelper.relativizeURI(uri2, uri1); | |||
assertEquals("../document.xml", retURI2to1.getPath()); | |||
// Document and CustomXML parts totally different [Julien C.] | |||
URI uriCustomXml = new URI("/customXml/item1.xml"); | |||
URI uriRes = PackagingURIHelper.relativizeURI(uri1, uriCustomXml); | |||
assertEquals("../customXml/item1.xml", uriRes.toString()); | |||
// Document to itself is the same place (empty URI) | |||
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 | |||
} | |||
} | |||
/** | |||
* Test createPartName(String, y) | |||
*/ | |||
public void testCreatePartNameRelativeString() | |||
throws InvalidFormatException { | |||
PackagePartName partNameToValid = PackagingURIHelper | |||
.createPartName("/word/media/image1.gif"); | |||
Package pkg = Package.create("DELETEIFEXISTS.docx"); | |||
// Base part | |||
PackagePartName nameBase = PackagingURIHelper | |||
.createPartName("/word/document.xml"); | |||
PackagePart partBase = pkg.createPart(nameBase, ContentTypes.XML); | |||
// Relative part name | |||
PackagePartName relativeName = PackagingURIHelper.createPartName( | |||
"media/image1.gif", partBase); | |||
assertTrue("The part name must be equal to " | |||
+ partNameToValid.getName(), partNameToValid | |||
.equals(relativeName)); | |||
pkg.revert(); | |||
} | |||
/** | |||
* Test createPartName(URI, y) | |||
*/ | |||
public void testCreatePartNameRelativeURI() throws Exception { | |||
PackagePartName partNameToValid = PackagingURIHelper | |||
.createPartName("/word/media/image1.gif"); | |||
Package pkg = Package.create("DELETEIFEXISTS.docx"); | |||
// Base part | |||
PackagePartName nameBase = PackagingURIHelper | |||
.createPartName("/word/document.xml"); | |||
PackagePart partBase = pkg.createPart(nameBase, ContentTypes.XML); | |||
// Relative part name | |||
PackagePartName relativeName = PackagingURIHelper.createPartName( | |||
new URI("media/image1.gif"), partBase); | |||
assertTrue("The part name must be equal to " | |||
+ partNameToValid.getName(), partNameToValid | |||
.equals(relativeName)); | |||
pkg.revert(); | |||
} | |||
} | |||
/* ==================================================================== | |||
Licensed to the Apache Software Foundation (ASF) under one or more | |||
contributor license agreements. See the NOTICE file distributed with | |||
this work for additional information regarding copyright ownership. | |||
The ASF licenses this file to You under the Apache License, Version 2.0 | |||
(the "License"); you may not use this file except in compliance with | |||
the License. You may obtain a copy of the License at | |||
http://www.apache.org/licenses/LICENSE-2.0 | |||
Unless required by applicable law or agreed to in writing, software | |||
distributed under the License is distributed on an "AS IS" BASIS, | |||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||
See the License for the specific language governing permissions and | |||
limitations under the License. | |||
==================================================================== */ | |||
package org.apache.poi.openxml4j.opc; | |||
import java.net.URI; | |||
import junit.framework.TestCase; | |||
import org.apache.poi.openxml4j.exceptions.InvalidFormatException; | |||
import org.apache.poi.openxml4j.opc.ContentTypes; | |||
import org.apache.poi.openxml4j.opc.OPCPackage; | |||
import org.apache.poi.openxml4j.opc.PackagePart; | |||
import org.apache.poi.openxml4j.opc.PackagePartName; | |||
import org.apache.poi.openxml4j.opc.PackagingURIHelper; | |||
public class TestPackagingURIHelper extends TestCase { | |||
/** | |||
* Test relativizePartName() method. | |||
* | |||
* TODO: fix and unable | |||
*/ | |||
public void testRelativizeURI() throws Exception { | |||
URI uri1 = new URI("/word/document.xml"); | |||
URI uri2 = new URI("/word/media/image1.gif"); | |||
// Document to image is down a directory | |||
URI retURI1to2 = PackagingURIHelper.relativizeURI(uri1, uri2); | |||
assertEquals("media/image1.gif", retURI1to2.getPath()); | |||
// Image to document is up a directory | |||
URI retURI2to1 = PackagingURIHelper.relativizeURI(uri2, uri1); | |||
assertEquals("../document.xml", retURI2to1.getPath()); | |||
// Document and CustomXML parts totally different [Julien C.] | |||
URI uriCustomXml = new URI("/customXml/item1.xml"); | |||
URI uriRes = PackagingURIHelper.relativizeURI(uri1, uriCustomXml); | |||
assertEquals("../customXml/item1.xml", uriRes.toString()); | |||
// Document to itself is the same place (empty URI) | |||
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 | |||
} | |||
} | |||
/** | |||
* Test createPartName(String, y) | |||
*/ | |||
public void testCreatePartNameRelativeString() | |||
throws InvalidFormatException { | |||
PackagePartName partNameToValid = PackagingURIHelper | |||
.createPartName("/word/media/image1.gif"); | |||
OPCPackage pkg = OPCPackage.create("DELETEIFEXISTS.docx"); | |||
// Base part | |||
PackagePartName nameBase = PackagingURIHelper | |||
.createPartName("/word/document.xml"); | |||
PackagePart partBase = pkg.createPart(nameBase, ContentTypes.XML); | |||
// Relative part name | |||
PackagePartName relativeName = PackagingURIHelper.createPartName( | |||
"media/image1.gif", partBase); | |||
assertTrue("The part name must be equal to " | |||
+ partNameToValid.getName(), partNameToValid | |||
.equals(relativeName)); | |||
pkg.revert(); | |||
} | |||
/** | |||
* Test createPartName(URI, y) | |||
*/ | |||
public void testCreatePartNameRelativeURI() throws Exception { | |||
PackagePartName partNameToValid = PackagingURIHelper | |||
.createPartName("/word/media/image1.gif"); | |||
OPCPackage pkg = OPCPackage.create("DELETEIFEXISTS.docx"); | |||
// Base part | |||
PackagePartName nameBase = PackagingURIHelper | |||
.createPartName("/word/document.xml"); | |||
PackagePart partBase = pkg.createPart(nameBase, ContentTypes.XML); | |||
// Relative part name | |||
PackagePartName relativeName = PackagingURIHelper.createPartName( | |||
new URI("media/image1.gif"), partBase); | |||
assertTrue("The part name must be equal to " | |||
+ partNameToValid.getName(), partNameToValid | |||
.equals(relativeName)); | |||
pkg.revert(); | |||
} | |||
} |
@@ -45,7 +45,7 @@ public class TestRelationships extends TestCase { | |||
*/ | |||
public void testLoadRelationships() throws Exception { | |||
InputStream is = OpenXML4JTestDataSamples.openSampleStream("sample.xlsx"); | |||
Package pkg = Package.open(is); | |||
OPCPackage pkg = OPCPackage.open(is); | |||
logger.debug("1: " + pkg); | |||
PackageRelationshipCollection rels = pkg.getRelationshipsByType(PackageRelationshipTypes.CORE_DOCUMENT); | |||
PackageRelationship coreDocRelationship = rels.getRelationship(0); | |||
@@ -66,7 +66,7 @@ public class TestRelationships extends TestCase { | |||
*/ | |||
public void testFetchFromCollection() throws Exception { | |||
InputStream is = OpenXML4JTestDataSamples.openSampleStream("ExcelWithHyperlinks.xlsx"); | |||
Package pkg = Package.open(is); | |||
OPCPackage pkg = OPCPackage.open(is); | |||
PackagePart sheet = pkg.getPart( | |||
PackagingURIHelper.createPartName(SHEET_WITH_COMMENTS)); | |||
assertNotNull(sheet); | |||
@@ -107,7 +107,7 @@ public class TestRelationships extends TestCase { | |||
*/ | |||
public void testLoadExcelHyperlinkRelations() throws Exception { | |||
InputStream is = OpenXML4JTestDataSamples.openSampleStream("ExcelWithHyperlinks.xlsx"); | |||
Package pkg = Package.open(is); | |||
OPCPackage pkg = OPCPackage.open(is); | |||
PackagePart sheet = pkg.getPart( | |||
PackagingURIHelper.createPartName(SHEET_WITH_COMMENTS)); | |||
assertNotNull(sheet); | |||
@@ -141,7 +141,7 @@ public class TestRelationships extends TestCase { | |||
*/ | |||
public void testCreateExcelHyperlinkRelations() throws Exception { | |||
String filepath = OpenXML4JTestDataSamples.getSampleFileName("ExcelWithHyperlinks.xlsx"); | |||
Package pkg = Package.open(filepath, PackageAccess.READ_WRITE); | |||
OPCPackage pkg = OPCPackage.open(filepath, PackageAccess.READ_WRITE); | |||
PackagePart sheet = pkg.getPart( | |||
PackagingURIHelper.createPartName(SHEET_WITH_COMMENTS)); | |||
assertNotNull(sheet); | |||
@@ -185,7 +185,7 @@ public class TestRelationships extends TestCase { | |||
ByteArrayOutputStream baos = new ByteArrayOutputStream(); | |||
pkg.save(baos); | |||
ByteArrayInputStream bais = new ByteArrayInputStream(baos.toByteArray()); | |||
pkg = Package.open(bais); | |||
pkg = OPCPackage.open(bais); | |||
// Check again | |||
sheet = pkg.getPart( | |||
@@ -208,7 +208,7 @@ public class TestRelationships extends TestCase { | |||
public void testCreateRelationsFromScratch() throws Exception { | |||
ByteArrayOutputStream baos = new ByteArrayOutputStream(); | |||
Package pkg = Package.create(baos); | |||
OPCPackage pkg = OPCPackage.create(baos); | |||
PackagePart partA = | |||
pkg.createPart(PackagingURIHelper.createPartName("/partA"), "text/plain"); | |||
@@ -235,7 +235,7 @@ public class TestRelationships extends TestCase { | |||
// Save, and re-load | |||
pkg.close(); | |||
ByteArrayInputStream bais = new ByteArrayInputStream(baos.toByteArray()); | |||
pkg = Package.open(bais); | |||
pkg = OPCPackage.open(bais); | |||
partA = pkg.getPart(PackagingURIHelper.createPartName("/partA")); | |||
partB = pkg.getPart(PackagingURIHelper.createPartName("/partB")); |
@@ -1,208 +1,208 @@ | |||
/* ==================================================================== | |||
Licensed to the Apache Software Foundation (ASF) under one or more | |||
contributor license agreements. See the NOTICE file distributed with | |||
this work for additional information regarding copyright ownership. | |||
The ASF licenses this file to You under the Apache License, Version 2.0 | |||
(the "License"); you may not use this file except in compliance with | |||
the License. You may obtain a copy of the License at | |||
http://www.apache.org/licenses/LICENSE-2.0 | |||
Unless required by applicable law or agreed to in writing, software | |||
distributed under the License is distributed on an "AS IS" BASIS, | |||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||
See the License for the specific language governing permissions and | |||
limitations under the License. | |||
==================================================================== */ | |||
package org.apache.poi.openxml4j.opc.compliance; | |||
import java.io.IOException; | |||
import java.io.InputStream; | |||
import java.net.URI; | |||
import java.net.URISyntaxException; | |||
import junit.framework.AssertionFailedError; | |||
import junit.framework.TestCase; | |||
import org.apache.poi.openxml4j.OpenXML4JTestDataSamples; | |||
import org.apache.poi.openxml4j.exceptions.InvalidFormatException; | |||
import org.apache.poi.openxml4j.exceptions.InvalidOperationException; | |||
import org.apache.poi.openxml4j.opc.ContentTypes; | |||
import org.apache.poi.openxml4j.opc.Package; | |||
import org.apache.poi.openxml4j.opc.PackageRelationshipTypes; | |||
import org.apache.poi.openxml4j.opc.PackagingURIHelper; | |||
import org.apache.poi.openxml4j.opc.TargetMode; | |||
/** | |||
* Test core properties Open Packaging Convention compliance. | |||
* | |||
* M4.1: The format designer shall specify and the format producer shall create | |||
* at most one core properties relationship for a package. A format consumer | |||
* shall consider more than one core properties relationship for a package to be | |||
* an error. If present, the relationship shall target the Core Properties part. | |||
* | |||
* M4.2: The format designer shall not specify and the format producer shall not | |||
* create Core Properties that use the Markup Compatibility namespace as defined | |||
* in Annex F, "Standard Namespaces and Content Types". A format consumer shall | |||
* consider the use of the Markup Compatibility namespace to be an error. | |||
* | |||
* M4.3: Producers shall not create a document element that contains refinements | |||
* to the Dublin Core elements, except for the two specified in the schema: | |||
* <dcterms:created> and <dcterms:modified> Consumers shall consider a document | |||
* element that violates this constraint to be an error. | |||
* | |||
* M4.4: Producers shall not create a document element that contains the | |||
* xml:lang attribute. Consumers shall consider a document element that violates | |||
* this constraint to be an error. | |||
* | |||
* M4.5: Producers shall not create a document element that contains the | |||
* xsi:type attribute, except for a <dcterms:created> or <dcterms:modified> | |||
* element where the xsi:type attribute shall be present and shall hold the | |||
* value dcterms:W3CDTF, where dcterms is the namespace prefix of the Dublin | |||
* Core namespace. Consumers shall consider a document element that violates | |||
* this constraint to be an error. | |||
* | |||
* @author Julien Chable | |||
*/ | |||
public final class TestOPCComplianceCoreProperties extends TestCase { | |||
public void testCorePropertiesPart() { | |||
Package pkg; | |||
try { | |||
InputStream is = OpenXML4JTestDataSamples.openComplianceSampleStream("OPCCompliance_CoreProperties_OnlyOneCorePropertiesPart.docx"); | |||
pkg = Package.open(is); | |||
} catch (InvalidFormatException e) { | |||
throw new RuntimeException(e); | |||
} catch (IOException e) { | |||
throw new RuntimeException(e); | |||
} | |||
pkg.revert(); | |||
} | |||
private static String extractInvalidFormatMessage(String sampleNameSuffix) { | |||
InputStream is = OpenXML4JTestDataSamples.openComplianceSampleStream("OPCCompliance_CoreProperties_" + sampleNameSuffix); | |||
Package pkg; | |||
try { | |||
pkg = Package.open(is); | |||
} catch (InvalidFormatException e) { | |||
// expected during successful test | |||
return e.getMessage(); | |||
} catch (IOException e) { | |||
throw new RuntimeException(e); | |||
} | |||
pkg.revert(); | |||
// Normally must thrown an InvalidFormatException exception. | |||
throw new AssertionFailedError("expected OPC compliance exception was not thrown"); | |||
} | |||
/** | |||
* Test M4.1 rule. | |||
*/ | |||
public void testOnlyOneCorePropertiesPart() { | |||
String msg = extractInvalidFormatMessage("OnlyOneCorePropertiesPartFAIL.docx"); | |||
assertEquals("OPC Compliance error [M4.1]: there is more than one core properties relationship in the package !", msg); | |||
} | |||
private static URI createURI(String text) { | |||
try { | |||
return new URI(text); | |||
} catch (URISyntaxException e) { | |||
throw new RuntimeException(e); | |||
} | |||
} | |||
/** | |||
* Test M4.1 rule. | |||
*/ | |||
public void testOnlyOneCorePropertiesPart_AddRelationship() { | |||
InputStream is = OpenXML4JTestDataSamples.openComplianceSampleStream("OPCCompliance_CoreProperties_OnlyOneCorePropertiesPart.docx"); | |||
Package pkg; | |||
try { | |||
pkg = Package.open(is); | |||
} catch (InvalidFormatException e) { | |||
throw new RuntimeException(e); | |||
} catch (IOException e) { | |||
throw new RuntimeException(e); | |||
} | |||
URI partUri = createURI("/docProps/core2.xml"); | |||
try { | |||
pkg.addRelationship(PackagingURIHelper.createPartName(partUri), TargetMode.INTERNAL, | |||
PackageRelationshipTypes.CORE_PROPERTIES); | |||
fail("expected OPC compliance exception was not thrown"); | |||
} catch (InvalidFormatException e) { | |||
throw new RuntimeException(e); | |||
} catch (InvalidOperationException e) { | |||
// expected during successful test | |||
assertEquals("OPC Compliance error [M4.1]: can't add another core properties part ! Use the built-in package method instead.", e.getMessage()); | |||
} | |||
pkg.revert(); | |||
} | |||
/** | |||
* Test M4.1 rule. | |||
*/ | |||
public void testOnlyOneCorePropertiesPart_AddPart() { | |||
String sampleFileName = OpenXML4JTestDataSamples.getComplianceSampleFileName("OPCCompliance_CoreProperties_OnlyOneCorePropertiesPart.docx"); | |||
Package pkg = null; | |||
try { | |||
pkg = Package.open(sampleFileName); | |||
} catch (InvalidFormatException e) { | |||
throw new RuntimeException(e); | |||
} | |||
URI partUri = createURI("/docProps/core2.xml"); | |||
try { | |||
pkg.createPart(PackagingURIHelper.createPartName(partUri), | |||
ContentTypes.CORE_PROPERTIES_PART); | |||
fail("expected OPC compliance exception was not thrown"); | |||
} catch (InvalidFormatException e) { | |||
throw new RuntimeException(e); | |||
} catch (InvalidOperationException e) { | |||
// expected during successful test | |||
assertEquals("OPC Compliance error [M4.1]: you try to add more than one core properties relationship in the package !", e.getMessage()); | |||
} | |||
pkg.revert(); | |||
} | |||
/** | |||
* Test M4.2 rule. | |||
*/ | |||
public void testDoNotUseCompatibilityMarkup() { | |||
String msg = extractInvalidFormatMessage("DoNotUseCompatibilityMarkupFAIL.docx"); | |||
assertEquals("OPC Compliance error [M4.2]: A format consumer shall consider the use of the Markup Compatibility namespace to be an error.", msg); | |||
} | |||
/** | |||
* Test M4.3 rule. | |||
*/ | |||
public void testDCTermsNamespaceLimitedUse() { | |||
String msg = extractInvalidFormatMessage("DCTermsNamespaceLimitedUseFAIL.docx"); | |||
assertEquals("OPC Compliance error [M4.3]: Producers shall not create a document element that contains refinements to the Dublin Core elements, except for the two specified in the schema: <dcterms:created> and <dcterms:modified> Consumers shall consider a document element that violates this constraint to be an error.", msg); | |||
} | |||
/** | |||
* Test M4.4 rule. | |||
*/ | |||
public void testUnauthorizedXMLLangAttribute() { | |||
String msg = extractInvalidFormatMessage("UnauthorizedXMLLangAttributeFAIL.docx"); | |||
assertEquals("OPC Compliance error [M4.4]: Producers shall not create a document element that contains the xml:lang attribute. Consumers shall consider a document element that violates this constraint to be an error.", msg); | |||
} | |||
/** | |||
* Test M4.5 rule. | |||
*/ | |||
public void testLimitedXSITypeAttribute_NotPresent() { | |||
String msg = extractInvalidFormatMessage("LimitedXSITypeAttribute_NotPresentFAIL.docx"); | |||
assertEquals("The element 'created' must have the 'xsi:type' attribute present !", msg); | |||
} | |||
/** | |||
* Test M4.5 rule. | |||
*/ | |||
public void testLimitedXSITypeAttribute_PresentWithUnauthorizedValue() { | |||
String msg = extractInvalidFormatMessage("LimitedXSITypeAttribute_PresentWithUnauthorizedValueFAIL.docx"); | |||
assertEquals("The element 'modified' must have the 'xsi:type' attribute with the value 'dcterms:W3CDTF' !", msg); | |||
} | |||
} | |||
/* ==================================================================== | |||
Licensed to the Apache Software Foundation (ASF) under one or more | |||
contributor license agreements. See the NOTICE file distributed with | |||
this work for additional information regarding copyright ownership. | |||
The ASF licenses this file to You under the Apache License, Version 2.0 | |||
(the "License"); you may not use this file except in compliance with | |||
the License. You may obtain a copy of the License at | |||
http://www.apache.org/licenses/LICENSE-2.0 | |||
Unless required by applicable law or agreed to in writing, software | |||
distributed under the License is distributed on an "AS IS" BASIS, | |||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||
See the License for the specific language governing permissions and | |||
limitations under the License. | |||
==================================================================== */ | |||
package org.apache.poi.openxml4j.opc.compliance; | |||
import java.io.IOException; | |||
import java.io.InputStream; | |||
import java.net.URI; | |||
import java.net.URISyntaxException; | |||
import junit.framework.AssertionFailedError; | |||
import junit.framework.TestCase; | |||
import org.apache.poi.openxml4j.OpenXML4JTestDataSamples; | |||
import org.apache.poi.openxml4j.exceptions.InvalidFormatException; | |||
import org.apache.poi.openxml4j.exceptions.InvalidOperationException; | |||
import org.apache.poi.openxml4j.opc.ContentTypes; | |||
import org.apache.poi.openxml4j.opc.OPCPackage; | |||
import org.apache.poi.openxml4j.opc.PackageRelationshipTypes; | |||
import org.apache.poi.openxml4j.opc.PackagingURIHelper; | |||
import org.apache.poi.openxml4j.opc.TargetMode; | |||
/** | |||
* Test core properties Open Packaging Convention compliance. | |||
* | |||
* M4.1: The format designer shall specify and the format producer shall create | |||
* at most one core properties relationship for a package. A format consumer | |||
* shall consider more than one core properties relationship for a package to be | |||
* an error. If present, the relationship shall target the Core Properties part. | |||
* | |||
* M4.2: The format designer shall not specify and the format producer shall not | |||
* create Core Properties that use the Markup Compatibility namespace as defined | |||
* in Annex F, "Standard Namespaces and Content Types". A format consumer shall | |||
* consider the use of the Markup Compatibility namespace to be an error. | |||
* | |||
* M4.3: Producers shall not create a document element that contains refinements | |||
* to the Dublin Core elements, except for the two specified in the schema: | |||
* <dcterms:created> and <dcterms:modified> Consumers shall consider a document | |||
* element that violates this constraint to be an error. | |||
* | |||
* M4.4: Producers shall not create a document element that contains the | |||
* xml:lang attribute. Consumers shall consider a document element that violates | |||
* this constraint to be an error. | |||
* | |||
* M4.5: Producers shall not create a document element that contains the | |||
* xsi:type attribute, except for a <dcterms:created> or <dcterms:modified> | |||
* element where the xsi:type attribute shall be present and shall hold the | |||
* value dcterms:W3CDTF, where dcterms is the namespace prefix of the Dublin | |||
* Core namespace. Consumers shall consider a document element that violates | |||
* this constraint to be an error. | |||
* | |||
* @author Julien Chable | |||
*/ | |||
public final class TestOPCComplianceCoreProperties extends TestCase { | |||
public void testCorePropertiesPart() { | |||
OPCPackage pkg; | |||
try { | |||
InputStream is = OpenXML4JTestDataSamples.openComplianceSampleStream("OPCCompliance_CoreProperties_OnlyOneCorePropertiesPart.docx"); | |||
pkg = OPCPackage.open(is); | |||
} catch (InvalidFormatException e) { | |||
throw new RuntimeException(e); | |||
} catch (IOException e) { | |||
throw new RuntimeException(e); | |||
} | |||
pkg.revert(); | |||
} | |||
private static String extractInvalidFormatMessage(String sampleNameSuffix) { | |||
InputStream is = OpenXML4JTestDataSamples.openComplianceSampleStream("OPCCompliance_CoreProperties_" + sampleNameSuffix); | |||
OPCPackage pkg; | |||
try { | |||
pkg = OPCPackage.open(is); | |||
} catch (InvalidFormatException e) { | |||
// expected during successful test | |||
return e.getMessage(); | |||
} catch (IOException e) { | |||
throw new RuntimeException(e); | |||
} | |||
pkg.revert(); | |||
// Normally must thrown an InvalidFormatException exception. | |||
throw new AssertionFailedError("expected OPC compliance exception was not thrown"); | |||
} | |||
/** | |||
* Test M4.1 rule. | |||
*/ | |||
public void testOnlyOneCorePropertiesPart() { | |||
String msg = extractInvalidFormatMessage("OnlyOneCorePropertiesPartFAIL.docx"); | |||
assertEquals("OPC Compliance error [M4.1]: there is more than one core properties relationship in the package !", msg); | |||
} | |||
private static URI createURI(String text) { | |||
try { | |||
return new URI(text); | |||
} catch (URISyntaxException e) { | |||
throw new RuntimeException(e); | |||
} | |||
} | |||
/** | |||
* Test M4.1 rule. | |||
*/ | |||
public void testOnlyOneCorePropertiesPart_AddRelationship() { | |||
InputStream is = OpenXML4JTestDataSamples.openComplianceSampleStream("OPCCompliance_CoreProperties_OnlyOneCorePropertiesPart.docx"); | |||
OPCPackage pkg; | |||
try { | |||
pkg = OPCPackage.open(is); | |||
} catch (InvalidFormatException e) { | |||
throw new RuntimeException(e); | |||
} catch (IOException e) { | |||
throw new RuntimeException(e); | |||
} | |||
URI partUri = createURI("/docProps/core2.xml"); | |||
try { | |||
pkg.addRelationship(PackagingURIHelper.createPartName(partUri), TargetMode.INTERNAL, | |||
PackageRelationshipTypes.CORE_PROPERTIES); | |||
fail("expected OPC compliance exception was not thrown"); | |||
} catch (InvalidFormatException e) { | |||
throw new RuntimeException(e); | |||
} catch (InvalidOperationException e) { | |||
// expected during successful test | |||
assertEquals("OPC Compliance error [M4.1]: can't add another core properties part ! Use the built-in package method instead.", e.getMessage()); | |||
} | |||
pkg.revert(); | |||
} | |||
/** | |||
* Test M4.1 rule. | |||
*/ | |||
public void testOnlyOneCorePropertiesPart_AddPart() { | |||
String sampleFileName = OpenXML4JTestDataSamples.getComplianceSampleFileName("OPCCompliance_CoreProperties_OnlyOneCorePropertiesPart.docx"); | |||
OPCPackage pkg = null; | |||
try { | |||
pkg = OPCPackage.open(sampleFileName); | |||
} catch (InvalidFormatException e) { | |||
throw new RuntimeException(e); | |||
} | |||
URI partUri = createURI("/docProps/core2.xml"); | |||
try { | |||
pkg.createPart(PackagingURIHelper.createPartName(partUri), | |||
ContentTypes.CORE_PROPERTIES_PART); | |||
fail("expected OPC compliance exception was not thrown"); | |||
} catch (InvalidFormatException e) { | |||
throw new RuntimeException(e); | |||
} catch (InvalidOperationException e) { | |||
// expected during successful test | |||
assertEquals("OPC Compliance error [M4.1]: you try to add more than one core properties relationship in the package !", e.getMessage()); | |||
} | |||
pkg.revert(); | |||
} | |||
/** | |||
* Test M4.2 rule. | |||
*/ | |||
public void testDoNotUseCompatibilityMarkup() { | |||
String msg = extractInvalidFormatMessage("DoNotUseCompatibilityMarkupFAIL.docx"); | |||
assertEquals("OPC Compliance error [M4.2]: A format consumer shall consider the use of the Markup Compatibility namespace to be an error.", msg); | |||
} | |||
/** | |||
* Test M4.3 rule. | |||
*/ | |||
public void testDCTermsNamespaceLimitedUse() { | |||
String msg = extractInvalidFormatMessage("DCTermsNamespaceLimitedUseFAIL.docx"); | |||
assertEquals("OPC Compliance error [M4.3]: Producers shall not create a document element that contains refinements to the Dublin Core elements, except for the two specified in the schema: <dcterms:created> and <dcterms:modified> Consumers shall consider a document element that violates this constraint to be an error.", msg); | |||
} | |||
/** | |||
* Test M4.4 rule. | |||
*/ | |||
public void testUnauthorizedXMLLangAttribute() { | |||
String msg = extractInvalidFormatMessage("UnauthorizedXMLLangAttributeFAIL.docx"); | |||
assertEquals("OPC Compliance error [M4.4]: Producers shall not create a document element that contains the xml:lang attribute. Consumers shall consider a document element that violates this constraint to be an error.", msg); | |||
} | |||
/** | |||
* Test M4.5 rule. | |||
*/ | |||
public void testLimitedXSITypeAttribute_NotPresent() { | |||
String msg = extractInvalidFormatMessage("LimitedXSITypeAttribute_NotPresentFAIL.docx"); | |||
assertEquals("The element 'created' must have the 'xsi:type' attribute present !", msg); | |||
} | |||
/** | |||
* Test M4.5 rule. | |||
*/ | |||
public void testLimitedXSITypeAttribute_PresentWithUnauthorizedValue() { | |||
String msg = extractInvalidFormatMessage("LimitedXSITypeAttribute_PresentWithUnauthorizedValueFAIL.docx"); | |||
assertEquals("The element 'modified' must have the 'xsi:type' attribute with the value 'dcterms:W3CDTF' !", msg); | |||
} | |||
} |
@@ -1,162 +1,162 @@ | |||
/* ==================================================================== | |||
Licensed to the Apache Software Foundation (ASF) under one or more | |||
contributor license agreements. See the NOTICE file distributed with | |||
this work for additional information regarding copyright ownership. | |||
The ASF licenses this file to You under the Apache License, Version 2.0 | |||
(the "License"); you may not use this file except in compliance with | |||
the License. You may obtain a copy of the License at | |||
http://www.apache.org/licenses/LICENSE-2.0 | |||
Unless required by applicable law or agreed to in writing, software | |||
distributed under the License is distributed on an "AS IS" BASIS, | |||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||
See the License for the specific language governing permissions and | |||
limitations under the License. | |||
==================================================================== */ | |||
package org.apache.poi.openxml4j.opc.compliance; | |||
import java.io.File; | |||
import junit.framework.TestCase; | |||
import org.apache.poi.openxml4j.exceptions.InvalidFormatException; | |||
import org.apache.poi.openxml4j.exceptions.InvalidOperationException; | |||
import org.apache.poi.openxml4j.opc.ContentTypes; | |||
import org.apache.poi.openxml4j.opc.Package; | |||
import org.apache.poi.openxml4j.opc.PackagePartName; | |||
import org.apache.poi.openxml4j.opc.PackageRelationshipTypes; | |||
import org.apache.poi.openxml4j.opc.PackagingURIHelper; | |||
import org.apache.poi.openxml4j.opc.TargetMode; | |||
/** | |||
* Test Open Packaging Convention package model compliance. | |||
* | |||
* M1.11 : A package implementer shall neither create nor recognize a part with | |||
* a part name derived from another part name by appending segments to it. | |||
* | |||
* @author Julien Chable | |||
*/ | |||
public class TestOPCCompliancePackageModel extends TestCase { | |||
public TestOPCCompliancePackageModel(String name) { | |||
super(name); | |||
} | |||
/** | |||
* A package implementer shall neither create nor recognize a part with a | |||
* part name derived from another part name by appending segments to it. | |||
* [M1.11] | |||
*/ | |||
public void testPartNameDerivationAdditionFailure() { | |||
Package pkg = Package.create("TODELETEIFEXIST.docx"); | |||
try { | |||
PackagePartName name = PackagingURIHelper | |||
.createPartName("/word/document.xml"); | |||
PackagePartName nameDerived = PackagingURIHelper | |||
.createPartName("/word/document.xml/image1.gif"); | |||
pkg.createPart(name, ContentTypes.XML); | |||
pkg.createPart(nameDerived, ContentTypes.EXTENSION_GIF); | |||
} catch (InvalidOperationException e) { | |||
pkg.revert(); | |||
return; | |||
} catch (InvalidFormatException e) { | |||
fail(e.getMessage()); | |||
} | |||
fail("A package implementer shall neither create nor recognize a part with a" | |||
+ " part name derived from another part name by appending segments to it." | |||
+ " [M1.11]"); | |||
} | |||
/** | |||
* A package implementer shall neither create nor recognize a part with a | |||
* part name derived from another part name by appending segments to it. | |||
* [M1.11] | |||
*/ | |||
public void testPartNameDerivationReadingFailure() { | |||
String filepath = System.getProperty("openxml4j.compliance.input") | |||
+ File.separator + "OPCCompliance_DerivedPartNameFAIL.docx"; | |||
try { | |||
Package.open(filepath); | |||
} catch (InvalidFormatException e) { | |||
return; | |||
} | |||
fail("A package implementer shall neither create nor recognize a part with a" | |||
+ " part name derived from another part name by appending segments to it." | |||
+ " [M1.11]"); | |||
} | |||
/** | |||
* Rule M1.12 : Packages shall not contain equivalent part names and package | |||
* implementers shall neither create nor recognize packages with equivalent | |||
* part names. | |||
*/ | |||
public void testAddPackageAlreadyAddFailure() throws Exception { | |||
Package pkg = Package.create("DELETEIFEXISTS.docx"); | |||
PackagePartName name1 = null; | |||
PackagePartName name2 = null; | |||
try { | |||
name1 = PackagingURIHelper.createPartName("/word/document.xml"); | |||
name2 = PackagingURIHelper.createPartName("/word/document.xml"); | |||
} catch (InvalidFormatException e) { | |||
throw new Exception(e.getMessage()); | |||
} | |||
pkg.createPart(name1, ContentTypes.XML); | |||
try { | |||
pkg.createPart(name2, ContentTypes.XML); | |||
} catch (InvalidOperationException e) { | |||
return; | |||
} | |||
fail("Packages shall not contain equivalent part names and package implementers shall neither create nor recognize packages with equivalent part names. [M1.12]"); | |||
} | |||
/** | |||
* Rule M1.12 : Packages shall not contain equivalent part names and package | |||
* implementers shall neither create nor recognize packages with equivalent | |||
* part names. | |||
*/ | |||
public void testAddPackageAlreadyAddFailure2() throws Exception { | |||
Package pkg = Package.create("DELETEIFEXISTS.docx"); | |||
PackagePartName partName = null; | |||
try { | |||
partName = PackagingURIHelper.createPartName("/word/document.xml"); | |||
} catch (InvalidFormatException e) { | |||
throw new Exception(e.getMessage()); | |||
} | |||
pkg.createPart(partName, ContentTypes.XML); | |||
try { | |||
pkg.createPart(partName, ContentTypes.XML); | |||
} catch (InvalidOperationException e) { | |||
return; | |||
} | |||
fail("Packages shall not contain equivalent part names and package implementers shall neither create nor recognize packages with equivalent part names. [M1.12]"); | |||
} | |||
/** | |||
* Try to add a relationship to a relationship part. | |||
* | |||
* Check rule M1.25: The Relationships part shall not have relationships to | |||
* any other part. Package implementers shall enforce this requirement upon | |||
* the attempt to create such a relationship and shall treat any such | |||
* relationship as invalid. | |||
*/ | |||
public void testAddRelationshipRelationshipsPartFailure() { | |||
Package pkg = Package.create("DELETEIFEXISTS.docx"); | |||
PackagePartName name1 = null; | |||
try { | |||
name1 = PackagingURIHelper | |||
.createPartName("/test/_rels/document.xml.rels"); | |||
} catch (InvalidFormatException e) { | |||
fail("This exception should never happen !"); | |||
} | |||
try { | |||
pkg.addRelationship(name1, TargetMode.INTERNAL, | |||
PackageRelationshipTypes.CORE_DOCUMENT); | |||
} catch (InvalidOperationException e) { | |||
return; | |||
} | |||
fail("Fail test -> M1.25: The Relationships part shall not have relationships to any other part"); | |||
} | |||
} | |||
/* ==================================================================== | |||
Licensed to the Apache Software Foundation (ASF) under one or more | |||
contributor license agreements. See the NOTICE file distributed with | |||
this work for additional information regarding copyright ownership. | |||
The ASF licenses this file to You under the Apache License, Version 2.0 | |||
(the "License"); you may not use this file except in compliance with | |||
the License. You may obtain a copy of the License at | |||
http://www.apache.org/licenses/LICENSE-2.0 | |||
Unless required by applicable law or agreed to in writing, software | |||
distributed under the License is distributed on an "AS IS" BASIS, | |||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||
See the License for the specific language governing permissions and | |||
limitations under the License. | |||
==================================================================== */ | |||
package org.apache.poi.openxml4j.opc.compliance; | |||
import java.io.File; | |||
import junit.framework.TestCase; | |||
import org.apache.poi.openxml4j.exceptions.InvalidFormatException; | |||
import org.apache.poi.openxml4j.exceptions.InvalidOperationException; | |||
import org.apache.poi.openxml4j.opc.ContentTypes; | |||
import org.apache.poi.openxml4j.opc.OPCPackage; | |||
import org.apache.poi.openxml4j.opc.PackagePartName; | |||
import org.apache.poi.openxml4j.opc.PackageRelationshipTypes; | |||
import org.apache.poi.openxml4j.opc.PackagingURIHelper; | |||
import org.apache.poi.openxml4j.opc.TargetMode; | |||
/** | |||
* Test Open Packaging Convention package model compliance. | |||
* | |||
* M1.11 : A package implementer shall neither create nor recognize a part with | |||
* a part name derived from another part name by appending segments to it. | |||
* | |||
* @author Julien Chable | |||
*/ | |||
public class TestOPCCompliancePackageModel extends TestCase { | |||
public TestOPCCompliancePackageModel(String name) { | |||
super(name); | |||
} | |||
/** | |||
* A package implementer shall neither create nor recognize a part with a | |||
* part name derived from another part name by appending segments to it. | |||
* [M1.11] | |||
*/ | |||
public void testPartNameDerivationAdditionFailure() { | |||
OPCPackage pkg = OPCPackage.create("TODELETEIFEXIST.docx"); | |||
try { | |||
PackagePartName name = PackagingURIHelper | |||
.createPartName("/word/document.xml"); | |||
PackagePartName nameDerived = PackagingURIHelper | |||
.createPartName("/word/document.xml/image1.gif"); | |||
pkg.createPart(name, ContentTypes.XML); | |||
pkg.createPart(nameDerived, ContentTypes.EXTENSION_GIF); | |||
} catch (InvalidOperationException e) { | |||
pkg.revert(); | |||
return; | |||
} catch (InvalidFormatException e) { | |||
fail(e.getMessage()); | |||
} | |||
fail("A package implementer shall neither create nor recognize a part with a" | |||
+ " part name derived from another part name by appending segments to it." | |||
+ " [M1.11]"); | |||
} | |||
/** | |||
* A package implementer shall neither create nor recognize a part with a | |||
* part name derived from another part name by appending segments to it. | |||
* [M1.11] | |||
*/ | |||
public void testPartNameDerivationReadingFailure() { | |||
String filepath = System.getProperty("openxml4j.compliance.input") | |||
+ File.separator + "OPCCompliance_DerivedPartNameFAIL.docx"; | |||
try { | |||
OPCPackage.open(filepath); | |||
} catch (InvalidFormatException e) { | |||
return; | |||
} | |||
fail("A package implementer shall neither create nor recognize a part with a" | |||
+ " part name derived from another part name by appending segments to it." | |||
+ " [M1.11]"); | |||
} | |||
/** | |||
* Rule M1.12 : Packages shall not contain equivalent part names and package | |||
* implementers shall neither create nor recognize packages with equivalent | |||
* part names. | |||
*/ | |||
public void testAddPackageAlreadyAddFailure() throws Exception { | |||
OPCPackage pkg = OPCPackage.create("DELETEIFEXISTS.docx"); | |||
PackagePartName name1 = null; | |||
PackagePartName name2 = null; | |||
try { | |||
name1 = PackagingURIHelper.createPartName("/word/document.xml"); | |||
name2 = PackagingURIHelper.createPartName("/word/document.xml"); | |||
} catch (InvalidFormatException e) { | |||
throw new Exception(e.getMessage()); | |||
} | |||
pkg.createPart(name1, ContentTypes.XML); | |||
try { | |||
pkg.createPart(name2, ContentTypes.XML); | |||
} catch (InvalidOperationException e) { | |||
return; | |||
} | |||
fail("Packages shall not contain equivalent part names and package implementers shall neither create nor recognize packages with equivalent part names. [M1.12]"); | |||
} | |||
/** | |||
* Rule M1.12 : Packages shall not contain equivalent part names and package | |||
* implementers shall neither create nor recognize packages with equivalent | |||
* part names. | |||
*/ | |||
public void testAddPackageAlreadyAddFailure2() throws Exception { | |||
OPCPackage pkg = OPCPackage.create("DELETEIFEXISTS.docx"); | |||
PackagePartName partName = null; | |||
try { | |||
partName = PackagingURIHelper.createPartName("/word/document.xml"); | |||
} catch (InvalidFormatException e) { | |||
throw new Exception(e.getMessage()); | |||
} | |||
pkg.createPart(partName, ContentTypes.XML); | |||
try { | |||
pkg.createPart(partName, ContentTypes.XML); | |||
} catch (InvalidOperationException e) { | |||
return; | |||
} | |||
fail("Packages shall not contain equivalent part names and package implementers shall neither create nor recognize packages with equivalent part names. [M1.12]"); | |||
} | |||
/** | |||
* Try to add a relationship to a relationship part. | |||
* | |||
* Check rule M1.25: The Relationships part shall not have relationships to | |||
* any other part. Package implementers shall enforce this requirement upon | |||
* the attempt to create such a relationship and shall treat any such | |||
* relationship as invalid. | |||
*/ | |||
public void testAddRelationshipRelationshipsPartFailure() { | |||
OPCPackage pkg = OPCPackage.create("DELETEIFEXISTS.docx"); | |||
PackagePartName name1 = null; | |||
try { | |||
name1 = PackagingURIHelper | |||
.createPartName("/test/_rels/document.xml.rels"); | |||
} catch (InvalidFormatException e) { | |||
fail("This exception should never happen !"); | |||
} | |||
try { | |||
pkg.addRelationship(name1, TargetMode.INTERNAL, | |||
PackageRelationshipTypes.CORE_DOCUMENT); | |||
} catch (InvalidOperationException e) { | |||
return; | |||
} | |||
fail("Fail test -> M1.25: The Relationships part shall not have relationships to any other part"); | |||
} | |||
} |
@@ -24,7 +24,7 @@ import org.apache.poi.poifs.filesystem.POIFSFileSystem; | |||
import org.apache.poi.ss.usermodel.Workbook; | |||
import org.apache.poi.ss.usermodel.WorkbookFactory; | |||
import org.apache.poi.xssf.usermodel.XSSFWorkbook; | |||
import org.apache.poi.openxml4j.opc.Package; | |||
import org.apache.poi.openxml4j.opc.OPCPackage; | |||
import junit.framework.TestCase; | |||
@@ -63,7 +63,7 @@ public class TestWorkbookFactory extends TestCase { | |||
// Package -> xssf | |||
wb = WorkbookFactory.create( | |||
Package.open(xlsx.toString()) | |||
OPCPackage.open(xlsx.toString()) | |||
); | |||
assertNotNull(wb); | |||
assertTrue(wb instanceof XSSFWorkbook); |
@@ -18,14 +18,14 @@ package org.apache.poi.xslf; | |||
import java.io.File; | |||
import junit.framework.TestCase; | |||
import org.apache.poi.POIXMLDocument; | |||
import org.apache.poi.openxml4j.opc.Package; | |||
import org.apache.poi.openxml4j.opc.OPCPackage; | |||
import org.apache.poi.openxml4j.opc.PackagePart; | |||
import org.openxmlformats.schemas.presentationml.x2006.main.CTSlideIdListEntry; | |||
import org.openxmlformats.schemas.presentationml.x2006.main.CTSlideMasterIdListEntry; | |||
import junit.framework.TestCase; | |||
public class TestXSLFSlideShow extends TestCase { | |||
private String sampleFile; | |||
@@ -39,7 +39,7 @@ public class TestXSLFSlideShow extends TestCase { | |||
} | |||
public void testContainsMainContentType() throws Exception { | |||
Package pack = POIXMLDocument.openPackage(sampleFile); | |||
OPCPackage pack = POIXMLDocument.openPackage(sampleFile); | |||
boolean found = false; | |||
for(PackagePart part : pack.getParts()) { |
@@ -1,75 +1,80 @@ | |||
/* ==================================================================== | |||
Licensed to the Apache Software Foundation (ASF) under one or more | |||
contributor license agreements. See the NOTICE file distributed with | |||
this work for additional information regarding copyright ownership. | |||
The ASF licenses this file to You under the Apache License, Version 2.0 | |||
(the "License"); you may not use this file except in compliance with | |||
the License. You may obtain a copy of the License at | |||
http://www.apache.org/licenses/LICENSE-2.0 | |||
Unless required by applicable law or agreed to in writing, software | |||
distributed under the License is distributed on an "AS IS" BASIS, | |||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||
See the License for the specific language governing permissions and | |||
limitations under the License. | |||
==================================================================== */ | |||
package org.apache.poi.xssf; | |||
import java.io.*; | |||
import org.apache.poi.hssf.HSSFTestDataSamples; | |||
import org.apache.poi.hssf.usermodel.HSSFWorkbook; | |||
import org.apache.poi.ss.usermodel.Workbook; | |||
import org.apache.poi.xssf.usermodel.XSSFWorkbook; | |||
import org.apache.poi.openxml4j.exceptions.InvalidFormatException; | |||
import org.apache.poi.openxml4j.opc.Package; | |||
/** | |||
* Centralises logic for finding/opening sample files in the src/testcases/org/apache/poi/hssf/hssf/data folder. | |||
* | |||
* @author Josh Micich | |||
*/ | |||
public class XSSFTestDataSamples { | |||
public static final XSSFWorkbook openSampleWorkbook(String sampleName) { | |||
InputStream is = HSSFTestDataSamples.openSampleFileStream(sampleName); | |||
try { | |||
Package pkg = Package.open(is); | |||
return new XSSFWorkbook(pkg); | |||
} catch (InvalidFormatException e) { | |||
throw new RuntimeException(e); | |||
} catch (IOException e) { | |||
throw new RuntimeException(e); | |||
} | |||
} | |||
public static <R extends Workbook> R writeOutAndReadBack(R wb) { | |||
Workbook result; | |||
try { | |||
if (wb instanceof HSSFWorkbook) { | |||
ByteArrayOutputStream baos = new ByteArrayOutputStream(8192); | |||
wb.write(baos); | |||
InputStream is = new ByteArrayInputStream(baos.toByteArray()); | |||
result = new HSSFWorkbook(is); | |||
} else if (wb instanceof XSSFWorkbook) { | |||
File tmp = File.createTempFile("poi-ooxml-", ".xlsx"); | |||
tmp.deleteOnExit(); | |||
FileOutputStream out = new FileOutputStream(tmp); | |||
wb.write(out); | |||
out.close(); | |||
Package pkg = Package.open(tmp.getAbsolutePath()); | |||
result = new XSSFWorkbook(pkg); | |||
} else { | |||
throw new RuntimeException("Unexpected workbook type (" | |||
+ wb.getClass().getName() + ")"); | |||
} | |||
} catch (InvalidFormatException e) { | |||
throw new RuntimeException(e); | |||
} catch (IOException e) { | |||
throw new RuntimeException(e); | |||
} | |||
@SuppressWarnings("unchecked") | |||
R r = (R) result; | |||
return r; | |||
} | |||
} | |||
/* ==================================================================== | |||
Licensed to the Apache Software Foundation (ASF) under one or more | |||
contributor license agreements. See the NOTICE file distributed with | |||
this work for additional information regarding copyright ownership. | |||
The ASF licenses this file to You under the Apache License, Version 2.0 | |||
(the "License"); you may not use this file except in compliance with | |||
the License. You may obtain a copy of the License at | |||
http://www.apache.org/licenses/LICENSE-2.0 | |||
Unless required by applicable law or agreed to in writing, software | |||
distributed under the License is distributed on an "AS IS" BASIS, | |||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||
See the License for the specific language governing permissions and | |||
limitations under the License. | |||
==================================================================== */ | |||
package org.apache.poi.xssf; | |||
import java.io.ByteArrayInputStream; | |||
import java.io.ByteArrayOutputStream; | |||
import java.io.File; | |||
import java.io.FileOutputStream; | |||
import java.io.IOException; | |||
import java.io.InputStream; | |||
import org.apache.poi.hssf.HSSFTestDataSamples; | |||
import org.apache.poi.hssf.usermodel.HSSFWorkbook; | |||
import org.apache.poi.openxml4j.exceptions.InvalidFormatException; | |||
import org.apache.poi.openxml4j.opc.OPCPackage; | |||
import org.apache.poi.ss.usermodel.Workbook; | |||
import org.apache.poi.xssf.usermodel.XSSFWorkbook; | |||
/** | |||
* Centralises logic for finding/opening sample files in the src/testcases/org/apache/poi/hssf/hssf/data folder. | |||
* | |||
* @author Josh Micich | |||
*/ | |||
public class XSSFTestDataSamples { | |||
public static final XSSFWorkbook openSampleWorkbook(String sampleName) { | |||
InputStream is = HSSFTestDataSamples.openSampleFileStream(sampleName); | |||
try { | |||
OPCPackage pkg = OPCPackage.open(is); | |||
return new XSSFWorkbook(pkg); | |||
} catch (InvalidFormatException e) { | |||
throw new RuntimeException(e); | |||
} catch (IOException e) { | |||
throw new RuntimeException(e); | |||
} | |||
} | |||
public static <R extends Workbook> R writeOutAndReadBack(R wb) { | |||
Workbook result; | |||
try { | |||
if (wb instanceof HSSFWorkbook) { | |||
ByteArrayOutputStream baos = new ByteArrayOutputStream(8192); | |||
wb.write(baos); | |||
InputStream is = new ByteArrayInputStream(baos.toByteArray()); | |||
result = new HSSFWorkbook(is); | |||
} else if (wb instanceof XSSFWorkbook) { | |||
File tmp = File.createTempFile("poi-ooxml-", ".xlsx"); | |||
tmp.deleteOnExit(); | |||
FileOutputStream out = new FileOutputStream(tmp); | |||
wb.write(out); | |||
out.close(); | |||
OPCPackage pkg = OPCPackage.open(tmp.getAbsolutePath()); | |||
result = new XSSFWorkbook(pkg); | |||
} else { | |||
throw new RuntimeException("Unexpected workbook type (" | |||
+ wb.getClass().getName() + ")"); | |||
} | |||
} catch (InvalidFormatException e) { | |||
throw new RuntimeException(e); | |||
} catch (IOException e) { | |||
throw new RuntimeException(e); | |||
} | |||
@SuppressWarnings("unchecked") | |||
R r = (R) result; | |||
return r; | |||
} | |||
} |
@@ -25,7 +25,7 @@ import junit.framework.TestCase; | |||
import org.apache.poi.util.IOUtils; | |||
import org.apache.poi.xssf.usermodel.XSSFRichTextString; | |||
import org.apache.poi.openxml4j.opc.Package; | |||
import org.apache.poi.openxml4j.opc.OPCPackage; | |||
/** | |||
* Tests for XSSFReader | |||
@@ -49,7 +49,7 @@ public class TestXSSFReader extends TestCase { | |||
public void testGetBits() throws Exception { | |||
File f = new File(dirName, "SampleSS.xlsx"); | |||
Package pkg = Package.open(f.toString()); | |||
OPCPackage pkg = OPCPackage.open(f.toString()); | |||
XSSFReader r = new XSSFReader(pkg); | |||
@@ -63,7 +63,7 @@ public class TestXSSFReader extends TestCase { | |||
public void testStyles() throws Exception { | |||
File f = new File(dirName, "SampleSS.xlsx"); | |||
Package pkg = Package.open(f.toString()); | |||
OPCPackage pkg = OPCPackage.open(f.toString()); | |||
XSSFReader r = new XSSFReader(pkg); | |||
@@ -73,7 +73,7 @@ public class TestXSSFReader extends TestCase { | |||
public void testStrings() throws Exception { | |||
File f = new File(dirName, "SampleSS.xlsx"); | |||
Package pkg = Package.open(f.toString()); | |||
OPCPackage pkg = OPCPackage.open(f.toString()); | |||
XSSFReader r = new XSSFReader(pkg); | |||
@@ -83,7 +83,7 @@ public class TestXSSFReader extends TestCase { | |||
public void testSheets() throws Exception { | |||
File f = new File(dirName, "SampleSS.xlsx"); | |||
Package pkg = Package.open(f.toString()); | |||
OPCPackage pkg = OPCPackage.open(f.toString()); | |||
XSSFReader r = new XSSFReader(pkg); | |||
byte[] data = new byte[4096]; | |||
@@ -116,7 +116,7 @@ public class TestXSSFReader extends TestCase { | |||
*/ | |||
public void testOrderOfSheets() throws Exception { | |||
File f = new File(dirName, "reordered_sheets.xlsx"); | |||
Package pkg = Package.open(f.toString()); | |||
OPCPackage pkg = OPCPackage.open(f.toString()); | |||
XSSFReader r = new XSSFReader(pkg); | |||
@@ -32,7 +32,7 @@ import org.apache.poi.xssf.usermodel.XSSFSheet; | |||
import org.apache.poi.xssf.usermodel.XSSFWorkbook; | |||
import org.apache.poi.xssf.XSSFTestDataSamples; | |||
import org.apache.poi.POIXMLDocumentPart; | |||
import org.apache.poi.openxml4j.opc.Package; | |||
import org.apache.poi.openxml4j.opc.OPCPackage; | |||
import org.openxmlformats.schemas.spreadsheetml.x2006.main.*; | |||
import junit.framework.TestCase; | |||
@@ -125,7 +125,7 @@ public class TestCommentsTable extends TestCase { | |||
); | |||
assertTrue(xml.exists()); | |||
Package pkg = Package.open(xml.toString()); | |||
OPCPackage pkg = OPCPackage.open(xml.toString()); | |||
XSSFWorkbook wb = new XSSFWorkbook(pkg); | |||
List<POIXMLDocumentPart> rels = wb.getSheetAt(0).getRelations(); | |||
CommentsTable ct = null; |
@@ -32,7 +32,7 @@ import org.apache.poi.ss.usermodel.CellValue; | |||
import org.apache.poi.ss.usermodel.FormulaEvaluator; | |||
import org.apache.poi.ss.usermodel.Row; | |||
import org.apache.poi.ss.usermodel.Sheet; | |||
import org.apache.poi.openxml4j.opc.Package; | |||
import org.apache.poi.openxml4j.opc.OPCPackage; | |||
/** | |||
* Performs much the same role as {@link TestFormulasFromSpreadsheet}, | |||
@@ -149,7 +149,7 @@ public final class TestFormulaEvaluatorOnXSSF extends TestCase { | |||
protected void setUp() throws Exception { | |||
if (workbook == null) { | |||
InputStream is = HSSFTestDataSamples.openSampleFileStream(SS.FILENAME); | |||
Package pkg = Package.open(is); | |||
OPCPackage pkg = OPCPackage.open(is); | |||
workbook = new XSSFWorkbook( pkg ); | |||
sheet = workbook.getSheetAt( 0 ); | |||
} |
@@ -21,7 +21,8 @@ import java.io.File; | |||
import junit.framework.TestCase; | |||
import org.apache.poi.openxml4j.opc.Package; | |||
import org.apache.poi.openxml4j.opc.OPCPackage; | |||
import org.apache.poi.openxml4j.opc.OPCPackage; | |||
import org.apache.poi.openxml4j.opc.PackagePart; | |||
import org.apache.poi.openxml4j.opc.PackagingURIHelper; | |||
import org.apache.poi.xssf.XSSFTestDataSamples; | |||
@@ -71,7 +72,7 @@ public class TestXSSFBugs extends TestCase { | |||
* We should carry vba macros over after save | |||
*/ | |||
public void test45431() throws Exception { | |||
Package pkg = Package.open(getFilePath("45431.xlsm")); | |||
OPCPackage pkg = OPCPackage.open(getFilePath("45431.xlsm")); | |||
XSSFWorkbook wb = new XSSFWorkbook(pkg); | |||
assertTrue(wb.isMacroEnabled()); | |||
@@ -89,7 +90,7 @@ public class TestXSSFBugs extends TestCase { | |||
// Save and re-open, both still there | |||
XSSFWorkbook nwb = XSSFTestDataSamples.writeOutAndReadBack(wb); | |||
Package nPkg = nwb.getPackage(); | |||
OPCPackage nPkg = nwb.getPackage(); | |||
assertTrue(nwb.isMacroEnabled()); | |||
vba = nPkg.getPart( |
@@ -1,77 +1,79 @@ | |||
/* ==================================================================== | |||
Licensed to the Apache Software Foundation (ASF) under one or more | |||
contributor license agreements. See the NOTICE file distributed with | |||
this work for additional information regarding copyright ownership. | |||
The ASF licenses this file to You under the Apache License, Version 2.0 | |||
(the "License"); you may not use this file except in compliance with | |||
the License. You may obtain a copy of the License at | |||
http://www.apache.org/licenses/LICENSE-2.0 | |||
Unless required by applicable law or agreed to in writing, software | |||
distributed under the License is distributed on an "AS IS" BASIS, | |||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||
See the License for the specific language governing permissions and | |||
limitations under the License. | |||
==================================================================== */ | |||
package org.apache.poi.xssf.usermodel; | |||
import junit.framework.TestCase; | |||
import org.apache.poi.xssf.XSSFTestDataSamples; | |||
import org.apache.poi.POIXMLDocumentPart; | |||
import java.util.List; | |||
/** | |||
* @author Yegor Kozlov | |||
*/ | |||
public class TestXSSFDrawing extends TestCase { | |||
public void testRead(){ | |||
XSSFWorkbook wb = XSSFTestDataSamples.openSampleWorkbook("WithDrawing.xlsx"); | |||
XSSFSheet sheet = wb.getSheetAt(0); | |||
//the sheet has one relationship and it is XSSFDrawing | |||
List<POIXMLDocumentPart> rels = sheet.getRelations(); | |||
assertEquals(1, rels.size()); | |||
assertTrue(rels.get(0) instanceof XSSFDrawing); | |||
XSSFDrawing drawing = (XSSFDrawing)rels.get(0); | |||
//sheet.createDrawingPatriarch() should return the same instance of XSSFDrawing | |||
assertSame(drawing, sheet.createDrawingPatriarch()); | |||
String drawingId = drawing.getPackageRelationship().getId(); | |||
//there should be a relation to this drawing in the worksheet | |||
assertTrue(sheet.getCTWorksheet().isSetDrawing()); | |||
assertEquals(drawingId, sheet.getCTWorksheet().getDrawing().getId()); | |||
} | |||
public void testNew(){ | |||
XSSFWorkbook wb = new XSSFWorkbook(); | |||
XSSFSheet sheet = wb.createSheet(); | |||
//multiple calls of createDrawingPatriarch should return the same instance of XSSFDrawing | |||
XSSFDrawing dr1 = sheet.createDrawingPatriarch(); | |||
XSSFDrawing dr2 = sheet.createDrawingPatriarch(); | |||
assertSame(dr1, dr2); | |||
List<POIXMLDocumentPart> rels = sheet.getRelations(); | |||
assertEquals(1, rels.size()); | |||
assertTrue(rels.get(0) instanceof XSSFDrawing); | |||
XSSFDrawing drawing = (XSSFDrawing)rels.get(0); | |||
String drawingId = drawing.getPackageRelationship().getId(); | |||
//there should be a relation to this drawing in the worksheet | |||
assertTrue(sheet.getCTWorksheet().isSetDrawing()); | |||
assertEquals(drawingId, sheet.getCTWorksheet().getDrawing().getId()); | |||
} | |||
public void testMultipleDrawings(){ | |||
XSSFWorkbook wb = new XSSFWorkbook(); | |||
for (int i = 0; i < 3; i++) { | |||
XSSFSheet sheet = wb.createSheet(); | |||
XSSFDrawing drawing = sheet.createDrawingPatriarch(); | |||
} | |||
org.apache.poi.openxml4j.opc.Package pkg = wb.getPackage(); | |||
assertEquals(3, pkg.getPartsByContentType(XSSFRelation.DRAWINGS.getContentType()).size()); | |||
} | |||
} | |||
/* ==================================================================== | |||
Licensed to the Apache Software Foundation (ASF) under one or more | |||
contributor license agreements. See the NOTICE file distributed with | |||
this work for additional information regarding copyright ownership. | |||
The ASF licenses this file to You under the Apache License, Version 2.0 | |||
(the "License"); you may not use this file except in compliance with | |||
the License. You may obtain a copy of the License at | |||
http://www.apache.org/licenses/LICENSE-2.0 | |||
Unless required by applicable law or agreed to in writing, software | |||
distributed under the License is distributed on an "AS IS" BASIS, | |||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||
See the License for the specific language governing permissions and | |||
limitations under the License. | |||
==================================================================== */ | |||
package org.apache.poi.xssf.usermodel; | |||
import java.util.List; | |||
import junit.framework.TestCase; | |||
import org.apache.poi.POIXMLDocumentPart; | |||
import org.apache.poi.openxml4j.opc.OPCPackage; | |||
import org.apache.poi.xssf.XSSFTestDataSamples; | |||
/** | |||
* @author Yegor Kozlov | |||
*/ | |||
public class TestXSSFDrawing extends TestCase { | |||
public void testRead(){ | |||
XSSFWorkbook wb = XSSFTestDataSamples.openSampleWorkbook("WithDrawing.xlsx"); | |||
XSSFSheet sheet = wb.getSheetAt(0); | |||
//the sheet has one relationship and it is XSSFDrawing | |||
List<POIXMLDocumentPart> rels = sheet.getRelations(); | |||
assertEquals(1, rels.size()); | |||
assertTrue(rels.get(0) instanceof XSSFDrawing); | |||
XSSFDrawing drawing = (XSSFDrawing)rels.get(0); | |||
//sheet.createDrawingPatriarch() should return the same instance of XSSFDrawing | |||
assertSame(drawing, sheet.createDrawingPatriarch()); | |||
String drawingId = drawing.getPackageRelationship().getId(); | |||
//there should be a relation to this drawing in the worksheet | |||
assertTrue(sheet.getCTWorksheet().isSetDrawing()); | |||
assertEquals(drawingId, sheet.getCTWorksheet().getDrawing().getId()); | |||
} | |||
public void testNew(){ | |||
XSSFWorkbook wb = new XSSFWorkbook(); | |||
XSSFSheet sheet = wb.createSheet(); | |||
//multiple calls of createDrawingPatriarch should return the same instance of XSSFDrawing | |||
XSSFDrawing dr1 = sheet.createDrawingPatriarch(); | |||
XSSFDrawing dr2 = sheet.createDrawingPatriarch(); | |||
assertSame(dr1, dr2); | |||
List<POIXMLDocumentPart> rels = sheet.getRelations(); | |||
assertEquals(1, rels.size()); | |||
assertTrue(rels.get(0) instanceof XSSFDrawing); | |||
XSSFDrawing drawing = (XSSFDrawing)rels.get(0); | |||
String drawingId = drawing.getPackageRelationship().getId(); | |||
//there should be a relation to this drawing in the worksheet | |||
assertTrue(sheet.getCTWorksheet().isSetDrawing()); | |||
assertEquals(drawingId, sheet.getCTWorksheet().getDrawing().getId()); | |||
} | |||
public void testMultipleDrawings(){ | |||
XSSFWorkbook wb = new XSSFWorkbook(); | |||
for (int i = 0; i < 3; i++) { | |||
XSSFSheet sheet = wb.createSheet(); | |||
XSSFDrawing drawing = sheet.createDrawingPatriarch(); | |||
} | |||
OPCPackage pkg = wb.getPackage(); | |||
assertEquals(3, pkg.getPartsByContentType(XSSFRelation.DRAWINGS.getContentType()).size()); | |||
} | |||
} |
@@ -29,7 +29,7 @@ import org.apache.poi.ss.util.CellRangeAddress; | |||
import org.apache.poi.xssf.XSSFTestDataSamples; | |||
import org.apache.poi.xssf.model.StylesTable; | |||
import org.apache.poi.openxml4j.opc.ContentTypes; | |||
import org.apache.poi.openxml4j.opc.Package; | |||
import org.apache.poi.openxml4j.opc.OPCPackage; | |||
import org.apache.poi.openxml4j.opc.PackagePart; | |||
import org.apache.poi.openxml4j.opc.PackagingURIHelper; | |||
import org.openxmlformats.schemas.spreadsheetml.x2006.main.CTSheet; | |||
@@ -251,7 +251,7 @@ public final class TestXSSFWorkbook extends TestCase { | |||
out.close(); | |||
// Check the package contains what we'd expect it to | |||
Package pkg = Package.open(file.toString()); | |||
OPCPackage pkg = OPCPackage.open(file.toString()); | |||
PackagePart wbRelPart = | |||
pkg.getPart(PackagingURIHelper.createPartName("/xl/_rels/workbook.xml.rels")); | |||
assertNotNull(wbRelPart); | |||
@@ -293,7 +293,7 @@ public final class TestXSSFWorkbook extends TestCase { | |||
assertNotNull(workbook.getStylesSource()); | |||
// And check a few low level bits too | |||
Package pkg = Package.open(HSSFTestDataSamples.openSampleFileStream("Formatting.xlsx")); | |||
OPCPackage pkg = OPCPackage.open(HSSFTestDataSamples.openSampleFileStream("Formatting.xlsx")); | |||
PackagePart wbPart = | |||
pkg.getPart(PackagingURIHelper.createPartName("/xl/workbook.xml")); | |||
@@ -18,13 +18,13 @@ package org.apache.poi.xwpf; | |||
import java.io.File; | |||
import junit.framework.TestCase; | |||
import org.apache.poi.POIXMLDocument; | |||
import org.apache.poi.openxml4j.opc.OPCPackage; | |||
import org.apache.poi.openxml4j.opc.PackagePart; | |||
import org.apache.poi.xwpf.usermodel.XWPFDocument; | |||
import org.apache.poi.xwpf.usermodel.XWPFRelation; | |||
import org.apache.poi.openxml4j.opc.Package; | |||
import org.apache.poi.openxml4j.opc.PackagePart; | |||
import junit.framework.TestCase; | |||
public class TestXWPFDocument extends TestCase { | |||
private File sampleFile; | |||
@@ -47,7 +47,7 @@ public class TestXWPFDocument extends TestCase { | |||
} | |||
public void testContainsMainContentType() throws Exception { | |||
Package pack = POIXMLDocument.openPackage(sampleFile.toString()); | |||
OPCPackage pack = POIXMLDocument.openPackage(sampleFile.toString()); | |||
boolean found = false; | |||
for(PackagePart part : pack.getParts()) { |