pandas-dev/pandas · error · TypeError

data is already tz-aware

Error message

data is already tz-aware {inferred_tz}, unable to set specified tz: {tz}

What it means

Raised by _validate_tz_from_dtype when both a tz argument and an inferred tz (from the data) are present and they disagree per timezones.tz_compare. The function's contract (documented in its Raises section) is to refuse silently substituting one tz for another. Both dtype-level tz and per-element tz must agree.

Solutions

  1. Pick one source of truth: either drop the `tz=` argument and let pandas infer, or strip tz from the data and pass the desired tz explicitly.
  2. Convert the data's tz first: `s.dt.tz_convert(target_tz)` and then construct without a separate tz arg.
  3. If the data tz is wrong, fix it at ingest rather than overriding at construction.

Example fix

// before
dti = pd.DatetimeIndex(list_of_est_timestamps, tz='US/Pacific')

// after
dti = pd.DatetimeIndex(list_of_est_timestamps).tz_convert('US/Pacific')
Defensive patterns

Strategy: validation

Validate before calling

import pandas as pd
from pandas.core.tools.datetimes import _validate_tz_from_dtype  # illustrative

def reconcile_tz(data_tz, kwarg_tz):
    if data_tz is not None and kwarg_tz is not None:
        if not pd.core.dtypes.common.timezones.tz_compare(data_tz, kwarg_tz):
            raise ValueError('tz mismatch')
    return kwarg_tz or data_tz

Type guard

def tz_consistent(data_tz, kwarg_tz) -> bool:
    if data_tz is None or kwarg_tz is None:
        return True
    import pandas as pd
    return pd.core.dtypes.common.timezones.tz_compare(data_tz, kwarg_tz)

Try / catch

try:
    dti = pd.DatetimeIndex(values, tz=tz)
except TypeError as e:
    if 'already tz-aware' in str(e):
        dti = pd.DatetimeIndex(values).tz_convert(tz)
    else:
        raise

Prevention

When it happens

Trigger: Calling `pd.DatetimeIndex(values_with_tz_A, tz='B')`, `pd.to_datetime(values, utc=False)` where values already carry tz A and you pass tz B, or constructing a Series/Index with conflicting tz sources. Also reached via the DatetimeIndex constructor when `dtype='datetime64[ns, US/Pacific]'` is passed for data inferred as US/Eastern.

Common situations: Loading tz-aware data from Parquet/SQL and then re-stamping with a tz via the constructor. Mixing a tz keyword argument with tz-aware Timestamps in a list. Misreading source data's tz and supplying the wrong override.

Related errors


AI-assisted analysis of pandas-dev/pandas@3b7651241d (2026-08-11). Data as JSON: /api/errors/2db79f9402531d8d. Report an issue: GitHub.

Appendix: source

Thrown at pandas/core/arrays/datetimes.py:2946

    Parameters
    ----------
    tz : tzinfo or None
    inferred_tz : tzinfo or None

    Returns
    -------
    tz : tzinfo or None

    Raises
    ------
    TypeError : if both timezones are present but do not match
    """
    if tz is None:
        tz = inferred_tz
    elif inferred_tz is None:
        pass
    elif not timezones.tz_compare(tz, inferred_tz):
        raise TypeError(
            f"data is already tz-aware {inferred_tz}, unable to set specified tz: {tz}"
        )
    return tz


def _validate_dt64_dtype(dtype):
    """
    Check that a dtype, if passed, represents either a numpy datetime64[ns]
    dtype or a pandas DatetimeTZDtype.

    Parameters
    ----------
    dtype : object

    Returns
    -------
    dtype : None, numpy.dtype, or DatetimeTZDtype

View on GitHub (pinned to 3b7651241d)