문자열로 되어 있는 시간을 Datetime 객체로 변경하는 방법은 많이 찾아 볼 수 있습니다. 여기서는 기존에 존재하는 방법과 추가 설치 모듈로 좀 더 간편하게 사용하는 방법을 설명하겠습니다.

1. Datetime

파이썬에 내장되어 있는 Datetime 패키지를 사용하여 아래와 같이 변환을 할 수 있습니다.

import datetime

date_time_str = '2018-06-29 08:15:27.243860'  
date_time_obj = datetime.datetime.strptime(date_time_str, '%Y-%m-%d %H:%M:%S.%f')

print('Date-time:', date_time_obj)


# Date-time: 2018-06-29 08:15:27.243860


흔히 사용하는 포맷은 ISO 8601으로  YYYY-MM-DDTHH:MM:SS.mmmmmm 와 같이 표현하고 있습니다. 이와 같은 포맷만 들어온다면 그대로 사용해도 무방하지만 아래와 같이 여러 타입이 존재한다면 고려할 사항이 많아집니다.

"Jun 28 2018 at 7:40AM" -> "%b %d %Y at %I:%M%p"
"September 18, 2017, 22:19:55" -> "%B %d, %Y, %H:%M:%S"
"Sun,05/12/99,12:30PM" -> "%a,%d/%m/%y,%I:%M%p"
"Mon, 21 March, 2015" -> "%a, %d %B, %Y"
"2018-03-12T10:12:45Z" -> "%Y-%m-%dT%H:%M:%SZ"

timezone 지정

위처럼 문자열을 datetime 객체로 변환하거나 현재 날짜+시간을 호출하면 현재 로컬시간을 기준으로 호출이 됩니다.

now = datetime.datetime.now()
print(now)


# 2019-02-02 15:54:07.244639


여기서 구한 현재 시간을 뉴욕시간대로 변경하고자 하면 아래와 같이 복잡한 절차를 거치게 됩니다. 또한 현재 시간이 뉴욕시간대로 변환되지 않고 timezone만 추가된 형태를 확인할 수 있습니다.

import datetime as dt
import pytz

date_time_obj = dt.datetime.now()

print('now:', date_time_obj)

timezone = pytz.timezone('America/New_York')
timezone_date_time_obj = timezone.localize(date_time_obj)

print(timezone_date_time_obj)
print(timezone_date_time_obj.tzinfo)


# now: 2019-02-02 15:56:15.197103
# 2019-02-02 15:56:15.197103-05:00
# America/New_York


datetime 패키지로만 충분히 변환하거나 시간대를 바꿀 수 있지만 다른 모듈을 설치하면 좀 더 간편하게 사용할 수 있습니다.

2. dateutil

dateutil 모듈을 설치하여 사용하면 문자열의 시간 포맷을 걱정할 필요가 없습니다.

from dateutil.parser import parse

date_array = [
    '2018-06-29 08:15:27.243860',
    'Jun 28 2018  7:40AM',
    'Jun 28 2018 at 7:40AM',
    'September 18, 2017, 22:19:55',
    'Sun, 05/12/1999, 12:30PM',
    'Mon, 21 March, 2015',
    '2018-03-12T10:12:45Z',
    '2018-06-29 17:08:00.586525+00:00',
    '2018-06-29 17:08:00.586525+05:00',
    'Tuesday , 6th September, 2017 at 4:30pm'
]

for date in date_array:
    print('Parsing: ' + date)
    dt = parse(date)
    print(dt.date())
    print(dt.time())
    print(dt.tzinfo)
    print()



# Parsing: 2018-06-29 08:15:27.243860
# 2018-06-29
# 08:15:27.243860
# None

# Parsing: Jun 28 2018  7:40AM
# 2018-06-28
# 07:40:00
# None

# Parsing: Jun 28 2018 at 7:40AM
# 2018-06-28
# 07:40:00
# None

# Parsing: September 18, 2017, 22:19:55
# 2017-09-18
# 22:19:55
# None

# Parsing: Sun, 05/12/1999, 12:30PM
# 1999-05-12
# 12:30:00
# None

# Parsing: Mon, 21 March, 2015
# 2015-03-21
# 00:00:00
# None

# Parsing: 2018-03-12T10:12:45Z
# 2018-03-12
# 10:12:45
# tzutc()

# Parsing: 2018-06-29 17:08:00.586525+00:00
# 2018-06-29
# 17:08:00.586525
# tzutc()

# Parsing: 2018-06-29 17:08:00.586525+05:00
# 2018-06-29
# 17:08:00.586525
# tzoffset(None, 18000)

# Parsing: Tuesday , 6th September, 2017 at 4:30pm
# 2017-09-06
# 16:30:00
# None


위 예시처럼 시간포맷을 알 필요가 없다는 장점이 있지만 timezone을 지정하지 않으면 로컬 시간을 바라보고 있는 것을 확인할 수 있습니다.

3. maya

마야 또한 위의 dateutil 모듈과 같이 시간 포맷에 상관없이 변환할 수 있습니다.

import maya

date_array = [  
    '2018-06-29 08:15:27.243860',
    'Jun 28 2018  7:40AM',
    'Jun 28 2018 at 7:40AM',
    'September 18, 2017, 22:19:55',
    'Sun, 05/12/1999, 12:30PM',
    'Mon, 21 March, 2015',
    '2018-03-12T10:12:45Z',
    '2018-06-29 17:08:00.586525+00:00',
    '2018-06-29 17:08:00.586525+05:00',
    'Tuesday , 6th September, 2017 at 4:30pm'
]

for date in date_array:  
    print('Parsing: ' + date)
    dt = maya.parse(date).datetime()
    print(dt)
    print(dt.date())
    print(dt.time())
    print(dt.tzinfo)
    print()


# Parsing: 2018-06-29 08:15:27.243860
# 2018-06-29 08:15:27.243860+00:00
# 2018-06-29
# 08:15:27.243860
# UTC

# Parsing: Jun 28 2018  7:40AM
# 2018-06-28 07:40:00+00:00
# 2018-06-28
# 07:40:00
# UTC

# Parsing: Jun 28 2018 at 7:40AM
# 2018-06-28 07:40:00+00:00
# 2018-06-28
# 07:40:00
# UTC

# Parsing: September 18, 2017, 22:19:55
# 2017-09-18 22:19:55+00:00
# 2017-09-18
# 22:19:55
# UTC

# Parsing: Sun, 05/12/1999, 12:30PM
# 1999-05-12 12:30:00+00:00
# 1999-05-12
# 12:30:00
# UTC

# Parsing: Mon, 21 March, 2015
# 2015-03-21 00:00:00+00:00
# 2015-03-21
# 00:00:00
# UTC

# Parsing: 2018-03-12T10:12:45Z
# 2018-03-12 10:12:45+00:00
# 2018-03-12
# 10:12:45
# UTC

# Parsing: 2018-06-29 17:08:00.586525+00:00
# 2018-06-29 17:08:00.586525+00:00
# 2018-06-29
# 17:08:00.586525
# UTC

# Parsing: 2018-06-29 17:08:00.586525+05:00
# 2018-06-29 12:08:00.586525+00:00
# 2018-06-29
# 12:08:00.586525
# UTC

# Parsing: Tuesday , 6th September, 2017 at 4:30pm
# 2017-09-06 16:30:00+00:00
# 2017-09-06
# 16:30:00
# UTC


dateutil과 다르게 maya는 로컬시간을 바라보지 않고 기본적으로 UTC로 지정합니다.

dateutil과 maya의 차이점

두 모듈은 비슷해 보이지만 timezone에 대해 아주 큰 차이가 있습니다.

import maya
import dateutil.parser

date_array = [  
    '2018-06-29 17:08:00.586525+05:00',
    '2018-06-29 17:08:00.586525',
]


for date in date_array:  
    print('Parsing: ' + date)
    maya_dt = maya.parse(date).datetime()
    dateutil_dt = dateutil.parser.parse(date)

    print('maya: ')
    print(maya_dt)
    print(maya_dt.tzinfo)

    print('dateutil: ')
    print(dateutil_dt)
    print(dateutil_dt.tzinfo)

    print()


# Parsing: 2018-06-29 17:08:00.586525+05:00
# maya: 
# 2018-06-29 12:08:00.586525+00:00
# UTC


# dateutil: 
# 2018-06-29 17:08:00.586525+05:00
# tzoffset(None, 18000)

# Parsing: 2018-06-29 17:08:00.586525
# maya: 
# 2018-06-29 17:08:00.586525+00:00
# UTC


# dateutil: 
# 2018-06-29 17:08:00.586525
# None


maya의 경우는 문자열에 존재하는 +05:00을 계산하여 timezone을 UTC로 세팅합니다. 위의 경우 17시에 +05:00가 존재하여 5시간을 뺀 후, timezone을 UTC라고 보여주고 있습니다. 반면 dateutil은 시간계산을 하지 않고 +05:00을 저장하게 됩니다. 

또한 timezone을 변경하거나 세팅할 때도 큰 차이가 존재합니다.

import maya
import dateutil.parser
import pytz
import dateutil

date = '2018-06-29 17:08:00.586525'

print('maya: ')
maya_dt = maya.parse(date)
print('parsing: ', maya_dt.datetime())
maya_dt = maya_dt.datetime(to_timezone='America/New_York', naive=False)


print('(timezone) America/New_York: ', maya_dt)
print(maya_dt.tzinfo)

print('------------------')

print('dateutil: ')
dateutil_dt = dateutil.parser.parse(date)
print('parsing: ', dateutil_dt)

timezone = pytz.timezone('America/New_York')
dateutil_dt = timezone.localize(dateutil_dt)

print('(timezone) America/New_York: ', dateutil_dt)
print(timezone)




# maya: 
# parsing:  2018-06-29 17:08:00.586525+00:00
# (timezone) America/New_York:  2018-06-29 13:08:00.586525-04:00
# America/New_York
# ------------------
# dateutil: 
# parsing:  2018-06-29 17:08:00.586525
# (timezone) America/New_York:  2018-06-29 17:08:00.586525-04:00
# America/New_York


maya의 경우, 파싱한 시간대에서 지정한 timezone의 시간만큼 계산하여 보여주지만 dateutil의 경우 datetime과 같이 시간은 계산하지 않고 timezone만 붙여서 보여주고 있습니다.

결론

문자열에서 datetime 객체로 변환하는 것은 third-party인 maya나 dateutil을 사용하는 것이 좋습니다. 또한 timezone을 변경하거나 각 다르게 사용할 경우, UTC로 변환하여 실행하는 서버 및 로컬의 시간대를 사용하지 않도록 하는 것이 중요합니다.

+ Random Posts