как один раз пройти аутентификацию с помощью gmail и использовать сгенерированные токены?

from oauth2client.client import OAuth2WebServerFlow
from oauth2client.tools import run_flow
from oauth2client.file import Storage
import requests    

CLIENT_ID = '9453asfasfaksdfh860b1osoiveogstt.apps.googleusercontent.com'
CLIENT_SECRET = '6gRid8wF7TW8asdfasdftX'


flow = OAuth2WebServerFlow(client_id=CLIENT_ID,
                           client_secret=CLIENT_SECRET,
                           scope='https://www.googleapis.com/auth/admin.directory.user https://www.googleapis.com/auth/admin.directory.user.readonly',
                           redirect_uri='http://example.com/auth_return')

storage = Storage('creds.data') #token details stored here
credentials = run_flow(flow, storage)
tokenhere=credentials.access_token #tokens generated

#send get request with token generated using requests
r=requests.get("https://www.googleapis.com/admin/directory/v1/users?domain=mydomain.ocm",headers={'Authorization': 'Bearer {token}'.format(token=tokenhere)})     
result=r.json()

Вот как я успешно прошел аутентификацию в Google и получил пользователей.

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

Но проблема в том, что это происходит каждый раз, когда я запускаю это.

Я знаю, что как только мы авторизуемся в следующий раз, нам не нужно повторять эти шаги снова и снова, а скорее напрямую передавать токен или использовать сохраненный.

Как это реально реализовано. Точных указаний нет. Кто-нибудь, пожалуйста, помогите мне в этом. Как и где это сделать. На данный момент мне удалось проверить и получить авторизованный токен.

ДОПОЛНИТЕЛЬНО: то, как я получаю токены, может выглядеть по-другому, потому что я пытаюсь получить токен непосредственно в консоли и поэтому использовал для этой цели один модуль и, таким образом, выглядит так


person Tara Prasad Gurung    schedule 04.05.2017    source источник


Ответы (1)


Если я правильно понимаю, это должно быть то, что вы ищете:

from oauth2client.client import OAuth2WebServerFlow
from oauth2client.tools import run_flow
from oauth2client.file import Storage
import requests
import os


CLIENT_ID = '9453asfasfaksdfh860b1osoiveogstt.apps.googleusercontent.com'
CLIENT_SECRET = '6gRid8wF7TW8asdfasdftX'

def get_new_token():
    flow = OAuth2WebServerFlow(client_id=CLIENT_ID,
                               client_secret=CLIENT_SECRET,
                               scope='https://www.googleapis.com/auth/admin.directory.user https://www.googleapis.com/auth/admin.directory.user.readonly',
                               redirect_uri='http://example.com/auth_return')
    storage = Storage('creds.data') #token details stored here
    credentials = run_flow(flow, storage)
    tokenhere=credentials.access_token #tokens generated
    return tokenhere

def retrieve_saved_token():
    if os.path.exists('creds.data'):
        with open('creds.data') as creds:
            tokenhere = creds.read()  # Change to reflect how the token data is reflected in your 'creds.data' file
    return tokenhere

def request_page(tokenhere):
    r = requests.get("https://www.googleapis.com/admin/directory/v1/users?domain=mydomain.com",
                     headers={'Authorization': 'Bearer {token}'.format(token=tokenhere)})
    result = r.json()

try:
    tokenhere = retrieve_saved_token()
    request_page(tokenhere)
except:
    tokenhere = get_new_token()
    request_page(tokenhere)

Здесь разбиты все компоненты того, что было сделано

Просто чтобы быть более объектно-ориентированным, я переместил вашу логику в функции:

def get_new_token():
    flow = OAuth2WebServerFlow(client_id=CLIENT_ID,
                               client_secret=CLIENT_SECRET,
                               scope='https://www.googleapis.com/auth/admin.directory.user https://www.googleapis.com/auth/admin.directory.user.readonly',
                               redirect_uri='http://example.com/auth_return')
    storage = Storage('creds.data') #token details stored here
    credentials = run_flow(flow, storage)
    tokenhere=credentials.access_token #tokens generated
    return tokenhere

def request_page(tokenhere):
    r = requests.get("https://www.googleapis.com/admin/directory/v1/users?domain=mydomain.com",
                     headers={'Authorization': 'Bearer {token}'.format(token=tokenhere)})
    result = r.json()

Я также добавил новую функцию для извлечения сохраненного токена, если файл токена существует:

def retrieve_saved_token():
    if os.path.exists('creds.data'):
        with open('creds.data') as creds:
            tokenhere = creds.read()  # Change to reflect how the token data is reflected in your 'creds.data' file
    return tokenhere

Наконец мы добираемся до той части, где на самом деле работает логика.

Сначала он пытается получить токен из файла, если файл не существует, будет возбуждено исключение, и вы перейдете к логике исключения. То, как написана логика попытки, также поймает, если будет успешно получен токен, но если срок действия этого токена истек, логика запроса должна вызвать исключение.

В логике исключения он выполняет вашу исходную логику получения нового токена и запроса страницы с этим токеном.

try:
    tokenhere = retrieve_saved_token()
    request_page(tokenhere)
except:
    tokenhere = get_new_token()
    request_page(tokenhere)

ИЗМЕНИТЬ 1

Я предполагаю, что вы не просто хотите запросить страницу, но и манипулировать данными на странице. Для этого у вас будет другая функция, которая извлекает данные со страницы, ища теги в созданном вами «результате» объекта json. Я называю эту функцию «do_something_with_request_function()» в приведенном ниже коде.

Первый Try/Except проверит, существует ли файл токена, если он существует, то возьмет этот токен и использует его, если нет, то сгенерирует новый токен.

Вторая попытка, за исключением того, что есть шанс передать токен с истекшим сроком действия. Итак, давайте предположим два сценария.
Сценарий 1: вы передаете действительный токен, вы получаете нужную страницу в запросе. Ваш метод, который вы используете для анализа данных на странице, будет искать определенные поля, которые существуют на этой странице, все работает нормально.
Сценарий 2: вы передаете недопустимый токен, вы получаете страницу с ошибкой для просроченного/недействительного токена. Ваш метод, который анализирует эту страницу в json и пытается манипулировать данными, выдаст ошибку, если не найдет значение, которое обычно существует на фактической странице, на которую вы пытаетесь попасть. Это заставит код перейти к блоку исключений.
Блок исключений создает новый токен, передает его для повторного запроса страницы и правильно обрабатывает ваши данные.

try:
    tokenhere = retrieve_saved_token()
except:
    tokenhere = get_new_token()
try:
    request_page(tokenhere)
    do_something_with_request_function(result)
except:
    tokenhere = get_new_token()
    request_page(tokenhere)
    do_something_with_request_function(result)
person HackerShark    schedule 04.05.2017
comment
так что все дело в получении токена из сохраненного местоположения. Но как насчет срока действия токена, как с этим справиться, что можно сделать для этого - person Tara Prasad Gurung; 04.05.2017
comment
Я изменил логику комментариями. Новый код указан в разделе EDIT 1. Это должно обрабатывать ваш сценарий, если срок действия токена истекает. - person HackerShark; 05.05.2017
comment
При этом нам необходимо повторно авторизоваться. Если мы не используем токен обновления, создание нового токена означает повторную авторизацию пользователя, которую он сделал один раз. Верно - person Tara Prasad Gurung; 06.05.2017
comment
Хорошо, но как на самом деле реализовать обновление токена, при просмотре учетных данных = run_flow (поток, хранилище) учетные данные также возвращают значение refresh_token. Но можно найти правильный способ его реализации. Чтобы пользователям снова не требовалась авторизация - person Tara Prasad Gurung; 06.05.2017
comment
Я не слишком хорошо знаком с тем, как работает токен обновления, но я нашел эти две другие ссылки на stackoverflow, которые, похоже, объясняют способы его обработки. первая ссылка вторая ссылка @TaraPrasadGurung - person HackerShark; 10.05.2017