python – 访问Calendar API V3的GAE中的OAuth2身份验证(域托管)

我正在用Python开发一个Google App Engine应用程序.我正在使用:

> Google Calendar API v3(用于访问我自己域中的日历.因此,这是我的域中安装的Google Apps)
>适用于Python的Google API客户端库.
> OAuth2验证我的域用户(name@mydomain.com)

我以为我必须使用服务帐户,因为这样:

“如果您的App Engine应用程序需要调用API来访问应用程序项目所拥有的数据,则可以使用服务帐户简化OAuth 2.0”

取自https://developers.google.com/api-client-library/python/platforms/google_app_engine#ServiceAccounts

但我不确定我是否误解了某些东西.我的方案(GAE应用尝试在我自己的域中访问Google Apps)是服务帐户的候选人吗?

我已经尝试了几种方法来处理OAuth2:

>使用服务帐户,如上所述
>使用Python API客户端库提供的Python装饰器(OAuth2Decorator和OAuth2DecoratorFromClientSecrets)

在这两种情况下,我都会遇到同样的错误:

>在我的本地机器上执行:请求https://www.googleapis.com/calendar/v3/calendars/primary/events?alt=json时的HttpError 401返回“Invalid Credentials”(我将事件创建为JSON对象,后面是:https://developers.google.com/google-apps/calendar/v3/reference/events/insert#examples).错误堆栈跟踪:https://dl.dropbox.com/u/61566717/output/local_error
>部署到GAE:错误310(net :: ERR_TOO_MANY_REDIRECTS).字符串“_ah / login_required?continue =”会多次附加在url的末尾.
使用API​​控制台生成的客户端ID /客户端密钥或服务帐户参数可能存在问题吗?我应该重新制作它们吗?

我完全迷失了.有线索吗?

提前谢谢了

最佳答案
您不需要服务帐户,但使用一个可能很有用.有关App Engine的服务帐户存在一些棘手的问题,详细信息请参见reported issue中的库.尝试使用Google APIs explorer,看看是否有助于阐明如何使用API​​.

只要您使用可以访问这些日历的帐户授权应用程序,您就可以访问它们,无论这是否在Google App Engine上.

在这里使用OAuth2Decorator是最好的选择.如果您举一个具体的例子,我很乐意提供一些代码片段来完成任务.

查看最近提出的类似问题:How can I log in to an arbitrary user in appengine for use with the Drive SDK?这似乎是您的使用案例,除非您想使用Calendar API而不是Drive API.

更新:

在阅读完other post之后(我会考虑关闭,如果我是你),我已经拼凑了一个样本,可以帮助您了解如何使用装饰器.

首先,要使用您的凭据,以便您的应用可以让用户授权它:

from apiclient.discovery import build
import json
from oauth2client.appengine import OAuth2Decorator
import webapp2

decorator = OAuth2Decorator(
  client_id='your_client_id',
  client_secret='your_client_secret',
  scope='https://www.googleapis.com/auth/calendar')

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

然后,您的主页面将确保您的用户已登录,@ decorator.oauth_required装饰器将在您的数据存储区中保存OAuth 2.0令牌.

class MainPage(webapp2.RequestHandler):
  @decorator.oauth_required
  def get(self):
    # This will force the user to go through OAuth
    self.response.write(...)
    # show some page to them

在您显示给它们的页面上,您可能会有一个POST到/ add-event的表单,此AddEvent处理程序将能够使用该令牌发出请求.我们使用@ decorator.oauth_aware而不是使用oauth_required来允许优雅的失败.如果App Engine在请求中检测到用户的浏览器会话(如果他们从表单发布,则会是这些用户),那么您的应用将在进行经过身份验证的日历请求之前从数据存储中查找OAuth 2.0凭据.

class AddEvent(webapp2.RequestHandler):
  @decorator.oauth_aware
  def post(self):
    if decorator.has_credentials():          
      event_name = self.request.get('event-name')
      some_event = {...}  # Create event here
      # Documented at
      # https://developers.google.com/google-apps/calendar/v3/reference/events/insert

      http = decorator.http()
      # Using 'primary' will insert the event for the current user
      request = service.events().insert(calendarId='primary', body=some_event)
      inserted = request.execute(http=http)
      self.response.write(json.dumps(inserted))
    else:
      self.response.write(json.dumps({'error': 'No credentials'})

最后,为了确保所有这些路由都有效,您需要为每个处理程序和装饰器使用的OAuth 2.0处理程序定义路由:

app = webapp2.WSGIApplication([
    ('/', MainPage),
    ('/add-event', AddEvent),
    (decorator.callback_path, decorator.callback_handler())
    ],
    debug=True)

额外参考:

https://developers.google.com/api-client-library/python/platforms/google_app_engine

https://developers.google.com/google-apps/calendar/v3/reference/events/insert

转载注明原文:python – 访问Calendar API V3的GAE中的OAuth2身份验证(域托管) - 代码日志