Python 和 Google 日历 API:时区/时间偏移问题

Python and Google Calendar API : Timezone / Time Offset issues

我在使用 Python、Google 日历 API 和以当地时间运行的客户端设备时遇到时区和时间偏移问题。

我有一个 Raspberry Pi 可以作为共享房间外的预订显示器。定期调用 Python 脚本以从 Google 日历 API 中提取下一个即将到来的日历事件,将结果拆分为变量,然后将这些变量传递回 bash调用它的脚本。

我是在冬天建造它的——当时英国的时区与 UTC 时区相同——而且它运行良好。现在,在英国夏令时,它没有。比较时间 objects 以检查会议是否正在进行中不起作用,房间在没有时显示为可用。

我已经阅读和阅读(然后是 re-read 和 re-read)关于在 Python 中使用时区和时间偏移的文章和解释,但我无法理解它。我不太了解 object-based 编程,这也无济于事,因此提供的示例脚本对我来说意义不大!

理想情况下,我希望一切都使用当地时间。 Raspberry Pi 已连接到互联网并自动更新其时间,Google 日历已正确设置为英国时区。我怎样才能让所有时间参考 'local',所以 Python 脚本中所有地方的时间 objects 总是英国当前时间?

请帮忙。 Stack Overflow 在过去一直是丰富的知识来源,我从来不需要自己问一个问题,但这让我的大脑受伤了!谢谢!

这就是我得到的,它是 Google 自己的示例脚本的修改版本:

    service = build('calendar', 'v3', credentials=creds)

    # Call the Calendar API
    timeStamp_now = datetime.datetime.utcnow()
    timeStamp_12 = timeStamp_now + timedelta(hours = 12)
    now = timeStamp_now.isoformat() + 'Z' # 'Z' indicates UTC time
    now12 = timeStamp_12.isoformat() + 'Z' # 'Z' indicates UTC time
    events_result = service.events().list(calendarId='###############@resource.calendar.google.com', timeZone="Europe/London", timeMin=now,
                                        maxResults=1, singleEvents=True, showDeleted=False, timeMax=now12,
                                        orderBy='startTime').execute()
    events = events_result.get('items', [])

    if not events:
        print('meetingStart="NoEvents"')
    for event in events:
        startTime=event['start'].get('dateTime')
        endTime=event['end'].get('dateTime')
        eventTitle=event['summary']
        eventOrganizer=event['creator'].get('email')
        try:
                eventConferencing=event['conferenceData'].get('conferenceSolution').get('name')
        except:
                eventConferencing=(' ')
        if startTime <= now <= endTime:
                inProgress=('true')
        else:
                inProgress=('false')
        safeEventTitle= ""
        for i in eventTitle:
                num = ord(i)
                if (num >=0) :
                        if (num <=127) :
                                safeEventTitle= safeEventTitle + i

        print('meetingStart="' + startTime + '"')
        print('meetingEnd="' + endTime + '"')
        print('meetingTitle="' + safeEventTitle + '"')
        print('meetingOrganizer="' + eventOrganizer + '"')
        print('meetingConferencing="' + eventConferencing + '"')
        print('meetingInProgress="' + inProgress + '"')

Raspberry Pi的时间设置正确:

pi@raspberrypi:~ $ date
Fri 16 Jul 20:31:38 BST 2021

Python脚本returns这个当运行:

pi@raspberrypi:~ python /myPythonScript.sh
meetingStart="2021-07-16T20:00:00+01:00"
meetingEnd="2021-07-16T21:00:00+01:00"
meetingTitle="Test"
meetingOrganizer="abc@def.com"
meetingConferencing=" "
meetingInProgress="false"

查看下面的示例代码,无论夏令时如何,它都会将您的日期时间调整为 UTC。

代码:

import datetime
import pytz

timeZone = pytz.timezone("Europe/London")
dt = datetime.datetime.utcnow() 

print("datetime now is:\t", dt)
local_dt = timeZone.localize(dt, is_dst=None)
utc_dt = local_dt.astimezone(pytz.utc)
print("Non-DST time is:\t", utc_dt) # prints utc regardless of DST

使用 bst 日期时间的输出:

使用 utc 日期时间输出:

你的情况:

timeZone = pytz.timezone("Europe/London")
dt = datetime.datetime.utcnow()
local_dt = timeZone.localize(dt, is_dst=None)
# timeStamp_now below should be in UTC already
timeStamp_now = local_dt.astimezone(pytz.utc)

参考:

  • How to convert local time string to UTC?
  • Python daylight savings time