Skip to content

TYP/CLN: cleanup _openpyxl.py, add type annotation #36021 #36022

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 9 commits into from
Sep 1, 2020
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion ci/deps/azure-37-locale_slow.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@ dependencies:
- lxml
- matplotlib=3.0.0
- numpy=1.16.*
- openpyxl=2.5.7
- openpyxl=2.6.0
- python-dateutil
- python-blosc
- pytz=2017.3
Expand Down
2 changes: 1 addition & 1 deletion ci/deps/azure-37-minimum_versions.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@ dependencies:
- numba=0.46.0
- numexpr=2.6.8
- numpy=1.16.5
- openpyxl=2.5.7
- openpyxl=2.6.0
- pytables=3.4.4
- python-dateutil=2.7.3
- pytz=2017.3
Expand Down
2 changes: 1 addition & 1 deletion doc/source/getting_started/install.rst
Original file line number Diff line number Diff line change
Expand Up @@ -274,7 +274,7 @@ html5lib 1.0.1 HTML parser for read_html (see :ref
lxml 4.3.0 HTML parser for read_html (see :ref:`note <optional_html>`)
matplotlib 2.2.3 Visualization
numba 0.46.0 Alternative execution engine for rolling operations
openpyxl 2.5.7 Reading / writing for xlsx files
openpyxl 2.6.0 Reading / writing for xlsx files
pandas-gbq 0.12.0 Google Big Query access
psycopg2 2.7 PostgreSQL engine for sqlalchemy
pyarrow 0.15.0 Parquet, ORC, and feather reading / writing
Expand Down
2 changes: 1 addition & 1 deletion doc/source/whatsnew/v1.2.0.rst
Original file line number Diff line number Diff line change
Expand Up @@ -109,7 +109,7 @@ Optional libraries below the lowest tested version may still work, but are not c
+-----------------+-----------------+---------+
| numba | 0.46.0 | |
+-----------------+-----------------+---------+
| openpyxl | 2.5.7 | |
| openpyxl | 2.6.0 | X |
+-----------------+-----------------+---------+
| pyarrow | 0.15.0 | X |
+-----------------+-----------------+---------+
Expand Down
59 changes: 16 additions & 43 deletions pandas/io/excel/_openpyxl.py
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
from typing import List
from typing import TYPE_CHECKING, Dict, List, Optional

import numpy as np

Expand All @@ -8,6 +8,9 @@
from pandas.io.excel._base import ExcelWriter, _BaseExcelReader
from pandas.io.excel._util import _validate_freeze_panes

if TYPE_CHECKING:
from openpyxl.descriptors.serialisable import Serialisable


class _OpenpyxlWriter(ExcelWriter):
engine = "openpyxl"
Expand All @@ -22,53 +25,22 @@ def __init__(self, path, engine=None, mode="w", **engine_kwargs):
if self.mode == "a": # Load from existing workbook
from openpyxl import load_workbook

book = load_workbook(self.path)
self.book = book
self.book = load_workbook(self.path)
else:
# Create workbook object with default optimized_write=True.
self.book = Workbook()

if self.book.worksheets:
try:
self.book.remove(self.book.worksheets[0])
except AttributeError:

# compat - for openpyxl <= 2.4
self.book.remove_sheet(self.book.worksheets[0])
self.book.remove(self.book.worksheets[0])

def save(self):
"""
Save workbook to disk.
"""
return self.book.save(self.path)

@classmethod
def _convert_to_style(cls, style_dict):
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't see this method is used anywhere. And it doesn't affect any test. Also, it seems like openpyxl doesn't have a style module anymore.

"""
Converts a style_dict to an openpyxl style object.

Parameters
----------
style_dict : style dictionary to convert
"""
from openpyxl.style import Style

xls_style = Style()
for key, value in style_dict.items():
for nk, nv in value.items():
if key == "borders":
(
xls_style.borders.__getattribute__(nk).__setattr__(
"border_style", nv
)
)
else:
xls_style.__getattribute__(key).__setattr__(nk, nv)

return xls_style
self.book.save(self.path)

@classmethod
def _convert_to_style_kwargs(cls, style_dict):
def _convert_to_style_kwargs(cls, style_dict: dict) -> Dict[str, "Serialisable"]:
"""
Convert a style_dict to a set of kwargs suitable for initializing
or updating-on-copy an openpyxl v2 style object.
Expand All @@ -93,7 +65,7 @@ def _convert_to_style_kwargs(cls, style_dict):
"""
_style_key_map = {"borders": "border"}

style_kwargs = {}
style_kwargs: Dict[str, Serialisable] = {}
for k, v in style_dict.items():
if k in _style_key_map:
k = _style_key_map[k]
Expand Down Expand Up @@ -404,7 +376,7 @@ def write_cells(
# Write the frame cells using openpyxl.
sheet_name = self._get_sheet_name(sheet_name)

_style_cache = {}
_style_cache: Dict[str, Dict[str, Serialisable]] = {}

if sheet_name in self.sheets:
wks = self.sheets[sheet_name]
Expand All @@ -426,7 +398,7 @@ def write_cells(
if fmt:
xcell.number_format = fmt

style_kwargs = {}
style_kwargs: Optional[Dict[str, Serialisable]] = {}
if cell.style:
key = str(cell.style)
style_kwargs = _style_cache.get(key)
Expand Down Expand Up @@ -515,16 +487,17 @@ def get_sheet_by_index(self, index: int):

def _convert_cell(self, cell, convert_float: bool) -> Scalar:

# TODO: replace with openpyxl constants
from openpyxl.cell.cell import TYPE_BOOL, TYPE_ERROR, TYPE_NUMERIC

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

openpyxl verion < 2.6 would raise import error here.

if cell.is_date:
return cell.value
elif cell.data_type == "e":
elif cell.data_type == TYPE_ERROR:
return np.nan
elif cell.data_type == "b":
elif cell.data_type == TYPE_BOOL:
return bool(cell.value)
elif cell.value is None:
return "" # compat with xlrd
elif cell.data_type == "n":
elif cell.data_type == TYPE_NUMERIC:
# GH5394
if convert_float:
val = int(cell.value)
Expand Down
3 changes: 0 additions & 3 deletions setup.cfg
Original file line number Diff line number Diff line change
Expand Up @@ -217,9 +217,6 @@ check_untyped_defs=False
[mypy-pandas.io.excel._base]
check_untyped_defs=False

[mypy-pandas.io.excel._openpyxl]
check_untyped_defs=False

[mypy-pandas.io.excel._util]
check_untyped_defs=False

Expand Down