Skip to content

Commit

Permalink
DateTime and more: Serialize CrateDB's DateTime types using zone info
Browse files Browse the repository at this point in the history
Effectively, just add `%z` to the format string passed to `strftime`.

-- https://docs.python.org/3/library/datetime.html#strftime-and-strptime-format-codes
  • Loading branch information
amotl committed Jun 25, 2024
1 parent 619c991 commit 145f701
Show file tree
Hide file tree
Showing 3 changed files with 15 additions and 13 deletions.
2 changes: 1 addition & 1 deletion src/sqlalchemy_cratedb/dialect.py
Original file line number Diff line number Diff line change
Expand Up @@ -117,7 +117,7 @@ def bind_processor(self, dialect):
def process(value):
if value is not None:
assert isinstance(value, datetime)
return value.strftime('%Y-%m-%dT%H:%M:%S.%fZ')
return value.strftime('%Y-%m-%dT%H:%M:%S.%f%z')
return value
return process

Expand Down
22 changes: 12 additions & 10 deletions tests/datetime_test.py
Original file line number Diff line number Diff line change
Expand Up @@ -51,12 +51,13 @@


INPUT_DATE = dt.date(2009, 5, 13)
INPUT_DATETIME_NOTZ = dt.datetime(2009, 5, 13, 19, 19, 30, 123456)
INPUT_DATETIME_TZ = dt.datetime(2009, 5, 13, 19, 19, 30, 123456, tzinfo=zoneinfo.ZoneInfo("Europe/Kyiv"))
INPUT_DATETIME_NOTZ = dt.datetime(2009, 5, 13, 19, 00, 30, 123456)
INPUT_DATETIME_TZ = dt.datetime(2009, 5, 13, 19, 00, 30, 123456, tzinfo=zoneinfo.ZoneInfo("Europe/Kyiv"))
OUTPUT_DATE = INPUT_DATE
OUTPUT_TIME = dt.time(19, 19, 30, 123000)
OUTPUT_DATETIME_NOTZ = dt.datetime(2009, 5, 13, 19, 19, 30, 123000)
OUTPUT_DATETIME_TZ = dt.datetime(2009, 5, 13, 19, 19, 30, 123000)
OUTPUT_TIMETZ_NOTZ = dt.time(19, 00, 30, 123000)
OUTPUT_TIMETZ_TZ = dt.time(16, 00, 30, 123000)
OUTPUT_DATETIME_NOTZ = dt.datetime(2009, 5, 13, 19, 00, 30, 123000)
OUTPUT_DATETIME_TZ = dt.datetime(2009, 5, 13, 16, 00, 30, 123000)


@skipIf(SA_VERSION < SA_1_4, "SQLAlchemy 1.3 suddenly has problems with these test cases")
Expand Down Expand Up @@ -143,11 +144,11 @@ def test_datetime_notz(session):
assert result["date"] == OUTPUT_DATE
assert result["datetime_notz"] == OUTPUT_DATETIME_NOTZ
assert result["datetime_notz"].tzname() is None
assert result["datetime_notz"].timetz() == OUTPUT_TIME
assert result["datetime_notz"].timetz() == OUTPUT_TIMETZ_NOTZ
assert result["datetime_notz"].tzinfo is None
assert result["datetime_tz"] == OUTPUT_DATETIME_NOTZ
assert result["datetime_tz"].tzname() is None
assert result["datetime_tz"].timetz() == OUTPUT_TIME
assert result["datetime_tz"].timetz() == OUTPUT_TIMETZ_NOTZ
assert result["datetime_tz"].tzinfo is None


Expand All @@ -169,16 +170,17 @@ def test_datetime_tz(session):
session.execute(sa.text("REFRESH TABLE foobar"))

# Query record.
session.expunge(foo_item)
result = session.execute(sa.select(
FooBar.name, FooBar.date, FooBar.datetime_notz, FooBar.datetime_tz)).mappings().first()

# Compare outcome.
assert result["date"] == OUTPUT_DATE
assert result["datetime_notz"] == OUTPUT_DATETIME_TZ
assert result["datetime_notz"] == OUTPUT_DATETIME_NOTZ
assert result["datetime_notz"].tzname() is None
assert result["datetime_notz"].timetz() == OUTPUT_TIME
assert result["datetime_notz"].timetz() == OUTPUT_TIMETZ_NOTZ
assert result["datetime_notz"].tzinfo is None
assert result["datetime_tz"] == OUTPUT_DATETIME_TZ
assert result["datetime_tz"].tzname() is None
assert result["datetime_tz"].timetz() == OUTPUT_TIME
assert result["datetime_tz"].timetz() == OUTPUT_TIMETZ_TZ
assert result["datetime_tz"].tzinfo is None
4 changes: 2 additions & 2 deletions tests/update_test.py
Original file line number Diff line number Diff line change
Expand Up @@ -81,7 +81,7 @@ def test_onupdate_is_triggered(self):
args = args[1]
self.assertEqual(expected_stmt, stmt)
self.assertEqual(40, args[0])
dt = datetime.strptime(args[1], '%Y-%m-%dT%H:%M:%S.%fZ')
dt = datetime.strptime(args[1], '%Y-%m-%dT%H:%M:%S.%f')
self.assertIsInstance(dt, datetime)
self.assertGreater(dt, now)
self.assertEqual('Arthur', args[2])
Expand Down Expand Up @@ -110,6 +110,6 @@ def test_bulk_update(self):
self.assertEqual(expected_stmt, stmt)
self.assertEqual('Julia', args[0])
self.assertEqual({'favorite_book': 'Romeo & Juliet'}, args[1])
dt = datetime.strptime(args[2], '%Y-%m-%dT%H:%M:%S.%fZ')
dt = datetime.strptime(args[2], '%Y-%m-%dT%H:%M:%S.%f')
self.assertIsInstance(dt, datetime)
self.assertGreater(dt, before_update_time)

0 comments on commit 145f701

Please sign in to comment.