【问题标题】:Python - problems accessing a Google spreadsheet using an OAuth 2.0 service clientPython - 使用 OAuth 2.0 服务客户端访问 Google 电子表格时出现问题
【发布时间】:2015-09-04 09:31:46
【问题描述】:

我拥有一个 Google 电子表格,我正在尝试通过我正在编写的一个小的 OAuth 2.0 Python 服务客户端访问它,使用 gspreadoauth2client

我在 Google Developers Console 上创建了一个 OAuth 2.0 服务帐户,并且 已与该电子邮件共享电子表格,授予客户端/应用程序对其的访问权限,并将包含凭据的 JSON 密钥文件放入一个小测试脚本中。虽然我能够构建 OAuth 2.0 凭据对象甚至获得电子表格客户端,但在客户端上调用 openall() 时会出现 XML 解析错误:

File "<stdin>", line 1, in <module>
File "/Library/Python/2.7/site-packages/gspread/client.py", line 214, in openall
  feed = self.get_spreadsheets_feed()
File "/Library/Python/2.7/site-packages/gspread/client.py", line 230, in get_spreadsheets_feed
  return ElementTree.fromstring(r.read())
File "/System/Library/Frameworks/Python.framework/Versions/2.7/lib/python2.7/xml/etree/ElementTree.py", line 1301, in XML
  return parser.close()
File "/System/Library/Frameworks/Python.framework/Versions/2.7/lib/python2.7/xml/etree/ElementTree.py", line 1654, in close
  self._raiseerror(v)
File "/System/Library/Frameworks/Python.framework/Versions/2.7/lib/python2.7/xml/etree/ElementTree.py", line 1506, in _raiseerror
  raise err
xml.etree.ElementTree.ParseError: no element found: line 1, column 0

代码如下:

import gspread
from gspread import Client
from gspread.httpsession import HTTPSession
from oauth2client.client import SignedJwtAssertionCredentials

OAuth2_JSON_key = {
  "client_auth_scope": "https://spreadsheets.google.com/feeds",
  "myspreadsheet_keys":
  {
    "myspreadsheet_key": "XXXX"
  },
  "private_key_id": "XXXX",
  "private_key": "XXXX",
  "client_email": "XXXXgkcvcke@developer.gserviceaccount.com",
  "client_id": "XXXXgkcvcke.apps.googleusercontent.com",
  "client_type": "service_account"
}

OAuth2_credentials = SignedJwtAssertionCredentials(
    OAuth2_JSON_key['client_email'],
    OAuth2_JSON_key['private_key'],
    OAuth2_JSON_key['client_auth_scope']
)

persistent_session = HTTPSession(headers={'Connection':'Keep-Alive'})

spreadsheet_client = gspread.Client(
    auth=OAuth2_credentials,
    http_session=persistent_session
)

spreadsheets = spreadsheet_client.openall()

【问题讨论】:

  • 如果我不使用gspread.Client(auth=OAuth2_credentials,http_session=persistent_session) 而只是使用gspread.authorize(OAuth_credentials),那么我会得到一个不为空的电子表格客户端。
  • 我认为gspread.Client 中存在错误,但我无法在 github repo github.com/burnash/gspread 上提出问题。

标签: python oauth-2.0 google-api gspread


【解决方案1】:

据我所见,使用 insert_rowgpsread.Client() 方法会导致问题。我将代码切换回gspread.authorize(),它工作得非常好。

【讨论】:

    【解决方案2】:

    我对此不太熟悉,但我遇到了类似的错误。您应该尝试从您的谷歌开发者控制台下载 json 密钥并运行:

    json_key = json.load(open('****.json'))  #Downloaded from google
    credentials = SignedJwtAssertionCredentials(json_key['client_email'],   json_key['private_key'], scope)
    gc = gspread.authorize(credentials)
    

    以这种方式访问​​我的电子表格没有任何错误。不要忘记与您的客户电子邮件共享您的电子表格。

    【讨论】:

    • 这就是我现在的连接代码。所以我认为我们可以说这绝对有效。但是通常似乎存在一些不可预测和意外的行为,因为如果您改为使用 gspread.Client(auth=&lt;OAuth2 credentials&gt;, http_session=&lt;persistent HTTP session&gt;) 创建客户端/连接,那么它似乎可以工作,因为有一个客户端,但它的所有电子表格/工作表方法都失败,并生成XML 解析错误。