Fix bug #56502 - When shifting XSSF rows with formula cells, if the formula can't be parsed, log + leave it unchanged rather than failing
git-svn-id: https://svn.apache.org/repos/asf/poi/trunk@1614916 13f79535-47bb-0310-9956-ffa450edef68
This commit is contained in:
parent
5f5d8f496e
commit
4bfe3c6784
@ -20,6 +20,7 @@ package org.apache.poi.xssf.usermodel.helpers;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
import org.apache.poi.ss.formula.FormulaParseException;
|
||||
import org.apache.poi.ss.formula.FormulaParser;
|
||||
import org.apache.poi.ss.formula.FormulaRenderer;
|
||||
import org.apache.poi.ss.formula.FormulaShifter;
|
||||
@ -30,6 +31,8 @@ import org.apache.poi.ss.formula.ptg.Ptg;
|
||||
import org.apache.poi.ss.usermodel.Cell;
|
||||
import org.apache.poi.ss.usermodel.Row;
|
||||
import org.apache.poi.ss.util.CellRangeAddress;
|
||||
import org.apache.poi.util.POILogFactory;
|
||||
import org.apache.poi.util.POILogger;
|
||||
import org.apache.poi.xssf.usermodel.XSSFCell;
|
||||
import org.apache.poi.xssf.usermodel.XSSFEvaluationWorkbook;
|
||||
import org.apache.poi.xssf.usermodel.XSSFName;
|
||||
@ -43,9 +46,10 @@ import org.openxmlformats.schemas.spreadsheetml.x2006.main.CTConditionalFormatti
|
||||
import org.openxmlformats.schemas.spreadsheetml.x2006.main.STCellFormulaType;
|
||||
|
||||
/**
|
||||
* @author Yegor Kozlov
|
||||
* Helper for shifting rows up or down
|
||||
*/
|
||||
public final class XSSFRowShifter {
|
||||
private static POILogger logger = POILogFactory.getLogger(XSSFRowShifter.class);
|
||||
private final XSSFSheet sheet;
|
||||
|
||||
public XSSFRowShifter(XSSFSheet sh) {
|
||||
@ -194,12 +198,19 @@ public final class XSSFRowShifter {
|
||||
XSSFWorkbook wb = sheet.getWorkbook();
|
||||
int sheetIndex = wb.getSheetIndex(sheet);
|
||||
XSSFEvaluationWorkbook fpb = XSSFEvaluationWorkbook.create(wb);
|
||||
Ptg[] ptgs = FormulaParser.parse(formula, fpb, FormulaType.CELL, sheetIndex);
|
||||
String shiftedFmla = null;
|
||||
if (shifter.adjustFormula(ptgs, sheetIndex)) {
|
||||
shiftedFmla = FormulaRenderer.toFormulaString(fpb, ptgs);
|
||||
|
||||
try {
|
||||
Ptg[] ptgs = FormulaParser.parse(formula, fpb, FormulaType.CELL, sheetIndex);
|
||||
String shiftedFmla = null;
|
||||
if (shifter.adjustFormula(ptgs, sheetIndex)) {
|
||||
shiftedFmla = FormulaRenderer.toFormulaString(fpb, ptgs);
|
||||
}
|
||||
return shiftedFmla;
|
||||
} catch (FormulaParseException fpe) {
|
||||
// Log, but don't change, rather than breaking
|
||||
logger.log(POILogger.WARN, "Error shifting formula on row ", row.getRowNum(), fpe);
|
||||
return formula;
|
||||
}
|
||||
return shiftedFmla;
|
||||
}
|
||||
|
||||
public void updateConditionalFormatting(FormulaShifter shifter) {
|
||||
|
@ -1787,6 +1787,10 @@ public final class TestXSSFBugs extends BaseTestBugzillaIssues {
|
||||
checkValue(excel, eval.getStringValue() + ".0");
|
||||
}
|
||||
|
||||
/**
|
||||
* New hyperlink with no initial cell reference, still need
|
||||
* to be able to change it
|
||||
*/
|
||||
@Test
|
||||
public void testBug56527() {
|
||||
XSSFWorkbook wb = new XSSFWorkbook();
|
||||
@ -1816,6 +1820,30 @@ public final class TestXSSFBugs extends BaseTestBugzillaIssues {
|
||||
assertEquals(5, hyperlink.getLastRow());
|
||||
assertEquals(3, hyperlink.getLastColumn());
|
||||
}
|
||||
|
||||
/**
|
||||
* Shifting rows with a formula that references a
|
||||
* function in another file
|
||||
*/
|
||||
@Test
|
||||
public void bug56502() throws Exception {
|
||||
Workbook wb = XSSFTestDataSamples.openSampleWorkbook("56502.xlsx");
|
||||
Sheet sheet = wb.getSheetAt(0);
|
||||
|
||||
Cell cFunc = sheet.getRow(3).getCell(0);
|
||||
assertEquals("[1]!LUCANET(\"Ist\")", cFunc.getCellFormula());
|
||||
Cell cRef = sheet.getRow(3).createCell(1);
|
||||
cRef.setCellFormula("A3");
|
||||
|
||||
// Shift it down one row
|
||||
sheet.shiftRows(1, sheet.getLastRowNum(), 1);
|
||||
|
||||
// Check the new formulas: Function won't change, Reference will
|
||||
cFunc = sheet.getRow(4).getCell(0);
|
||||
assertEquals("[1]!LUCANET(\"Ist\")", cFunc.getCellFormula());
|
||||
cRef = sheet.getRow(4).getCell(1);
|
||||
assertEquals("A4", cRef.getCellFormula());
|
||||
}
|
||||
|
||||
private void checkValue(XSSFWorkbook excel, String expect) {
|
||||
XSSFFormulaEvaluator evaluator = new XSSFFormulaEvaluator(excel);
|
||||
|
BIN
test-data/spreadsheet/56502.xlsx
Normal file
BIN
test-data/spreadsheet/56502.xlsx
Normal file
Binary file not shown.
Loading…
Reference in New Issue
Block a user