问题
I have implemented the python code here below based on the documentation in order to access a spreadsheet accessible through a public link. It works once every hour. If I execute a few seconds after a success, I receive an error :
Error opening spreadsheet no element found: line 1, column 0
Assumption: The access token has an expiry date of 1 hour. So the appengine would proceed to a token refresh after an hour, resetting the whole.
Question: This code requests a new token for each request. So what should I do ? Save the token ? When I try the token_to_blob in order to save the token, I get an error : Scope undefined
Thanks in advance for your help !
try :
credentials = AppAssertionCredentials(scope=('https://www.googleapis.com/auth/drive','https://spreadsheets.google.com/feeds','https://docs.google.com/feeds'))
logging.info("credentials")
http_auth = credentials.authorize(httplib2.Http())
authclient = build('oauth2','v2',http=http_auth)
auth2token = gdata.gauth.OAuth2TokenFromCredentials(credentials)
except Exception as details:
logging.error("Error Google credentials %s"%details)
return "Error"
try :
gd_client = gdata.spreadsheets.client.SpreadsheetsClient()
gd_client = auth2token.authorize(gd_client)
feed = gd_client.GetListFeed(<spreadsheetKey>,1)
except Exception as details:
logging.error("Error opening spreadsheet %s"%details)
return "Error"
回答1:
I finally declared the credentials & the token as global. In this case, it was working for several subsequent requests but after 1 hour, the token was invalid.
I tested with the method access_token_expired but this method always returned false.
So, I finally execute the refresh systematically and it works. Not elegant but functional. Another option would be to store the time of next refresh and only refresh after 1 hour.
Your comments are welcome for elegant alternatives.
I did not try gspread since the rest of the code was already functional for gdata.spreadsheets but perhaps I should.
from oauth2client.contrib.appengine import AppAssertionCredentials
from oauth2client.client import Credentials
from oauth2client.service_account import ServiceAccountCredentials
from googleapiclient.discovery import build
import httplib2
global credentials
global auth2token
try :
credentials = AppAssertionCredentials(scope=('https://www.googleapis.com/auth/drive','https://spreadsheets.google.com/feeds','https://docs.google.com/feeds'))
http_auth = credentials.authorize(httplib2.Http())
authclient = build('oauth2','v2',http=http_auth)
auth2token = gdata.gauth.OAuth2TokenFromCredentials(credentials)
except Exception as details:
logging.error("Error Google credentials %s"%details)
class importFromSpreadsheet(webapp2.RequestHandler):
def __importFromSpreadsheet(self,u):
try :
credentials._refresh(httplib2.Http())
except Exception as details:
logging.error("Error refreshing Google credentials %s"%details)
...
try :
gd_client = gdata.spreadsheets.client.SpreadsheetsClient()
gd_client = auth2token.authorize(gd_client)
feed = gd_client.GetListFeed(u,1)
except Exception as details:
logging.error("Error opening 1st spreadsheet %s"%details)
return "Error"
来源:https://stackoverflow.com/questions/36081860/access-google-spreadsheet-from-google-appengine-with-service-account-working-o