allow sheet names longer than 31 chars in XSSF, enforce name uniqueness on the first 31 chars
git-svn-id: https://svn.apache.org/repos/asf/poi/trunk@993246 13f79535-47bb-0310-9956-ffa450edef68
This commit is contained in:
parent
d55edf3f78
commit
05593e6902
@ -34,6 +34,7 @@
|
||||
|
||||
<changes>
|
||||
<release version="3.7-beta3" date="2010-??-??">
|
||||
<action dev="poi-developers" type="fix">49887 - allow sheet names longer than 31 chars in XSSF, enforce name uniqueness on the first 31 chars</action>
|
||||
<action dev="poi-developers" type="fix">49878 - improved API for hiding sheets</action>
|
||||
<action dev="poi-developers" type="fix">49875 - fixed XSSFWorkbook.createSheet to throw exception if sheet name begins or ends with a single quote (')</action>
|
||||
<action dev="poi-developers" type="fix">49873 - fixed XSSFFormulaEvaluator to support blank cells</action>
|
||||
|
@ -89,6 +89,12 @@ public class XSSFWorkbook extends POIXMLDocument implements Workbook, Iterable<X
|
||||
*/
|
||||
public static final float DEFAULT_CHARACTER_WIDTH = 7.0017f;
|
||||
|
||||
/**
|
||||
* Excel silently truncates long sheet names to 31 chars.
|
||||
* This constant is used to ensure uniqueness in the first 31 chars
|
||||
*/
|
||||
private static final int MAX_SENSITIVE_SHEET_NAME_LEN = 31;
|
||||
|
||||
/**
|
||||
* The underlying XML bean
|
||||
*/
|
||||
@ -1216,6 +1222,7 @@ public class XSSFWorkbook extends POIXMLDocument implements Workbook, Iterable<X
|
||||
|
||||
/**
|
||||
* Determines whether a workbook contains the provided sheet name.
|
||||
* For the purpose of comparison, long names are truncated to 31 chars.
|
||||
*
|
||||
* @param name the name to test (case insensitive match)
|
||||
* @param excludeSheetIdx the sheet to exclude from the check or -1 to include all sheets in the check.
|
||||
@ -1225,8 +1232,17 @@ public class XSSFWorkbook extends POIXMLDocument implements Workbook, Iterable<X
|
||||
CTSheet[] ctSheetArray = new CTSheet[workbook.getSheets().getSheetList().size()];
|
||||
workbook.getSheets().getSheetList().toArray(ctSheetArray);
|
||||
|
||||
if (name.length() > MAX_SENSITIVE_SHEET_NAME_LEN) {
|
||||
name = name.substring(0, MAX_SENSITIVE_SHEET_NAME_LEN);
|
||||
}
|
||||
|
||||
for (int i = 0; i < ctSheetArray.length; i++) {
|
||||
if (excludeSheetIdx != i && name.equalsIgnoreCase(ctSheetArray[i].getName()))
|
||||
String ctName = ctSheetArray[i].getName();
|
||||
if (ctName.length() > MAX_SENSITIVE_SHEET_NAME_LEN) {
|
||||
ctName = ctName.substring(0, MAX_SENSITIVE_SHEET_NAME_LEN);
|
||||
}
|
||||
|
||||
if (excludeSheetIdx != i && name.equalsIgnoreCase(ctName))
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
|
@ -114,6 +114,44 @@ public abstract class BaseTestWorkbook extends TestCase {
|
||||
assertEquals(2, wb.getSheetIndex("I changed!"));
|
||||
}
|
||||
|
||||
/**
|
||||
* POI allows creating sheets with names longer than 31 characters.
|
||||
*
|
||||
* Excel opens files with long sheet names without error or warning.
|
||||
* However, long sheet names are silently truncated to 31 chars. In order to
|
||||
* avoid funny duplicate sheet name errors, POI enforces uniqueness on only the first 31 chars.
|
||||
* but for the purpose of uniqueness long sheet names are silently truncated to 31 chars.
|
||||
*/
|
||||
public final void testCreateSheetWithLongNames() {
|
||||
Workbook wb = _testDataProvider.createWorkbook();
|
||||
|
||||
String sheetName1 = "My very long sheet name which is longer than 31 chars";
|
||||
Sheet sh1 = wb.createSheet(sheetName1);
|
||||
assertEquals(sheetName1, sh1.getSheetName());
|
||||
assertSame(sh1, wb.getSheet(sheetName1));
|
||||
|
||||
String sheetName2 = "My very long sheet name which is longer than 31 chars " +
|
||||
"and sheetName2.substring(0, 31) == sheetName1.substring(0, 31)";
|
||||
try {
|
||||
Sheet sh2 = wb.createSheet(sheetName2);
|
||||
fail("expected exception");
|
||||
} catch (IllegalArgumentException e) {
|
||||
// expected during successful test
|
||||
assertEquals("The workbook already contains a sheet of this name", e.getMessage());
|
||||
}
|
||||
|
||||
String sheetName3 = "POI allows creating sheets with names longer than 31 characters";
|
||||
Sheet sh3 = wb.createSheet(sheetName3);
|
||||
assertEquals(sheetName3, sh3.getSheetName());
|
||||
assertSame(sh3, wb.getSheet(sheetName3));
|
||||
|
||||
//serialize and read again
|
||||
wb = _testDataProvider.writeOutAndReadBack(wb);
|
||||
assertEquals(2, wb.getNumberOfSheets());
|
||||
assertEquals(0, wb.getSheetIndex(sheetName1));
|
||||
assertEquals(1, wb.getSheetIndex(sheetName3));
|
||||
}
|
||||
|
||||
public final void testRemoveSheetAt() {
|
||||
Workbook workbook = _testDataProvider.createWorkbook();
|
||||
workbook.createSheet("sheet1");
|
||||
|
Loading…
Reference in New Issue
Block a user