Skip to content
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

[openpyxl] Annotate Worksheet and other items #9892

Merged
merged 10 commits into from
Mar 23, 2023
Merged
Show file tree
Hide file tree
Changes from 1 commit
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
4 changes: 4 additions & 0 deletions stubs/openpyxl/@tests/stubtest_allowlist.txt
Original file line number Diff line number Diff line change
Expand Up @@ -3,3 +3,7 @@ openpyxl.descriptors.slots.AutoSlotProperties.__new__

# Requires numpy to be installed
openpyxl.utils.dataframe

# Element can be imported from lxml or xml.etree, so the attributes can
# differ at runtime.
openpyxl.xml.functions.Element.*
8 changes: 4 additions & 4 deletions stubs/openpyxl/openpyxl/cell/cell.pyi
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
from _typeshed import Incomplete
from datetime import datetime
from datetime import date, datetime, time, timedelta

from openpyxl.comments.comments import Comment
from openpyxl.styles.cell_style import StyleArray
Expand Down Expand Up @@ -52,11 +52,11 @@ class Cell(StyleableObject):
def check_string(self, value: str): ...
def check_error(self, value: object) -> str: ...
@property
def value(self) -> str | float | datetime | None: ...
def value(self) -> str | float | date | time | timedelta | None: ...
@value.setter
def value(self, value: str | float | datetime | None) -> None: ...
def value(self, value: str | float | date | time | timedelta | None) -> None: ...
@property
def internal_value(self) -> str | float | datetime | None: ...
def internal_value(self) -> str | float | date | time | timedelta | None: ...
AlexWaygood marked this conversation as resolved.
Show resolved Hide resolved
@property
def hyperlink(self) -> Hyperlink | None: ...
@hyperlink.setter
Expand Down
12 changes: 7 additions & 5 deletions stubs/openpyxl/openpyxl/utils/bound_dictionary.pyi
Original file line number Diff line number Diff line change
@@ -1,7 +1,9 @@
from _typeshed import Incomplete
from collections import defaultdict
from typing import Generic, TypeVar

class BoundDictionary(defaultdict[Incomplete, Incomplete]):
reference: Incomplete
def __init__(self, reference: Incomplete | None = ..., *args, **kw) -> None: ...
def __getitem__(self, key): ...
_KT = TypeVar("_KT")
_VT = TypeVar("_VT")

class BoundDictionary(defaultdict[_KT, _VT], Generic[_KT, _VT]):
srittau marked this conversation as resolved.
Show resolved Hide resolved
reference: str | None
def __init__(self, reference: str | None = None, *args, **kw) -> None: ...
Copy link
Member

Choose a reason for hiding this comment

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

The *args, **kwargs here just forward on the arguments to defaultdict.__init__, but we have 8 overloads for that. So I'm fine with keeping this as it is for now.

159 changes: 91 additions & 68 deletions stubs/openpyxl/openpyxl/worksheet/dimensions.pyi
Original file line number Diff line number Diff line change
@@ -1,95 +1,118 @@
from _typeshed import Incomplete
from _typeshed import Incomplete, Unused
from collections.abc import Callable, Generator
from typing import Generic, TypeVar
from typing_extensions import Self

from openpyxl.descriptors import Strict
from openpyxl.descriptors.base import Alias, Bool, Float, Integer, String
from openpyxl.descriptors.serialisable import Serialisable
from openpyxl.styles.styleable import StyleableObject
from openpyxl.utils.bound_dictionary import BoundDictionary
from openpyxl.worksheet.worksheet import Worksheet
from openpyxl.xml.functions import Element

_DimT = TypeVar("_DimT", bound=Dimension)

class Dimension(Strict, StyleableObject):
__fields__: Incomplete
index: Incomplete
hidden: Incomplete
outlineLevel: Incomplete
outline_level: Incomplete
collapsed: Incomplete
style: Incomplete
__fields__: tuple[str, ...]
srittau marked this conversation as resolved.
Show resolved Hide resolved

index: Integer
hidden: Bool
outlineLevel: Integer
outline_level: Alias
collapsed: Bool
style: Alias

def __init__(
self, index, hidden, outlineLevel, collapsed, worksheet, visible: bool = ..., style: Incomplete | None = ...
self,
index: int,
hidden: bool,
outlineLevel: int | None,
collapsed: bool,
worksheet: Worksheet,
visible: bool = True,
style: Incomplete | None = None,
) -> None: ...
def __iter__(self): ...
def __copy__(self): ...
def __iter__(self) -> Generator[tuple[str, str], None, None]: ...
srittau marked this conversation as resolved.
Show resolved Hide resolved
def __copy__(self) -> Self: ...

class RowDimension(Dimension):
__fields__: Incomplete
r: Incomplete
s: Incomplete
ht: Incomplete
height: Incomplete
thickBot: Incomplete
thickTop: Incomplete
__fields__: tuple[str, ...]
srittau marked this conversation as resolved.
Show resolved Hide resolved

r: Alias
s: Alias
ht: Float
height: Alias
thickBot: Bool
thickTop: Bool
AlexWaygood marked this conversation as resolved.
Show resolved Hide resolved

def __init__(
self,
worksheet,
index: int = ...,
ht: Incomplete | None = ...,
customHeight: Incomplete | None = ...,
s: Incomplete | None = ...,
customFormat: Incomplete | None = ...,
hidden: bool = ...,
outlineLevel: int = ...,
outline_level: Incomplete | None = ...,
collapsed: bool = ...,
visible: Incomplete | None = ...,
height: Incomplete | None = ...,
r: Incomplete | None = ...,
spans: Incomplete | None = ...,
thickBot: Incomplete | None = ...,
thickTop: Incomplete | None = ...,
**kw,
worksheet: Worksheet,
index: int = 0,
ht: Incomplete | None = None,
customHeight: Incomplete | None = None,
s: Incomplete | None = None,
customFormat: Incomplete | None = None,
hidden: bool = False,
outlineLevel: int = 0,
outline_level: Incomplete | None = None,
collapsed: bool = False,
visible: Incomplete | None = None,
height: Incomplete | None = None,
r: Incomplete | None = None,
spans: Incomplete | None = None,
thickBot: Incomplete | None = None,
thickTop: Incomplete | None = None,
**kw: Unused,
) -> None: ...
@property
def customFormat(self): ...
def customFormat(self) -> bool: ...
@property
def customHeight(self): ...
def customHeight(self) -> bool: ...

class ColumnDimension(Dimension):
width: Incomplete
bestFit: Incomplete
auto_size: Incomplete
index: Incomplete
min: Incomplete
max: Incomplete
collapsed: Incomplete
__fields__: Incomplete
width: Float
bestFit: Bool
auto_size: Alias
srittau marked this conversation as resolved.
Show resolved Hide resolved
index: String # type: ignore[assignment]
min: Integer
max: Integer
collapsed: Bool
__fields__: tuple[str, ...]
srittau marked this conversation as resolved.
Show resolved Hide resolved

def __init__(
self,
worksheet,
index: str = ...,
width=...,
bestFit: bool = ...,
hidden: bool = ...,
outlineLevel: int = ...,
outline_level: Incomplete | None = ...,
collapsed: bool = ...,
style: Incomplete | None = ...,
min: Incomplete | None = ...,
max: Incomplete | None = ...,
customWidth: bool = ...,
visible: Incomplete | None = ...,
auto_size: Incomplete | None = ...,
worksheet: Worksheet,
index: str = "A",
width: int = ...,
bestFit: bool = False,
hidden: bool = False,
outlineLevel: int = 0,
outline_level: int | None = None,
collapsed: bool = False,
style: Incomplete | None = None,
min: int | None = None,
max: int | None = None,
customWidth: bool = False,
visible: bool | None = None,
auto_size: bool | None = None,
) -> None: ...
@property
def customWidth(self): ...
def customWidth(self) -> bool: ...
def reindex(self) -> None: ...
def to_tree(self): ...
def to_tree(self) -> Element | None: ...

class DimensionHolder(BoundDictionary):
worksheet: Incomplete
max_outline: Incomplete
default_factory: Incomplete
def __init__(self, worksheet, reference: str = ..., default_factory: Incomplete | None = ...) -> None: ...
def group(self, start, end: Incomplete | None = ..., outline_level: int = ..., hidden: bool = ...) -> None: ...
def to_tree(self): ...
class DimensionHolder(BoundDictionary[str, _DimT], Generic[_DimT]):
worksheet: Worksheet
max_outline: Incomplete | None
srittau marked this conversation as resolved.
Show resolved Hide resolved
default_factory: Callable[[], _DimT] | None

def __init__(
self, worksheet: Worksheet, reference: str = "index", default_factory: Callable[[], _DimT] | None = None
) -> None: ...
def group(self, start: str, end: str | None = None, outline_level: int = 1, hidden: bool = False) -> None: ...
def to_tree(self) -> Element | None: ...

class SheetFormatProperties(Serialisable):
tagname: str
Expand Down
51 changes: 42 additions & 9 deletions stubs/openpyxl/openpyxl/worksheet/worksheet.pyi
Original file line number Diff line number Diff line change
@@ -1,25 +1,34 @@
from _typeshed import Incomplete
from collections.abc import Generator, Iterable, Iterator
from datetime import datetime
from typing import overload
from typing_extensions import Literal
from typing import Any, overload
from typing_extensions import Final, Literal

from openpyxl.cell.cell import Cell
from openpyxl.formatting.formatting import ConditionalFormattingList
from openpyxl.workbook.child import _WorkbookChild
from openpyxl.workbook.defined_name import DefinedNameDict
from openpyxl.workbook.workbook import Workbook
from openpyxl.worksheet.cell_range import CellRange
from openpyxl.worksheet.datavalidation import DataValidation
from openpyxl.worksheet.cell_range import CellRange, MultiCellRange
from openpyxl.worksheet.datavalidation import DataValidation, DataValidationList
from openpyxl.worksheet.dimensions import ColumnDimension, DimensionHolder, RowDimension, SheetFormatProperties
from openpyxl.worksheet.filters import AutoFilter
from openpyxl.worksheet.page import PageMargins, PrintOptions, PrintPageSetup
from openpyxl.worksheet.pagebreak import ColBreak, RowBreak
from openpyxl.worksheet.properties import WorksheetProperties
from openpyxl.worksheet.protection import SheetProtection
from openpyxl.worksheet.scenario import ScenarioList
from openpyxl.worksheet.table import Table, TableList
from openpyxl.worksheet.views import SheetView
from openpyxl.worksheet.views import SheetView, SheetViewList

class Worksheet(_WorkbookChild):
mime_type: str
BREAK_NONE: int
BREAK_ROW: int
BREAK_COLUMN: int
SHEETSTATE_VISIBLE: str
SHEETSTATE_HIDDEN: str
SHEETSTATE_VERYHIDDEN: str
SHEETSTATE_VISIBLE: Final = "visible"
SHEETSTATE_HIDDEN: Final = "hidden"
SHEETSTATE_VERYHIDDEN: Final = "veryHidden"
PAPERSIZE_LETTER: str
PAPERSIZE_LETTER_SMALL: str
PAPERSIZE_TABLOID: str
Expand All @@ -33,6 +42,27 @@ class Worksheet(_WorkbookChild):
PAPERSIZE_A5: str
ORIENTATION_PORTRAIT: str
ORIENTATION_LANDSCAPE: str

row_dimensions: DimensionHolder[RowDimension]
column_dimensions: DimensionHolder[ColumnDimension]
row_breaks: RowBreak
col_breaks: ColBreak
merged_cells: MultiCellRange
data_validations: DataValidationList
sheet_state: Literal["visible", "hidden", "veryHidden"]
page_setup: PrintPageSetup
print_options: PrintOptions
page_margins: PageMargins
views: SheetViewList
protection: SheetProtection
defined_names: DefinedNameDict
auto_filter: AutoFilter
conditional_formatting: ConditionalFormattingList
legacy_drawing: Incomplete | None
sheet_properties: WorksheetProperties
sheet_format: SheetFormatProperties
scenarios: ScenarioList

def __init__(self, parent: Workbook, title: str | None = ...) -> None: ...
@property
def sheet_view(self) -> SheetView: ...
Expand All @@ -49,7 +79,10 @@ class Worksheet(_WorkbookChild):
@freeze_panes.setter
def freeze_panes(self, topLeftCell: Incomplete | None = ...) -> None: ...
def cell(self, row: int, column: int, value: str | None = ...) -> Cell: ...
def __getitem__(self, key: str | int | slice) -> Cell | tuple[Cell, ...]: ...
@overload
def __getitem__(self, key: int | slice) -> tuple[Cell, ...]: ...
@overload
def __getitem__(self, key: str) -> Any: ... # Cell | tuple[Cell, ...]
Copy link
Collaborator Author

Choose a reason for hiding this comment

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

Another instance where python/typing#566 would come in handy.

def __setitem__(self, key: str, value: str) -> None: ...
def __iter__(self) -> Iterator[Cell]: ...
def __delitem__(self, key: str) -> None: ...
Expand Down
1 change: 1 addition & 0 deletions stubs/openpyxl/openpyxl/xml/functions.pyi
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
from _typeshed import Incomplete
from xml.etree.ElementTree import Element as Element # possibly also imported from lxml

NS_REGEX: Incomplete

Expand Down