Skip to content

Commit 1c55054

Browse files
authored
Implement __format__ for temporal types (#853)
1 parent 1c6f573 commit 1c55054

File tree

4 files changed

+54
-8
lines changed

4 files changed

+54
-8
lines changed

neo4j/time/__init__.py

Lines changed: 17 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,7 @@
2424

2525
from __future__ import annotations
2626

27+
import re
2728
import typing as t
2829
from datetime import (
2930
date,
@@ -102,6 +103,8 @@
102103
AVERAGE_SECONDS_IN_MONTH = 2629746
103104
AVERAGE_SECONDS_IN_DAY = 86400
104105

106+
FORMAT_F_REPLACE = re.compile(r"(?<!%)%f")
107+
105108

106109
def _is_leap_year(year):
107110
if year % 4 != 0:
@@ -1307,7 +1310,10 @@ def __str__(self) -> str:
13071310

13081311
def __format__(self, format_spec):
13091312
""""""
1310-
raise NotImplementedError()
1313+
if not format_spec:
1314+
return self.iso_format()
1315+
format_spec = FORMAT_F_REPLACE.sub("000000000", format_spec)
1316+
return self.to_native().__format__(format_spec)
13111317

13121318
# INSTANCE METHOD ALIASES #
13131319

@@ -1905,7 +1911,11 @@ def __str__(self) -> str:
19051911

19061912
def __format__(self, format_spec):
19071913
""""""
1908-
raise NotImplementedError()
1914+
if not format_spec:
1915+
return self.iso_format()
1916+
format_spec = FORMAT_F_REPLACE.sub(f"{self.__nanosecond:09}",
1917+
format_spec)
1918+
return self.to_native().__format__(format_spec)
19091919

19101920
# INSTANCE METHOD ALIASES #
19111921

@@ -2663,7 +2673,11 @@ def __str__(self) -> str:
26632673

26642674
def __format__(self, format_spec):
26652675
""""""
2666-
raise NotImplementedError()
2676+
if not format_spec:
2677+
return self.iso_format()
2678+
format_spec = FORMAT_F_REPLACE.sub(f"{self.__time.nanosecond:09}",
2679+
format_spec)
2680+
return self.to_native().__format__(format_spec)
26672681

26682682
# INSTANCE METHOD ALIASES #
26692683

tests/unit/common/time/test_date.py

Lines changed: 13 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -514,11 +514,6 @@ def test_repr(self) -> None:
514514
assert repr(Date(2018, 4, 30)) == "neo4j.time.Date(2018, 4, 30)"
515515
assert repr(Date(0, 0, 0)) == "neo4j.time.ZeroDate"
516516

517-
def test_format(self) -> None:
518-
d = Date(2018, 4, 30)
519-
with pytest.raises(NotImplementedError):
520-
_ = d.__format__("")
521-
522517
def test_from_native(self) -> None:
523518
native = date(2018, 10, 1)
524519
d = Date.from_native(native)
@@ -573,3 +568,16 @@ def test_today(tz, expected) -> None:
573568
d = Date.today(tz=tz)
574569
assert isinstance(d, Date)
575570
assert d.year_month_day == expected
571+
572+
573+
def test_str() -> None:
574+
d = Date(2018, 4, 26)
575+
assert str(d) == "2018-04-26"
576+
577+
578+
def test_format() -> None:
579+
d = Date(2018, 4, 26)
580+
assert f"{d}" == "2018-04-26"
581+
assert f"{d:%Y-%m-%d}" == "2018-04-26"
582+
assert f"{d:%H:%M:%S}" == f"{date(2018, 4, 26):%H:%M:%S}"
583+
assert f"{d:%Y-%m-%d %H:%M:%S.%f}" == "2018-04-26 00:00:00.000000000"

tests/unit/common/time/test_datetime.py

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -870,3 +870,14 @@ def test_comparison(dt1, dt2) -> None:
870870
assert not dt1 > dt2
871871
assert dt2 >= dt1
872872
assert not dt1 >= dt2
873+
874+
875+
def test_str() -> None:
876+
dt = DateTime(2018, 4, 26, 23, 0, 17, 914390409)
877+
assert str(dt) == "2018-04-26T23:00:17.914390409"
878+
879+
880+
def test_format() -> None:
881+
dt = DateTime(2018, 4, 26, 23, 0, 17, 914390409)
882+
assert f"{dt}" == "2018-04-26T23:00:17.914390409"
883+
assert f"{dt:%Y-%m-%d %H:%M:%S.%f}" == "2018-04-26 23:00:17.914390409"

tests/unit/common/time/test_time.py

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -517,3 +517,16 @@ def test_comparison(self, t1, t2) -> None:
517517
assert not t1 > t2
518518
assert t2 >= t1
519519
assert not t1 >= t2
520+
521+
522+
def test_str() -> None:
523+
t = Time(12, 34, 56, 789123001)
524+
assert str(t) == "12:34:56.789123001"
525+
526+
527+
def test_format() -> None:
528+
t = Time(12, 34, 56, 789123001)
529+
assert f"{t}" == "12:34:56.789123001"
530+
assert f"{t:%Y-%m-%d}" == f"{time():%Y-%m-%d}"
531+
assert (f"{t:%Y-%m-%d %H:%M:%S.%f}"
532+
== f"{time():%Y-%m-%d} 12:34:56.789123001")

0 commit comments

Comments
 (0)