EPPlus icon indicating copy to clipboard operation
EPPlus copied to clipboard

Fatal Exception thrown when loading XLSX with no CellStyleXfs

Open TechSavvySam opened this issue 6 years ago • 1 comments
trafficstars

I have an .XLSX created by a 3rd party. I can read it in Excel just fine, however if I try to read it with EPPlus, I get the following exception:

Index was out of range. Must be non-negative and less than the size of the collection.
Parameter name: index

at System.ThrowHelper.ThrowArgumentOutOfRangeException(ExceptionArgument argument, ExceptionResource resource)
   at OfficeOpenXml.Style.ExcelStyle..ctor(ExcelStyles styles, ChangedEventHandler ChangedEvent, Int32 positionID, String Address, Int32 xfsId)
   at OfficeOpenXml.Style.XmlAccess.ExcelNamedStyleXml..ctor(XmlNamespaceManager NameSpaceManager, XmlNode topNode, ExcelStyles styles)
   at OfficeOpenXml.ExcelStyles.LoadFromDocument()
   at OfficeOpenXml.ExcelStyles..ctor(XmlNamespaceManager NameSpaceManager, XmlDocument xml, ExcelWorkbook wb)
   at OfficeOpenXml.ExcelWorkbook.get_Styles()
   at OfficeOpenXml.ExcelWorkbook.get_MaxFontWidth()
   at OfficeOpenXml.ExcelWorksheet.get_DefaultColWidth()
   at OfficeOpenXml.ExcelWorksheet.LoadColumns(XmlReader xr)
   at OfficeOpenXml.ExcelWorksheet.CreateXml()
   at OfficeOpenXml.ExcelWorksheet..ctor(XmlNamespaceManager ns, ExcelPackage excelPackage, String relID, Uri uriWorksheet, String sheetName, Int32 sheetID, Int32 positionID, eWorkSheetHidden hide)
   at OfficeOpenXml.ExcelWorksheets..ctor(ExcelPackage pck, XmlNamespaceManager nsm, XmlNode topNode)
   at OfficeOpenXml.ExcelWorkbook.get_Worksheets()

If I open the file in Excel and then save it as a new file, EPPlus can read the file just fine. Obviously, this is not a solution that is reasonable for the end users of my system. This also tells me that Excel can deal with a file that has this "issue".

I hacked this class into the EPPlusSamples project (I will attach this file to the ticket):

    public class SamTest1
    {
        public static string RunSamTest1()
        {
            var f = File.Open("c:/temp/Submittal Extract 5 ton.xlsx", FileMode.Open);

            using (var package = new ExcelPackage(f))
            {

                var ws = package.Workbook.Worksheets; // <== this will throw an exception
            }
            return "";
        }
    }

Here's the problem. In the code below

positionID = -1 and _styles.CellStyleXfs list is empty, so the "else" gets called

 internal ExcelStyle(ExcelStyles styles, OfficeOpenXml.XmlHelper.ChangedEventHandler ChangedEvent, int positionID, string Address, int xfsId) :
        base(styles, ChangedEvent, positionID, Address)
    {
        Index = xfsId;
        ExcelXfs xfs;
        if (positionID > -1)
        {
            xfs = _styles.CellXfs[xfsId];
        }
        else
        {
            xfs = _styles.CellStyleXfs[xfsId];
        }


and that throws an exception because the code that's called can't handle an empty list.

public T this[int PositionID]
    {
        get
        {
            return _list[PositionID]; // <<<--- this blows up because _list has no members
        }
    }


I tweaked the code to be this, and it worked OK, but I'm not sure of the best way to deal with that list being empty:

if (positionID > -1 || _styles.CellStyleXfs.Count == 0)

I posted this question to stackoverflow to gather my thoughts about this issue: https://stackoverflow.com/questions/58031166/index-was-out-of-range-exception-when-attempting-to-access-worksheets-object

Submittal Extract 5 ton.xlsx

TechSavvySam avatar Sep 21 '19 13:09 TechSavvySam

bump.

Is there anything going on with this project? I would put a pull request in for this update, but there are over 60 open pull requests already...

TechSavvySam avatar Oct 23 '19 14:10 TechSavvySam