-1

So, "2021-08-17T20:03:36.480-07:00", is given as as a string. I want to convert it into the local time.

Something like this 2020-01-06 00:00:00.

This is what I had tried earlier

from datetime import datetime

def convert_utc_local(utc_time):
    conv_time = ' '.join(utc_time.split("T"))
    return conv_time.astimezone(tzlocal())

And the error came to

return utc_time.astimezone(tzlocal())
AttributeError: 'str' object has no attribute 'astimezone'"

So what worked for me was this:

def convert_utc_local(utc_time):
    to_zone = tz.gettz('Asia/Tokyo')
    
    iso_to_local = datetime.fromisoformat(utc_time).astimezone(to_zone)
    dt = str(iso_to_local.replace(tzinfo=None).isoformat(' ', timespec='seconds'))
    return dt
chixcy
  • 51
  • 9
  • 1
    I believe you had tried somethings, right? Please post your try as well. And additionally try to read [ask] and [mre] as well. – imxitiz Aug 25 '21 at 09:30
  • 1
    have a look at the docs and you find [datetime.fromisoformat](https://docs.python.org/3/library/datetime.html#datetime.datetime.fromisoformat). now combine with [astimezone](https://docs.python.org/3/library/datetime.html#datetime.datetime.astimezone) and you have it: `datetime.fromisoformat("2021-08-17T20:03:36.480-07:00").astimezone(None)`... – FObersteiner Aug 25 '21 at 09:35
  • Besides @Xitiz's observation -- and to help you make it better -- you should realize that if you want to translate something (space or time) you need a reference starting point (right?). In other words, you need to know the original timezone, then apply the corresponding _delta_ in time. – Brandt Aug 25 '21 at 09:36
  • 1
    When giving a [mre] you should include the _error_, which is presumably related to the fact that you're treating a string as if it was a datetime (you never actually use the imported `datetime`) and `tzlocal` isn't defined. – jonrsharpe Aug 25 '21 at 09:39
  • 1
    @chixy You want to convert `2021-08-17T20:03:36.480-07:00` into `2020-01-06 00:00:00` are you saying this or, I am not understanding? – imxitiz Aug 25 '21 at 09:46
  • @xitiz yes this is what i want – chixcy Aug 25 '21 at 09:50
  • @chixy Does [Convert UTC datetime string to local datetime](https://stackoverflow.com/a/4771733/12446721) solves your problem? – imxitiz Aug 25 '21 at 09:55
  • 1
    @Xitiz: in the linked q&a, the iso string has no UTC offset specified, so UTC is set explicitly as tzinfo in the accepted answer. If you do the same here, the result is incorrect. – FObersteiner Aug 25 '21 at 10:18
  • @chixy You aren't supposed to answer your question in question. If you has found the solution which is not here then you may write your own answer, or you had already accepted the answer, so that mean that answer worked for you. If you want to change some minor changes the ask the person to change to . – imxitiz Aug 25 '21 at 14:34

2 Answers2

0

Before you change timezone you need to convert conv_time to datetime object with strptime. Then, to change the format you simply use strftime.

For example:

from datetime import datetime
from dateutil import tz


def convert_utc_local(utc_time):
    time = datetime.strptime(utc_time, '%Y-%m-%dT%H:%M:%S.%f%z')
    # Convert time zone
    local_time = time.astimezone(tz.tzlocal())
    return local_time.strftime('%Y-%m-%d %H:%M')

print(convert_utc_local("2021-08-17T20:03:36.480-07:00"))
prody
  • 194
  • 1
  • 11
0

Make use of datetime.fromisoformat. It gives clean code and is efficient. There's also the "inverse" method available, datetime.isoformat, which returns a string from a datetime object.

Converter can be written as a one-liner:

from datetime import datetime

# iso_to_localdt converts an ISO8601 date/time string to datetime object,
# representing local time (OS setting).
iso_to_localdt = lambda t: datetime.fromisoformat(t).astimezone(None)

In use:

dt = iso_to_localdt("2021-08-17T20:03:36.480-07:00")

print(repr(dt))
# datetime.datetime(2021, 8, 18, 5, 3, 36, 480000, tzinfo=datetime.timezone(datetime.timedelta(seconds=7200), 'Mitteleuropäische Sommerzeit'))

print(dt.isoformat(' ', timespec='seconds'))
# 2021-08-18 05:03:36+02:00

# to get local time without the UTC offset specified, i.e. naive datetime:
print(str(dt.replace(tzinfo=None).isoformat(' ', timespec='seconds')))
# 2021-08-18 05:03:36

Note: your time zone might be different.

FObersteiner
  • 22,500
  • 8
  • 42
  • 72