Поточно-безопасная клиентская библиотека на движке приложения (Python)

Я нашел небольшой образец кода о вставке bigquery в один из репозиториев git Google.

https://github.com/GoogleCloudPlatform/python-docs-samples/blob/master/appengine/standard/bigquery/main.py

Если вы видите app.yaml, в нем говорится, что этот код должен быть потокобезопасным, но если я заглянул в документацию клиентской библиотеки (https://developers.google.com/api-client-library/python/guide/thread_safety) он не должен быть потокобезопасным. Я немного запутался, мой следующий код является потокобезопасным или нет? Он работает на стандартном env движка приложений.

import pprint

from googleapiclient.discovery import build
from oauth2client.client import GoogleCredentials


credentials = GoogleCredentials.get_application_default()

# Create the bigquery api client
service = build('bigquery', 'v2', credentials=credentials)

response = service.datasets().list(projectId='PROJECTID').execute()

pprint.pprint(response)

---- ОБНОВЛЕНИЕ ---- После ответа Тима я изменил свой код на следующий. Теперь это должно быть хорошо:

import pprint

from googleapiclient.discovery import build
from oauth2client.contrib.appengine import AppAssertionCredentials
import httplib2


credentials = AppAssertionCredentials(scope='https://www.googleapis.com/auth/bigquery')


# Create the bigquery api client
service = build('bigquery', 'v2')


def get():
    # authorize http object with client credentials
    http = credentials.authorize(httplib2.Http())
    response = service.datasets().list(projectId='PROJECTID').execute(http=http)

    pprint.pprint(response)

person Zoltan Molnar    schedule 14.06.2016    source источник


Ответы (1)


Если вы читаете документы, на которые ссылаетесь, там написано

Библиотека google-api-python-client построена на основе библиотеки httplib2, которая не является потокобезопасной. Следовательно, если вы работаете как многопоточное приложение, каждый поток, из которого вы делаете запросы, должен иметь свой собственный экземпляр httplib2.Http ().

Затем они покажут вам, как это сделать. Если вы будете следовать инструкциям, то да, так и будет.

Ваш пример кода слишком прост и не пытается выполнить то, что было описано в документации.

# Create a new Http() object for every request
  def build_request(http, *args, **kwargs):
    new_http = httplib2.Http()
    return apiclient.http.HttpRequest(new_http, *args, **kwargs)
  service = build('api_name', 'api_version', requestBuilder=build_request)

  # Pass in a new Http() manually for every request
  service = build('api_name', 'api_version')
  http = httplib2.Http()
  service.stamps().list().execute(http=http)

Поэтому, если вы попробуете свой код в многопоточной ситуации, он не будет потокобезопасным. Если вы просто пробуете этот код из REPL, то я сомневаюсь, что вы попали в многопоточную ситуацию.

person Tim Hoffman    schedule 14.06.2016
comment
Не могли бы вы взглянуть на обновление? Спасибо - person Zoltan Molnar; 14.06.2016