Reputation: 146
I'm trying to load the workbook, I can't read this specific file.
input_workbook = openpyxl.load_workbook(input_file)
Error i'm receiving is:
Traceback (most recent call last):
File "/home/admin/Development/pythonProject/venv/RFQ_Analysis_R01.py", line 121, in <module>
input_workbook = openpyxl.load_workbook(input_file)
File "/home/admin/Development/pythonProject/venv/lib/python3.7/site-packages/openpyxl/reader/excel.py", line 315, in load_workbook
reader.read()
File "/home/admin/Development/pythonProject/venv/lib/python3.7/site-packages/openpyxl/reader/excel.py", line 280, in read
self.read_worksheets()
File "/home/admin/Development/pythonProject/venv/lib/python3.7/site-packages/openpyxl/reader/excel.py", line 228, in read_worksheets
ws_parser.bind_all()
File "/home/admin/Development/pythonProject/venv/lib/python3.7/site-packages/openpyxl/worksheet/_reader.py", line 434, in bind_all
self.bind_cells()
File "/home/admin/Development/pythonProject/venv/lib/python3.7/site-packages/openpyxl/worksheet/_reader.py", line 339, in bind_cells
style = self.ws.parent._cell_styles[cell['style_id']]
IndexError: list index out of range
Upvotes: 6
Views: 5451
Reputation: 11
I'm not sure what's wrong with your excel file and I also didn't meet the same problem but just try this one, I believe it will work well:
Go to the _reader.py (.\Python\Python311\Lib\site-packages\openpyxl\worksheet)
Find the bind_cells()
in class WorksheetReader
and simply apply try/except like as:
def bind_cells(self):
for idx, row in self.parser.parse():
for cell in row:
try: style = self.ws.parent._cell_styles[cell['style_id']]
except: style = StyleArray('i', [0, 0, 0, 0, 0, 0, 0, 0, 0])
c = Cell(self.ws, row=cell['row'], column=cell['column'], style_array=style)
c._value = cell['value']
c.data_type = cell['data_type']
self.ws._cells[(cell['row'], cell['column'])] = c
if self.ws._cells:
self.ws._current_row = self.ws.max_row # use cells not row dimensions
Upvotes: 0
Reputation: 11
I meet the same problem and this is my solution: Go to the _reader.py (.\Python\Python311\Lib\site-packages\openpyxl\worksheet)
Find the bind_row_dimensions()
in class WorksheetReader
and simply apply try/except
like as:
def bind_row_dimensions(self):
for row, rd in self.parser.row_dimensions.items():
if 's' in rd:
key = int(rd['s'])
try: rd['s'] = self.ws.parent._cell_styles[key]
except: rd['s'] = None
self.ws.row_dimensions[int(row)] = RowDimension(self.ws, **rd)
It works for me and hope you so.
Upvotes: 0
Reputation: 1688
tldr - if you are using XlsxWriter
make sure you are not writing None
as the format for a cell.
I ran in to this while generating a simple xlsx file while using XlsxWriter. The xlsx files always opened fine but failed to load with openpyxl
Turns out I had a helper function like this
def writerow(worksheet, row, cols, fmt=None):
for i, val in enumerate(cols):
worksheet.write(r, i, val, fmt)
If you notice I was essentially calling worksheet.write(r, i, val, None)
when I did not explicitly pass a format.
The fix is to just make sure you always have a format when you are writing a row.
default_format = workbook.add_format()
worksheet.write(row, col, value, default_format)
Upvotes: 0
Reputation: 16141
I've run into the same issue. It does not appear to be an issue with the file format, as the file opens just fine in Excel. This just looks like it's a bug with openpyxl
. (I've opened a issue request here)
You can workaround it with the following monkey patch. Just put it into your startup code somewhere.
def monkey_patch_openpyxl():
'''Openpyxl has a bug with workbooks that have wrong cell styling information.
Monkey patch the library so it can handle these types of workbooks.'''
from openpyxl.worksheet import _reader
from openpyxl.cell import Cell
def bind_cells(self):
for idx, row in self.parser.parse():
for cell in row:
try:
style = self.ws.parent._cell_styles[cell['style_id']]
except: ## This is the patch, original doesn't have a try/except here
style = None
c = Cell(self.ws, row=cell['row'], column=cell['column'], style_array=style)
c._value = cell['value']
c.data_type = cell['data_type']
self.ws._cells[(cell['row'], cell['column'])] = c
self.ws.formula_attributes = self.parser.array_formulae
if self.ws._cells:
self.ws._current_row = self.ws.max_row # use cells not row dimensions
_reader.WorksheetReader.bind_cells = bind_cells
monkey_patch_openpyxl()
Upvotes: 4