Skip to content

Commit 65d31eb

Browse files
committed
Don't localize TIMESTAMP columns if they are already tz-aware.
1 parent a0fa0a5 commit 65d31eb

File tree

2 files changed

+12
-24
lines changed

2 files changed

+12
-24
lines changed

pandas_gbq/gbq.py

Lines changed: 8 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,6 @@
1212
BIGQUERY_INSTALLED_VERSION = None
1313
SHOW_VERBOSE_DEPRECATION = False
1414
SHOW_PRIVATE_KEY_DEPRECATION = False
15-
USE_TZAWARE_TIMESTAMP = False
1615
PRIVATE_KEY_DEPRECATION_MESSAGE = (
1716
"private_key is deprecated and will be removed in a future version."
1817
"Use the credentials argument instead. See "
@@ -27,7 +26,7 @@
2726

2827

2928
def _check_google_client_version():
30-
global BIGQUERY_INSTALLED_VERSION, SHOW_VERBOSE_DEPRECATION, SHOW_PRIVATE_KEY_DEPRECATION, USE_TZAWARE_TIMESTAMP
29+
global BIGQUERY_INSTALLED_VERSION, SHOW_VERBOSE_DEPRECATION, SHOW_PRIVATE_KEY_DEPRECATION
3130

3231
try:
3332
import pkg_resources
@@ -62,12 +61,6 @@ def _check_google_client_version():
6261
SHOW_PRIVATE_KEY_DEPRECATION = (
6362
pandas_installed_version >= pandas_version_with_credentials_arg
6463
)
65-
pandas_version_supporting_tzaware_dtype = pkg_resources.parse_version(
66-
"0.24.0"
67-
)
68-
USE_TZAWARE_TIMESTAMP = (
69-
pandas_installed_version >= pandas_version_supporting_tzaware_dtype
70-
)
7164

7265

7366
def _test_google_api_imports():
@@ -501,8 +494,8 @@ def run_query(self, query, **kwargs):
501494
if df.empty:
502495
df = _cast_empty_df_dtypes(schema_fields, df)
503496

504-
if not USE_TZAWARE_TIMESTAMP:
505-
df = _localize_df(schema_fields, df)
497+
# Ensure any TIMESTAMP columns are tz-aware.
498+
df = _localize_df(schema_fields, df)
506499

507500
logger.debug("Got {} rows.\n".format(rows_iter.total_rows))
508501
return df
@@ -662,20 +655,14 @@ def _bqschema_to_nullsafe_dtypes(schema_fields):
662655
See: http://pandas.pydata.org/pandas-docs/dev/missing_data.html
663656
#missing-data-casting-rules-and-indexing
664657
"""
665-
import pandas.api.types
666-
667-
# pandas doesn't support timezone-aware dtype in DataFrame/Series
668-
# constructors until 0.24.0. See:
669-
# https://github.com/pandas-dev/pandas/issues/25843#issuecomment-479656947
670-
timestamp_dtype = "datetime64[ns]"
671-
if USE_TZAWARE_TIMESTAMP:
672-
timestamp_dtype = pandas.api.types.DatetimeTZDtype(unit="ns", tz="UTC")
673-
674658
# If you update this mapping, also update the table at
675659
# `docs/source/reading.rst`.
676660
dtype_map = {
677661
"FLOAT": np.dtype(float),
678-
"TIMESTAMP": timestamp_dtype,
662+
# pandas doesn't support timezone-aware dtype in DataFrame/Series
663+
# constructors. It's more idiomatic to localize after construction.
664+
# https://github.com/pandas-dev/pandas/issues/25843
665+
"TIMESTAMP": "datetime64[ns]",
679666
"TIME": "datetime64[ns]",
680667
"DATE": "datetime64[ns]",
681668
"DATETIME": "datetime64[ns]",
@@ -734,7 +721,7 @@ def _localize_df(schema_fields, df):
734721
if field["mode"].upper() == "REPEATED":
735722
continue
736723

737-
if field["type"].upper() == "TIMESTAMP":
724+
if field["type"].upper() == "TIMESTAMP" and df[column].dt.tz is None:
738725
df[column] = df[column].dt.tz_localize("UTC")
739726

740727
return df

tests/system/test_gbq.py

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -329,9 +329,10 @@ def test_should_properly_handle_arbitrary_timestamp(self, project_id):
329329
{"valid_timestamp": ["2004-09-15T05:00:00.000000Z"]},
330330
dtype="datetime64[ns]",
331331
)
332-
expected["valid_timestamp"] = expected[
333-
"valid_timestamp"
334-
].dt.tz_localize("UTC")
332+
if expected["valid_timestamp"].dt.tz is None:
333+
expected["valid_timestamp"] = expected[
334+
"valid_timestamp"
335+
].dt.tz_localize("UTC")
335336
tm.assert_frame_equal(df, expected)
336337

337338
def test_should_properly_handle_datetime_unix_epoch(self, project_id):

0 commit comments

Comments
 (0)