{"record":{"id":"9ef17acd3948afeb","repo":"pandas-dev/pandas","slug":"already-tz-aware-use-tz-convert-to-convert","errorCode":null,"errorMessage":"Already tz-aware, use tz_convert to convert.","messagePattern":"Already tz-aware, use tz_convert to convert\\.","errorType":"exception","errorClass":"TypeError","httpStatus":null,"severity":"error","filePath":"pandas/core/arrays/datetimes.py","lineNumber":1115,"sourceCode":"        0   2015-03-29 03:30:00+02:00\n        1   2015-03-29 03:30:00+02:00\n        dtype: datetime64[ns, Europe/Warsaw]\n        \"\"\"  # noqa: E501\n        nonexistent_options = (\"raise\", \"NaT\", \"shift_forward\", \"shift_backward\")\n        if nonexistent not in nonexistent_options and not isinstance(\n            nonexistent, timedelta\n        ):\n            raise ValueError(\n                \"The nonexistent argument must be one of 'raise', \"\n                \"'NaT', 'shift_forward', 'shift_backward' or \"\n                \"a timedelta object\"\n            )\n\n        if self.tz is not None:\n            if tz is None:\n                new_dates = tz_convert_from_utc(self.asi8, self.tz, reso=self._creso)\n            else:\n                raise TypeError(\"Already tz-aware, use tz_convert to convert.\")\n        else:\n            tz = timezones.maybe_get_tz(tz)\n            # Convert to UTC\n\n            new_dates = tzconversion.tz_localize_to_utc(\n                self.asi8,\n                tz,\n                ambiguous=ambiguous,\n                nonexistent=nonexistent,\n                creso=self._creso,\n            )\n        new_dates_dt64 = new_dates.view(f\"M8[{self.unit}]\")\n        dtype = tz_to_dtype(tz, unit=self.unit)\n\n        return self._simple_new(new_dates_dt64, dtype=dtype)\n\n    # ----------------------------------------------------------------\n    # Conversion Methods - Vectorized analogues of Timestamp methods","sourceCodeStart":1097,"sourceCodeEnd":1133,"githubUrl":"https://github.com/pandas-dev/pandas/blob/71959b8cb9b2459c16e14b34f28b178ccfe14735/pandas/core/arrays/datetimes.py#L1097-L1133","documentation":"Raised by tz_localize when the data already has a tz (self.tz is not None) and a new tz is requested. tz_localize attaches a tz; once data is aware you must use tz_convert to change it, so pandas refuses to silently overwrite. TypeError.","triggerScenarios":"Calling .tz_localize('UTC') on data that was parsed with utc=True or already localized; re-localizing in a loop; applying tz_localize to a column produced by another tz_localize.","commonSituations":"Generic pipeline that always calls tz_localize regardless of current state; data already in UTC from the DB but code treats it as naive.","solutions":["Switch to tz_convert: idx.tz_convert(target_tz).","Branch on idx.tz: tz_localize when None, tz_convert otherwise.","Drop the tz first with tz_localize(None) only if you genuinely want to re-localize wall time."],"exampleFix":"# before\nidx.tz_localize('US/Eastern')  # idx already aware\n# after\nidx.tz_convert('US/Eastern')","handlingStrategy":"validation","validationCode":"def set_tz(idx, target):\n    if idx.tz is not None:\n        return idx.tz_convert(target)\n    return idx.tz_localize(target)","typeGuard":"def is_aware(idx) -> bool:\n    return getattr(idx, 'tz', None) is not None","tryCatchPattern":"try:\n    out = idx.tz_localize('UTC')\nexcept TypeError as e:\n    if 'Already tz-aware' in str(e):\n        out = idx.tz_convert('UTC')\n    else:\n        raise","preventionTips":["Branch on idx.tz: localize when None, convert otherwise.","Avoid blanket tz_localize in generic helpers.","Track column awareness in schema metadata."],"tags":["datetime","timezone","tz-localize","pandas"],"analyzedSha":"71959b8cb9b2459c16e14b34f28b178ccfe14735","analyzedAt":"2026-08-07T01:30:20.476Z","schemaVersion":2},"datasetVersion":"2026-08-07T03:17:09.362Z"}