如何使用 gspread 缓存 Google 工作表的授权?

How to cache authorization for Google Sheets using gspread?

我正在尝试创建一个简单的函数,将一些数据发布到 Google 表格电子表格。我在 AWS Lambda 中托管此函数。不管怎样,代码看起来有点像这样:

import gspread
from oauth2client.service_account import ServiceAccountCredentials

scope = [
    'https://spreadsheets.google.com/feeds',
    'https://www.googleapis.com/auth/drive'
]
credentials = ServiceAccountCredentials.from_json_keyfile_name(
    'my_creds.json', scope
)
gc = gspread.authorize(credentials)

这非常有效,但不幸的是,这个过程非常缓慢。大部分时间似乎都花在了授权上。所以我的问题是:有没有办法授权和保存授权对象并在接下来的几个请求中重新使用它?一旦有效期用完,该功能可以再次授权。非常感谢任何帮助!

  • 您不想 运行 授权过程每 运行。
  • 您想将授权数据保存到一个文件中,并希望通过加载它来使用 gspread。

如果我的理解是正确的,这个答案怎么样?请将此视为几个可能的答案之一。

在这个答案中,包括访问令牌在内的令牌信息被保存为一个文件。因为 access token 的过期时间是 3600 秒。这个是用的。

流量:

本次回答的流程如下

  1. 检查包含授权数据的令牌文件。
    • 如果文件不存在,授权过程会检索访问令牌并将令牌信息保存到令牌文件中。
    • 如果文件存在且限制时间大于当前时间,则使用从令牌文件中检索到的访问令牌。
    • 如果文件存在且限制时间小于当前时间,则授权过程检索访问令牌并将令牌信息保存到令牌文件中。
  2. 使用访问令牌使用 gspread。

通过此流程,授权过程 运行 每大约 1 小时一次,而不是每 运行 一次。

示例脚本:

在运行脚本之前,请修改token_filecredential_file的变量。

import datetime
import gspread
import json
import os
from oauth2client.service_account import ServiceAccountCredentials
from oauth2client.client import AccessTokenCredentials


token_file = "./access_token.txt"  # token file including the authorization data
credential_file = "###credential file of service account###"
now = int(datetime.datetime.now().timestamp())


def getNewAccessToken():
    scope = ['https://www.googleapis.com/auth/spreadsheets']
    credentials = ServiceAccountCredentials.from_json_keyfile_name(credential_file, scope)
    gc = gspread.authorize(credentials)
    token_response = gc.auth.token_response
    token_response['limitTime'] = token_response['expires_in'] + now - 300
    with open(token_file, mode='w') as f:
        json.dump(token_response, f)
    return token_response['access_token']


def getCredential():
    access_token = ""
    if os.path.exists(token_file):
        with open(token_file) as f:
            token = json.load(f)
        access_token = token['access_token'] if token['limitTime'] > now else getNewAccessToken()
    else:
        access_token = getNewAccessToken()
    return AccessTokenCredentials(access_token, None)


# Use gspread
credentials = getCredential()
gc = gspread.authorize(credentials)
  • 在上面的脚本中,访问令牌的限制时间设置为3600 - 300秒。因为如果限制时间设置为3600秒,在脚本运行ning.
  • 期间可能会出现授权错误

参考:

如果我误解了你的问题,这不是你想要的方向,我深表歉意。