8000 Add type hints to tests (#50) · realpython/codetiming@e51e4c3 · GitHub
[go: up one dir, main page]

Skip to content

Commit e51e4c3

Browse files
authored
Add type hints to tests (#50)
* Add type hints to tests * Workaround for Python 3.7 which doesn't support Protocol
1 parent 0ebf506 commit e51e4c3

File tree

5 files changed

+101
-54
lines changed

5 files changed

+101
-54
lines changed

CHANGELOG.md

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,7 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
99

1010
### Changed
1111

12+
- Add type hints to tests ([#50])
1213
- Drop explicit support for Python 3.6 ([#48])
1314

1415
## [1.4.0] - 2022-11-08
@@ -77,6 +78,7 @@ Initial version of `codetiming`. Version 1.0.0 corresponds to the code in the tu
7778
[1.1.0]: https://github.com/realpython/codetiming/compare/v1.0.0...v1.1.0
7879
[1.0.0]: https://github.com/realpython/codetiming/releases/tag/v1.0.0
7980

81+
[#50]: https://github.com/realpython/codetiming/pull/50
8082
[#48]: https://github.com/realpython/codetiming/pull/48
8183
[#47]: https://github.com/realpython/codetiming/pull/47
8284
[#46]: https://github.com/realpython/codetiming/pull/46

CONTRIBUTING.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -50,7 +50,7 @@ Run tests using [`tox`](https://tox.readthedocs.io/). You can also run individua
5050
- Static type hinting using [`mypy`](http://mypy-lang.org/). Test your type hints as follows:
5151

5252
```console
53-
$ mypy --strict codetiming/
53+
$ mypy --strict codetiming/ tests/
5454
```
5555

5656
See Real Python's [Python Type Checking guide](https://realpython.com/python-type-checking/) for more information.

codetiming/_timer.py

Lines changed: 25 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -9,12 +9,32 @@
99
import time
1010
from contextlib import ContextDecorator
1111
from dataclasses import dataclass, field
12-
from typing import Any, Callable, ClassVar, Optional, Union
12+
from typing import TYPE_CHECKING, Any, Callable, ClassVar, Optional, Union
1313

1414
# Codetiming imports
8000
1515
from codetiming._timers import Timers
1616

17+
# Special types, Protocol only works for Python >= 3.8
18+
if TYPE_CHECKING: # pragma: nocover
19+
# Standard library imports
20+
from typing import Protocol, TypeVar
1721

22+
T = TypeVar("T")
23+
24+
class FloatArg(Protocol):
25+
"""Protocol type that allows classes that take one float argument"""
26+
27+
def __call__(self: T, __seconds: float) -> T:
28+
"""Callable signature"""
29+
... # pragma: nocover
30+
31+
else:
32+
33+
class FloatArg:
34+
"""Dummy runtime class"""
35+
36+
37+
# Timer code
1838
class TimerError(Exception):
1939
"""A custom exception used to report errors in use of Timer class."""
2040

@@ -24,12 +44,12 @@ class Timer(ContextDecorator):
2444
"""Time your code using a class, context manager, or decorator."""
2545

2646
timers: ClassVar[Timers] = Timers()
27-
_start_time: Optional[float] = field(default=None, init=False, repr=False)
2847
name: Optional[str] = None
29-
text: Union[str, Callable[[float], str]] = "Elapsed time: {:0.4f} seconds"
30-
initial_text: Union[bool, str] = False
48+
text: Union[str, FloatArg, Callable[[float], str]] = "Elapsed time: {:0.4f} seconds"
49+
initial_text: Union[bool, str, FloatArg] = False
3150
logger: Optional[Callable[[str], None]] = print
3251
last: float = field(default=math.nan, init=False, repr=False)
52+
_start_time: Optional[float] = field(default=None, init=False, repr=False)
3353

3454
def start(self) -> None:
3555
"""Start a new timer."""
@@ -69,7 +89,7 @@ def stop(self) -> float:
6989
"minutes": self.last / 60,
7090
}
7191
text = self.text.format(self.last, **attributes)
72-
self.logger(text)
92+
self.logger(str(text))
7393
if self.name:
7494
self.timers.add(self.name, self.last)
7595

0 commit comments

Comments
 (0)
0