AccessTokenRefreshError: Google Spreadsheet API with oAuth 2.0 Service Account of App Engine App

前端 未结 1 1598
死守一世寂寞
死守一世寂寞 2020-12-10 10:09

I\'m trying to access a Google Spreadsheet via the GData API using oAuth 2.0 service-account credentials created for a Python 2.7 app hosted on Google App Engine.

相关标签:
1条回答
  • 2020-12-10 10:48

    I've figured out that calling SignedJwtAssertionCredentials with-out the sub parameter (for the "impersonated" user) will not produce AccessTokenRefreshError: access_denied

    import os
    import httplib2
    from google.appengine.api import memcache
    from apiclient.discovery import build
    from oauth2client.client import SignedJwtAssertionCredentials
    import gdata.spreadsheets.client
    import gdata.spreadsheet.service
    
    # AppAssertionCredentials is not supported in gdata python client library,
    # so we use SignedJwtAssertionCredentials with the credential 
    # file of this service account.
    # Load the key in PKCS 12 format that you downloaded from the Google API
    # Console when you created your Service account.
    clientEmail = '10346........-g3dp......................3m1em8@developer.gserviceaccount.com'
    p12File = 'app.p12'
    path = os.path.join(ROOT_DIR, 'data', 'oAuth2', p12File)
    impersonateUser = 'user@mygoogleappsdomain.com'
    spreadsheetKey = '1mcJHJ...................................juQMw' # ID copied from URL of desired spreadsheet in Google Drive
    with open(path) as f:
        privateKey = f.read()
        f.close()
    
    # Getting credentials with AppAssertionCredentials only worked successfully
    # for Google API Client Library for Python, e.g. accessing file's meta-data.
    # So we use SignedJwtAssertionCredentials, as suggested in
    # http://stackoverflow.com/questions/16026286/using-oauth2-with-service-account-on-gdata-in-python
    # but with-out the sub parameter!
    credentials = SignedJwtAssertionCredentials(
        clientEmail,
        privateKey,
        scope=(
            'https://www.googleapis.com/auth/drive.file ',
            # added the scope above as suggested somewhere else,
            # but error occurs with and with-out this scope
            'https://www.googleapis.com/auth/drive',
            'https://spreadsheets.google.com/feeds',
            'https://docs.google.com/feeds'
        ),
    #    sub=impersonateUser
    )
    
    http = httplib2.Http()
    http = credentials.authorize(http)
    auth2token = gdata.gauth.OAuth2TokenFromCredentials(credentials)
    # this pattern would eventually also work using SpreadsheetsService()
    # SpreadsheetsService methods are different from SpreadsheetsClient, though
    #srv = gdata.spreadsheet.service.SpreadsheetsService()
    #srv = auth2token.authorize(srv)
    
    clt = gdata.spreadsheets.client.SpreadsheetsClient()
    clt = auth2token.authorize(clt)
    
    wks = clt.get_worksheets(spreadsheetKey)
    # works now!
    
    0 讨论(0)
提交回复
热议问题