我目前正在使用Drive v3 API开发App Engine应用程序,但此问题适用于大多数Google API。
由于Drive API在某些操作中有点慢,我想将每个文件处理分成不同的任务。为了做到这一点,我使用延迟库来避免序列化 - 反序列化参数。
主要参数是给定用户已经授权的Drive API服务对象(使用服务帐户和域范围权限)。
代码的简化代码段如下所示:
class Main(webapp2.RequestHandler):
def get(self):
# Authorize and get the Drive service
service = get_drive_service(keyfile, 'user@my-domain.com')
# Iterate through all the (previously retrieved) file list
for file_id in file_list:
# Queue a new task by passing the function and its arguments
deferred.defer(test_drive_service, service, file_id)
def test_drive_service(service, file_id):
# Do a simple Drive operation
response = service.files().get(fileId=file_id).execute()
print response.get('name')
app.yaml 文件的和部分:
handlers:
- url: /_ah/queue/deferred
script: google.appengine.ext.deferred.deferred.application
login: admin
builtins:
- deferred: on
如果我不使用 deferred.defer()
,并直接调用test_drive_service()
函数 ,则没有问题,我得到了正确的文件,信息正确。
但是,使用延迟库时,会引发以下错误:
HttpError: <HttpError 403 when requesting (...) returned "Daily Limit for Unauthenticated Use Exceeded. Continued use requires signup.">
我的配额很好,所以没有达到每日限额。
可能导致此问题的原因是什么? 是否有任何其他特定方法可以将服务对象正确传递给任务队列?
修改
根据要求,这是我的身份验证流程:
def get_drive_service(keyfile, user_email):
'''Builds and returns a Drive service object authorized with the service
account that acts on behalf of the given user.
@param keyfile: generated JSON containing the service account details
@param user_email: the email of the user.
@return: Drive API service instance
'''
from oauth2client.service_account import ServiceAccountCredentials
credentials = ServiceAccountCredentials.from_json_keyfile_dict(keyfile, SCOPES)
credentials = credentials.create_delegated(user_email)
http = credentials.authorize(httplib2.Http())
service = discovery.build('drive', 'v3', http=http)
return service
它基于Google Server-to-server OAuth 2.0 docs(“其他平台”部分),并且在直接调用函数时工作正常,而不是将其添加到任务队列。
答案 0 :(得分:1)
问题可能是service
未正确序列化/反序列化。如果反序列化的服务对象缺少其访问令牌,那将解释403 Quota for unauthenticated use
。
您有一个次要问题,您需要处理访问令牌在您的排队任务转向使用之前到期的可能性(这种情况会引发401状态)。
我不太了解AppEngine上的python建议一个简单的解决方案。我建议发布这是一个标记为appengine / python / google-oauth的新问题。
一个非简单的解决方案是创建一个新的端点,排队的任务可以调用该端点来获取访问令牌。
另一种方法是将auth流程移动到延迟任务中。由于您使用的是服务帐户,因此auth不需要任何用户交互。
答案 1 :(得分:0)
超出未经身份验证的使用的每日限制。继续使用需要注册
表示您未获得授权。您尚未向请求发送访问令牌。您的身份验证有些问题。
您正在使用哪个库我认为您需要找到更好的服务帐户示例。使用创建服务发送密钥文件对我来说不合适。