Start to tidy up the model loading, to reduce duplicated code, and make it cleaner

git-svn-id: https://svn.apache.org/repos/asf/poi/branches/ooxml@637680 13f79535-47bb-0310-9956-ffa450edef68
This commit is contained in:
Nick Burch 2008-03-16 22:44:10 +00:00
parent 7cec45a438
commit fe2cd2d286
7 changed files with 151 additions and 24 deletions

View File

@ -17,6 +17,8 @@
package org.apache.poi.ss.usermodel;
import java.io.IOException;
/**
* Allows the getting and saving of shared strings
*/
@ -37,4 +39,9 @@ public interface SharedStringSource {
* @return The 0-based position of the newly added string.
*/
public int putSharedString(String s);
/**
* Write back out
*/
public void save() throws IOException;
}

View File

@ -16,7 +16,14 @@
==================================================================== */
package org.apache.poi.ss.usermodel;
import java.io.IOException;
public interface StylesSource {
public String getNumberFormatAt(long idx);
public long putNumberFormat(String fmt);
/**
* Write back out
*/
public void save() throws IOException;
}

View File

@ -40,7 +40,7 @@ import org.openxmlformats.schemas.spreadsheetml.x2006.main.SstDocument;
*
* @version $Id$
*/
public class SharedStringsTable implements SharedStringSource {
public class SharedStringsTable implements SharedStringSource, XSSFModel {
private final LinkedList<String> strings = new LinkedList<String>();

View File

@ -46,7 +46,7 @@ import org.openxmlformats.schemas.spreadsheetml.x2006.main.StyleSheetDocument;;
*
* @version $Id: SharedStringsTable.java 612495 2008-01-16 16:08:22Z ugo $
*/
public class StylesTable implements StylesSource {
public class StylesTable implements StylesSource, XSSFModel {
private final Hashtable<Long,String> numberFormats = new Hashtable<Long,String>();
private final LinkedList<CTFont> fonts = new LinkedList<CTFont>();
private final LinkedList<CTFill> fills = new LinkedList<CTFill>();
@ -99,6 +99,10 @@ public class StylesTable implements StylesSource {
}
}
// ===========================================================
// Start of style related getters and setters
// ===========================================================
public String getNumberFormatAt(long idx) {
return numberFormats.get(idx);
}

View File

@ -0,0 +1,26 @@
/* ====================================================================
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.model;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
public interface XSSFModel {
public void readFrom(InputStream is) throws IOException;
public void writeTo(OutputStream out) throws IOException;
}

View File

@ -41,6 +41,7 @@ import org.apache.poi.util.POILogFactory;
import org.apache.poi.util.POILogger;
import org.apache.poi.xssf.model.SharedStringsTable;
import org.apache.poi.xssf.model.StylesTable;
import org.apache.poi.xssf.model.XSSFModel;
import org.apache.xmlbeans.XmlException;
import org.apache.xmlbeans.XmlObject;
import org.apache.xmlbeans.XmlOptions;
@ -64,18 +65,52 @@ import org.openxmlformats.schemas.spreadsheetml.x2006.main.WorksheetDocument;
public class XSSFWorkbook extends POIXMLDocument implements Workbook {
private static final String WORKSHEET_TYPE = "application/vnd.openxmlformats-officedocument.spreadsheetml.worksheet+xml";
private static final String WORKSHEET_RELATIONSHIP = "http://schemas.openxmlformats.org/officeDocument/2006/relationships/worksheet";
private static final String SHARED_STRINGS_RELATIONSHIP = "http://schemas.openxmlformats.org/officeDocument/2006/relationships/sharedStrings";
private static final String STYLES_RELATIONSHIP = "http://schemas.openxmlformats.org/officeDocument/2006/relationships/styles";
private static final String DRAWING_RELATIONSHIP = "http://schemas.openxmlformats.org/officeDocument/2006/relationships/drawing";
private static final String IMAGE_RELATIONSHIP = "http://schemas.openxmlformats.org/officeDocument/2006/relationships/image";
public static class XSSFRelation {
private String TYPE;
private String REL;
private String DEFAULT_NAME;
private Class<? extends XSSFModel> CLASS;
private XSSFRelation(String TYPE, String REL, String DEFAULT_NAME, Class<? extends XSSFModel> CLASS) {
this.TYPE = TYPE;
this.REL = REL;
this.DEFAULT_NAME = DEFAULT_NAME;
this.CLASS = CLASS;
}
public String getContentType() { return TYPE; }
public String getRelation() { return REL; }
public String getDefaultFileName() { return DEFAULT_NAME; }
}
public static final XSSFRelation WORKSHEET = new XSSFRelation(
"application/vnd.openxmlformats-officedocument.spreadsheetml.worksheet+xml",
"http://schemas.openxmlformats.org/officeDocument/2006/relationships/worksheet",
"/xl/worksheets/sheet#.xml",
null
);
public static final XSSFRelation SHARED_STRINGS = new XSSFRelation(
"application/vnd.openxmlformats-officedocument.spreadsheetml.sharedStrings+xml",
"http://schemas.openxmlformats.org/officeDocument/2006/relationships/sharedStrings",
"/xl/sharedStrings.xml",
SharedStringsTable.class
);
public static final XSSFRelation STYLES = new XSSFRelation(
"application/vnd.openxmlformats-officedocument.spreadsheetml.styles+xml",
"http://schemas.openxmlformats.org/officeDocument/2006/relationships/styles",
"/xl/styles.xml",
StylesTable.class
);
public static final XSSFRelation DRAWINGS = new XSSFRelation(
"application/vnd.openxmlformats-officedocument.drawingml.chart+xml",
"http://schemas.openxmlformats.org/officeDocument/2006/relationships/drawing",
"/xl/drawings/drawing#.xml",
null
);
public static final XSSFRelation IMAGES = new XSSFRelation(
null, // TODO
"http://schemas.openxmlformats.org/officeDocument/2006/relationships/image",
"/xl/image#.xml",
null
);
private CTWorkbook workbook;
@ -107,20 +142,24 @@ public class XSSFWorkbook extends POIXMLDocument implements Workbook {
Iterator<PackageRelationship> it;
// Load shared strings
prc = getCorePart().getRelationshipsByType(SHARED_STRINGS_RELATIONSHIP);
prc = getCorePart().getRelationshipsByType(SHARED_STRINGS.getRelation());
it = prc.iterator();
if (it.hasNext()) {
PackageRelationship rel = it.next();
PackagePart part = getTargetPart(rel);
this.sharedStringSource = new SharedStringsTable(part);
} else {
log.log(POILogger.WARN, "No shared strings part found");
}
// Load styles source
prc = getCorePart().getRelationshipsByType(STYLES_RELATIONSHIP);
prc = getCorePart().getRelationshipsByType(STYLES.getRelation());
it = prc.iterator();
if (it.hasNext()) {
PackageRelationship rel = it.next();
PackagePart part = getTargetPart(rel);
this.stylesSource = new StylesTable(part);
} else {
log.log(POILogger.WARN, "No styles part found");
}
// Load individual sheets
@ -276,10 +315,10 @@ public class XSSFWorkbook extends POIXMLDocument implements Workbook {
if (sheetPart == null) {
continue;
}
PackageRelationshipCollection prc = sheetPart.getRelationshipsByType(DRAWING_RELATIONSHIP);
PackageRelationshipCollection prc = sheetPart.getRelationshipsByType(DRAWINGS.getRelation());
for (PackageRelationship rel : prc) {
PackagePart drawingPart = getTargetPart(rel);
PackageRelationshipCollection prc2 = drawingPart.getRelationshipsByType(IMAGE_RELATIONSHIP);
PackageRelationshipCollection prc2 = drawingPart.getRelationshipsByType(IMAGES.getRelation());
for (PackageRelationship rel2 : prc2) {
PackagePart imagePart = getTargetPart(rel2);
XSSFPictureData pd = new XSSFPictureData(imagePart);
@ -519,8 +558,8 @@ public class XSSFWorkbook extends POIXMLDocument implements Workbook {
for (int i = 0 ; i < this.getNumberOfSheets() ; ++i) {
XSSFSheet sheet = (XSSFSheet) this.getSheetAt(i);
PackagePartName partName = PackagingURIHelper.createPartName("/xl/worksheets/sheet" + i + ".xml");
corePart.addRelationship(partName, TargetMode.INTERNAL, WORKSHEET_RELATIONSHIP, "rSheet" + 1);
PackagePart part = pkg.createPart(partName, WORKSHEET_TYPE);
corePart.addRelationship(partName, TargetMode.INTERNAL, WORKSHEET.getRelation(), "rSheet" + 1);
PackagePart part = pkg.createPart(partName, WORKSHEET.getContentType());
// XXX This should not be needed, but apparently the setSaveOuter call above does not work in XMLBeans 2.2
xmlOptions.setSaveSyntheticDocumentElement(new QName(CTWorksheet.type.getName().getNamespaceURI(), "worksheet"));
@ -530,11 +569,28 @@ public class XSSFWorkbook extends POIXMLDocument implements Workbook {
out.close();
}
// TODO - shared strings source
// TODO - styles source
// Write shared strings and styles
if(sharedStringSource != null) {
SharedStringsTable sst = (SharedStringsTable)sharedStringSource;
PackagePartName sstName = PackagingURIHelper.createPartName(SHARED_STRINGS.getDefaultFileName());
corePart.addRelationship(sstName, TargetMode.INTERNAL, SHARED_STRINGS.getRelation());
PackagePart sstPart = pkg.createPart(sstName, SHARED_STRINGS.getContentType());
out = sstPart.getOutputStream();
sst.writeTo(out);
out.close();
}
if(stylesSource != null) {
StylesTable st = (StylesTable)stylesSource;
PackagePartName stName = PackagingURIHelper.createPartName(STYLES.getDefaultFileName());
corePart.addRelationship(stName, TargetMode.INTERNAL, STYLES.getRelation());
PackagePart stPart = pkg.createPart(stName, STYLES.getContentType());
out = stPart.getOutputStream();
st.writeTo(out);
out.close();
}
// All done
pkg.close();
} catch (InvalidFormatException e) {
// TODO: replace with more meaningful exception
throw new RuntimeException(e);

View File

@ -145,6 +145,33 @@ public class TestXSSFWorkbook extends TestCase {
assertNotNull(workbook.getStylesSource());
}
public void testLoadSave() throws Exception {
File xml = new File(
System.getProperty("HSSF.testdata.path") +
File.separator + "Formatting.xlsx"
);
assertTrue(xml.exists());
XSSFWorkbook workbook = new XSSFWorkbook(xml.toString());
assertEquals(3, workbook.getNumberOfSheets());
assertEquals("dd/mm/yyyy", workbook.getSheetAt(0).getRow(1).getCell(0).getRichStringCellValue().getString());
assertNotNull(workbook.getSharedStringSource());
assertNotNull(workbook.getStylesSource());
// Write out, and check
File tmpFile = File.createTempFile("poi-tmp", ".xlsx");
workbook.write(new FileOutputStream(tmpFile));
// Load up again, check all still there
XSSFWorkbook wb2 = new XSSFWorkbook(tmpFile.toString());
assertEquals(3, wb2.getNumberOfSheets());
// TODO - fix these!
assertEquals("dd/mm/yyyy", wb2.getSheetAt(0).getRow(1).getCell(0).getRichStringCellValue().getString());
assertNotNull(wb2.getSharedStringSource());
assertNotNull(wb2.getStylesSource());
}
public void testStyles() throws Exception {
File xml = new File(
System.getProperty("HSSF.testdata.path") +