OpenID Connect

Interfejsy API Google OAuth 2.0 mogą być używane zarówno do uwierzytelniania, jak i autoryzacji. W tym dokumencie opisujemy naszą implementację OAuth 2.0 na potrzeby uwierzytelniania, która jest zgodna ze specyfikacją OpenID Connect i ma certyfikat OpenID. Dokumentacja w artykule Używanie protokołu OAuth 2.0 na potrzeby dostępu do interfejsów API Google dotyczy też tej usługi. Jeśli chcesz interaktywnie poznać ten protokół, polecamy OAuth 2.0 Playground od Google. Aby uzyskać pomoc na Stack Overflow, oznacz swoje pytania tagiem „google-oauth”.

Konfigurowanie protokołu OAuth 2.0

Zanim aplikacja będzie mogła używać systemu uwierzytelniania OAuth 2.0 Google do logowania użytkowników, musisz skonfigurować projekt w  , aby uzyskać dane logowania OAuth 2.0, ustawić identyfikator URI przekierowania i (opcjonalnie) dostosować informacje o marce, które użytkownicy widzą na ekranie akceptacji. Możesz też użyć , aby utworzyć konto usługi, włączyć rozliczenia, skonfigurować filtrowanie i wykonać inne zadania. Więcej informacji znajdziesz w  Centrum pomocy.

Uzyskiwanie danych logowania OAuth 2.0

Aby uwierzytelniać użytkowników i uzyskiwać dostęp do interfejsów API Google, potrzebujesz danych logowania OAuth 2.0, w tym identyfikatora klienta i tajnego klucza klienta.

Aby wyświetlić identyfikator klienta i klucz tajny klienta dla danego poświadczenia OAuth 2.0, kliknij następujący tekst: Wybierz poświadczenie . W oknie, które zostanie otwarte, wybierz projekt i żądane poświadczenia, a następnie kliknij opcję Wyświetl .

Lub wyświetl swój identyfikator klienta i API Console tajny klienta ze strony Poświadczenia w API Console :

  1. Go to the Credentials page.
  2. Kliknij nazwę swojego poświadczenia lub ikonę ołówka ( ). Twój identyfikator klienta i sekret znajdują się u góry strony.

Ustawianie identyfikatora URI przekierowania

Identyfikator URI przekierowania ustawiony w  określa, gdzie Google wysyła odpowiedzi na żądania uwierzytelniania.

Aby utworzyć, wyświetlić lub edytować identyfikatory URI przekierowania dla danego poświadczenia OAuth 2.0, wykonaj następujące czynności:

  1. Go to the Credentials page.
  2. W sekcji identyfikatorów klientów OAuth 2.0 na stronie kliknij poświadczenie.
  3. Wyświetl lub edytuj identyfikatory URI przekierowania.

Jeśli na stronie Poświadczenia nie ma sekcji identyfikatorów klientów OAuth 2.0 , Twój projekt nie ma poświadczeń OAuth. Aby je utworzyć, kliknij Utwórz dane logowania .

Dostosowywanie ekranu zgody użytkownika

W przypadku użytkowników proces uwierzytelniania OAuth 2.0 obejmuje ekran zgody, na którym opisane są informacje, które użytkownik udostępnia, oraz obowiązujące warunki. Na przykład podczas logowania użytkownik może zostać poproszony o przyznanie aplikacji dostępu do jego adresu e-mail i podstawowych informacji o koncie. O dostęp do tych informacji możesz poprosić za pomocą parametru scope, który Twoja aplikacja uwzględnia w żądaniu uwierzytelniania. Zakresów możesz też używać do wysyłania próśb o dostęp do innych interfejsów API Google.

Na ekranie zgody użytkownika wyświetlane są też informacje o marce, takie jak nazwa produktu, logo i adres URL strony głównej. Informacjami o marce możesz zarządzać w .

Aby włączyć ekran akceptacji projektu:

  1. Otwórz Consent Screen page w Google API Console .
  2. If prompted, select a project, or create a new one.
  3. Wypełnij formularz i kliknij Zapisz .

W tym oknie dialogowym zgody widać, co zobaczy użytkownik, gdy w żądaniu występuje kombinacja zakresów OAuth 2.0 i Dysku Google. (Ten ogólny dialog został wygenerowany za pomocą narzędzia Google OAuth 2.0 Playground, więc nie zawiera informacji o marce, które byłyby ustawione w  ).

Przykład strony wyrażania zgody
Rysunek 1. Zrzut ekranu strony zgody

Uzyskiwanie dostępu do usługi

Google i firmy zewnętrzne udostępniają biblioteki, które umożliwiają obsługę wielu szczegółów implementacji związanych z uwierzytelnianiem użytkowników i uzyskiwaniem dostępu do interfejsów API Google. Przykłady to usługi Google Identity Servicesbiblioteki klienta Google, które są dostępne na różnych platformach.

Jeśli nie chcesz korzystać z biblioteki, postępuj zgodnie z instrukcjami w pozostałej części tego dokumentu, w której opisano przepływy żądań HTTP, na których opierają się dostępne biblioteki.

Uwierzytelnianie użytkownika

Uwierzytelnianie użytkownika polega na uzyskaniu tokena identyfikatora i jego zweryfikowaniu. Tokeny tożsamości to standardowa funkcja OpenID Connect, która służy do udostępniania w internecie potwierdzeń tożsamości.

Najczęściej stosowane metody uwierzytelniania użytkownika i uzyskiwania tokena identyfikatora to przepływ „serwerowy” i przepływ „niejawny”. Proces po stronie serwera umożliwia serwerowi backendu aplikacji weryfikację tożsamości osoby korzystającej z przeglądarki lub urządzenia mobilnego. Przepływ niejawny jest używany, gdy aplikacja po stronie klienta (zwykle aplikacja JavaScript działająca w przeglądarce) musi mieć bezpośredni dostęp do interfejsów API zamiast korzystać z serwera backendu.

Z tego dokumentu dowiesz się, jak przeprowadzić przepływ po stronie serwera w celu uwierzytelnienia użytkownika. Przepływ niejawny jest znacznie bardziej skomplikowany ze względu na ryzyko związane z bezpieczeństwem obsługi i używania tokenów po stronie klienta. Jeśli musisz wdrożyć przepływ niejawny, zdecydowanie zalecamy użycie usług tożsamości Google.

Przepływ serwera

Aby umożliwić aplikacji korzystanie z tych protokołów i uwierzytelnianie użytkowników, skonfiguruj ją w  . Gdy użytkownik spróbuje zalogować się przez Google, musisz:

  1. Tworzenie tokena stanu chroniącego przed fałszowaniem
  2. Wysyłanie do Google prośby o uwierzytelnienie
  3. Potwierdź token stanu zapobiegający fałszowaniu
  4. Wymiana code na token dostępu i token identyfikatora
  5. Pobieranie informacji o użytkowniku z tokena identyfikatora
  6. Uwierzytelnianie użytkownika

1. Tworzenie tokena stanu chroniącego przed fałszowaniem

Musisz chronić bezpieczeństwo użytkowników, zapobiegając atakom polegającym na fałszowaniu żądań. Pierwszym krokiem jest utworzenie unikalnego tokena sesji, który przechowuje stan między aplikacją a klientem użytkownika. Później dopasujesz ten unikalny token sesji do odpowiedzi uwierzytelniania zwróconej przez usługę logowania OAuth Google, aby sprawdzić, czy żądanie pochodzi od użytkownika, a nie od złośliwego atakującego. Te tokeny są często określane jako tokeny zapobiegające fałszowaniu żądań między witrynami (CSRF).

Dobrym wyborem w przypadku tokena stanu jest ciąg około 30 znaków utworzony za pomocą generatora liczb losowych wysokiej jakości. Innym jest hash wygenerowany przez podpisanie niektórych zmiennych stanu sesji za pomocą klucza, który jest przechowywany w tajemnicy na Twoim backendzie.

Poniższy kod pokazuje, jak generować unikalne tokeny sesji.

PHP

Aby użyć tego przykładu, musisz pobrać bibliotekę klienta interfejsów API Google dla języka PHP.

// Create a state token to prevent request forgery.
// Store it in the session for later validation.
$state = bin2hex(random_bytes(128/8));
$app['session']->set('state', $state);
// Set the client ID, token state, and application name in the HTML while
// serving it.
return $app['twig']->render('index.html', array(
    'CLIENT_ID' => CLIENT_ID,
    'STATE' => $state,
    'APPLICATION_NAME' => APPLICATION_NAME
));

Java

Aby użyć tego przykładu, musisz pobrać bibliotekę klienta interfejsów API Google dla języka Java.

// Create a state token to prevent request forgery.
// Store it in the session for later validation.
String state = new BigInteger(130, new SecureRandom()).toString(32);
request.session().attribute("state", state);
// Read index.html into memory, and set the client ID,
// token state, and application name in the HTML before serving it.
return new Scanner(new File("index.html"), "UTF-8")
    .useDelimiter("\\A").next()
    .replaceAll("[{]{2}\\s*CLIENT_ID\\s*[}]{2}", CLIENT_ID)
    .replaceAll("[{]{2}\\s*STATE\\s*[}]{2}", state)
    .replaceAll("[{]{2}\\s*APPLICATION_NAME\\s*[}]{2}",
    APPLICATION_NAME);

Python

Aby użyć tego przykładu, musisz pobrać bibliotekę klienta interfejsów API Google dla języka Python.

# Create a state token to prevent request forgery.
# Store it in the session for later validation.
state = hashlib.sha256(os.urandom(1024)).hexdigest()
session['state'] = state
# Set the client ID, token state, and application name in the HTML while
# serving it.
response = make_response(
    render_template('index.html',
                    CLIENT_ID=CLIENT_ID,
                    STATE=state,
                    APPLICATION_NAME=APPLICATION_NAME))

2. Wysyłanie do Google żądania uwierzytelnienia

Kolejnym krokiem jest utworzenie żądania HTTPS GET z odpowiednimi parametrami URI. Zwróć uwagę, że we wszystkich krokach tego procesu używamy protokołu HTTPS zamiast HTTP. Połączenia HTTP są odrzucane. Podstawowy identyfikator URI należy pobrać z dokumentu Discovery za pomocą wartości metadanych authorization_endpoint. W dalszej części przyjmujemy, że podstawowy identyfikator URI to https://accounts.google.com/o/oauth2/v2/auth.

W przypadku podstawowego żądania określ te parametry:

  • client_id, który uzyskasz z  .
  • response_type, które w podstawowym żądaniu przepływu kodu autoryzacji powinno mieć wartość code. (Więcej informacji znajdziesz w artykule response_type).
  • scope, która w przypadku podstawowego żądania powinna mieć wartość openid email. (Więcej informacji znajdziesz scope).
  • redirect_uri powinien być punktem końcowym HTTP na Twoim serwerze, który będzie otrzymywać odpowiedź od Google. Wartość musi być dokładnie taka sama jak jeden z autoryzowanych identyfikatorów URI przekierowania dla klienta OAuth 2.0, który został skonfigurowany w  Credentials page. Jeśli ta wartość nie pasuje do autoryzowanego identyfikatora URI, żądanie zakończy się niepowodzeniem i zostanie zwrócony błąd redirect_uri_mismatch.
  • state powinien zawierać wartość unikalnego tokena sesji zapobiegającego fałszowaniu, a także wszelkie inne informacje potrzebne do odzyskania kontekstu, gdy użytkownik wróci do aplikacji, np. adres URL strony początkowej. (Więcej informacji znajdziesz state).
  • nonce to losowa wartość wygenerowana przez aplikację, która w przypadku wystąpienia włącza ochronę przed powtórzeniem.
  • login_hint może być adresem e-mail użytkownika lub ciągiem znaków sub, który jest odpowiednikiem identyfikatora Google użytkownika. Jeśli nie podasz parametru login_hint, a użytkownik jest zalogowany, na ekranie zgody pojawi się prośba o zatwierdzenie udostępnienia adresu e-mail użytkownika Twojej aplikacji. (Więcej informacji znajdziesz w artykule login_hint).
  • Użyj parametru hd, aby zoptymalizować proces OpenID Connect dla użytkowników określonej domeny powiązanej z organizacją Google Workspace lub Cloud (więcej informacji znajdziesz na stronie hd).

Oto przykład pełnego identyfikatora URI uwierzytelniania OpenID Connect z podziałami wierszy i spacjami dla lepszej czytelności:

https://accounts.google.com/o/oauth2/v2/auth?
 response_type=code&
 client_id=424911365001.apps.googleusercontent.com&
 scope=openid%20email&
 redirect_uri=https%3A//oauth2.example.com/code&
 state=security_token%3D138r5719ru3e1%26url%3Dhttps%3A%2F%2Foauth2-login-demo.example.com%2FmyHome&
 login_hint=jsmith@example.com&
 nonce=0394852-3190485-2490358&
 hd=example.com

Użytkownicy muszą wyrazić zgodę, jeśli aplikacja prosi o nowe informacje na ich temat lub o dostęp do konta, na który nie wyrazili wcześniej zgody.

3. Potwierdzenie tokenu stanu zabezpieczającego przed fałszerstwem

Odpowiedź jest wysyłana na adres redirect_uri podany w żądaniu. Wszystkie odpowiedzi są zwracane w ciągu zapytania:

https://oauth2.example.com/code?state=security_token%3D138r5719ru3e1%26url%3Dhttps%3A%2F%2Foa2cb.example.com%2FmyHome&code=4/P7q7W91a-oMsCeLvIaQm6bTrgtp7&scope=openid%20email%20https://www.googleapis.com/auth/userinfo.email

Na serwerze musisz potwierdzić, że wartość state otrzymana od Google jest zgodna z tokenem sesji utworzonym w kroku 1. Ta weryfikacja dwukierunkowa pomaga sprawdzić, czy żądanie pochodzi od użytkownika, a nie od złośliwego skryptu.

Poniższy kod pokazuje, jak potwierdzić tokeny sesji utworzone w kroku 1:

PHP

Aby użyć tego przykładu, musisz pobrać bibliotekę klienta interfejsów API Google dla języka PHP.

// Ensure that there is no request forgery going on, and that the user
// sending us this connect request is the user that was supposed to.
if ($request->get('state') != ($app['session']->get('state'))) {
  return new Response('Invalid state parameter', 401);
}

Java

Aby użyć tego przykładu, musisz pobrać bibliotekę klienta interfejsów API Google dla języka Java.

// Ensure that there is no request forgery going on, and that the user
// sending us this connect request is the user that was supposed to.
if (!request.queryParams("state").equals(
    request.session().attribute("state"))) {
  response.status(401);
  return GSON.toJson("Invalid state parameter.");
}

Python

Aby użyć tego przykładu, musisz pobrać bibliotekę klienta interfejsów API Google dla języka Python.

# Ensure that the request is not a forgery and that the user sending
# this connect request is the expected user.
if request.args.get('state', '') != session['state']:
  response = make_response(json.dumps('Invalid state parameter.'), 401)
  response.headers['Content-Type'] = 'application/json'
  return response

4. Wymiana code na token dostępu i token identyfikatora

Odpowiedź zawiera parametr code, czyli jednorazowy kod autoryzacji, który Twój serwer może wymienić na token dostępu i token identyfikatora. Serwer przeprowadza tę wymianę, wysyłając żądanie HTTPS POST. Żądanie POST jest wysyłane do punktu końcowego tokena, który należy pobrać z dokumentu Discovery za pomocą wartości metadanych token_endpoint. W dalszej części przyjmujemy, że punkt końcowy to https://oauth2.googleapis.com/token. Żądanie musi zawierać te parametry w treści POST:

Pola
code Kod autoryzacji zwrócony z pierwszego żądania.
client_id Identyfikator klienta uzyskany z , zgodnie z opisem w artykule Uzyskiwanie danych uwierzytelniających OAuth 2.0.
client_secret Klucz klienta uzyskany z zgodnie z opisem w artykule Uzyskiwanie danych logowania OAuth 2.0.
redirect_uri Autoryzowany identyfikator URI przekierowania dla danego parametru client_id określonego w parametrze w parametrze , zgodnie z opisem w artykule Ustawianie identyfikatora URI przekierowania.
grant_type To pole musi zawierać wartość authorization_code, zgodnie ze specyfikacją OAuth 2.0.

Rzeczywiste żądanie może wyglądać tak:

POST /token HTTP/1.1
Host: oauth2.googleapis.com
Content-Type: application/x-www-form-urlencoded

code=4/P7q7W91a-oMsCeLvIaQm6bTrgtp7&
client_id=your-client-id&
client_secret=your-client-secret&
redirect_uri=https%3A//oauth2.example.com/code&
grant_type=authorization_code

Odpowiedź informująca o powodzeniu zawiera te pola w tablicy JSON:

Pola
access_token Token, który można wysłać do interfejsu API Google.
expires_in Pozostały czas ważności tokena dostępu w sekundach.
id_token JWT zawierający informacje o tożsamości użytkownika, które są podpisane cyfrowo przez Google.
scope Zakresy dostępu przyznane przez access_token w postaci listy ciągów znaków oddzielonych spacjami, w których rozróżniana jest wielkość liter.
token_type Określa typ zwróconego tokena. Obecnie to pole ma zawsze wartość Bearer.
refresh_token (opcjonalnie)

To pole jest obecne tylko wtedy, gdy w żądaniu uwierzytelniania parametr access_type miał wartość offline. Więcej informacji znajdziesz w sekcji Tokeny odświeżania.

5. Pobieranie informacji o użytkowniku z tokena identyfikatora

Token tożsamości to JWT (token sieciowy JSON), czyli obiekt JSON zakodowany w formacie Base64 i podpisany kryptograficznie. Zwykle weryfikacja tokena identyfikatora przed jego użyciem jest kluczowa, ale ponieważ komunikujesz się bezpośrednio z Google za pomocą kanału HTTPS bez pośredników i używasz tajnego klucza klienta do uwierzytelniania się w Google, możesz mieć pewność, że otrzymany token rzeczywiście pochodzi od Google i jest ważny. Jeśli serwer przekazuje token identyfikatora do innych komponentów aplikacji, bardzo ważne jest, aby inne komponenty sprawdzały poprawność tokena przed jego użyciem.

Większość bibliotek interfejsu API łączy weryfikację z dekodowaniem wartości zakodowanych w formacie base64url i parsowaniem kodu JSON, więc prawdopodobnie i tak zweryfikujesz token podczas uzyskiwania dostępu do roszczeń w tokenie identyfikatora.

Ładunek tokena identyfikatora

Token tożsamości to obiekt JSON zawierający zbiór par nazwa/wartość. Oto przykład sformatowany w celu zwiększenia czytelności:

{
  "iss": "https://accounts.google.com",
  "azp": "1234987819200.apps.googleusercontent.com",
  "aud": "1234987819200.apps.googleusercontent.com",
  "sub": "10769150350006150715113082367",
  "at_hash": "HK6E_P6Dh8Y93mRNtsDB1Q",
  "hd": "example.com",
  "email": "jsmith@example.com",
  "email_verified": "true",
  "iat": 1353601026,
  "exp": 1353604926,
  "nonce": "0394852-3190485-2490358"
}

Tokeny tożsamości Google mogą zawierać następujące pola (nazywane deklaracjami):

Roszczenie Udostępniony Opis
aud zawsze Odbiorca, dla którego jest przeznaczony dany token tożsamości. Musi to być jeden z identyfikatorów klienta OAuth 2.0 Twojej aplikacji.
exp zawsze Czas wygaśnięcia, po którym tokenu identyfikatora nie można już akceptować. Podany jako czas uniksowy (całkowita liczba sekund).
iat zawsze Czas wystawienia tokena tożsamości. Podany jako czas uniksowy (całkowita liczba sekund).
iss zawsze Identyfikator wystawcy odpowiedzi. W przypadku tokenów tożsamości Google zawsze jest to https://accounts.google.com lub accounts.google.com.
sub zawsze Identyfikator użytkownika, niepowtarzalny wśród wszystkich kont Google i nieużywany ponownie. Konto Google może mieć w różnych momentach wiele powiązanych adresów e-mail, ale wartość sub nie zmienia się nigdy. Użyj właściwości sub w swojej aplikacji jako unikalnego klucza, a zarazem identyfikatora użytkownika. Maksymalna długość to 255 znaków ASCII z uwzględnieniem wielkości liter.
at_hash Hash tokena dostępu. Sprawdza, czy token dostępu jest powiązany z tokenem tożsamości. Jeśli token identyfikatora jest wydawany z wartością access_token w przepływie po stronie serwera, to roszczenie jest zawsze uwzględniane. To roszczenie może być używane jako alternatywny mechanizm ochrony przed atakami typu cross-site request forgery, ale jeśli wykonasz krok 1krok 3, weryfikacja tokena dostępu nie będzie konieczna.
azp client_id autoryzowanej aplikacji prezentującej token. Ta deklaracja jest potrzebna tylko wtedy, gdy strona żądająca tokena tożsamości różni się od jego odbiorcy. W Google może tak być w przypadku aplikacji hybrydowych, gdy aplikacja internetowa i aplikacja na Androida mają inny identyfikator klienta OAuth 2.0client_id, ale są związane z tym samym projektem interfejsów API Google.
email Adres e-mail użytkownika. Wartość jest podawana tylko wtedy, gdy w żądaniu uwzględniono zakres email. Wartość tego roszczenia może nie być unikalna dla tego konta i może się zmieniać z czasem, dlatego nie należy jej używać jako głównego identyfikatora do łączenia z rekordem użytkownika. Nie możesz też polegać na domenie roszczenia email, aby identyfikować użytkowników organizacji Google Workspace lub Cloud. Zamiast tego użyj roszczenia hd.
email_verified Wartość „prawda”, jeśli adres e-mail użytkownika został zweryfikowany. W przeciwnym razie „fałsz”.
family_name Nazwisko użytkownika. Może być podany, gdy występuje roszczenie name.
given_name Imię lub imiona użytkownika. Może być podany, gdy występuje roszczenie name.
hd Domena powiązana z organizacją Google Workspace lub Cloud użytkownika. Podawana tylko wtedy, gdy użytkownik należy do organizacji Google Cloud. Musisz sprawdzić to roszczenie, gdy ograniczasz dostęp do zasobu tylko do użytkowników z określonych domen. Brak tego roszczenia oznacza, że konto nie należy do domeny hostowanej przez Google.
locale Lokalizacja użytkownika reprezentowana przez tag języka BCP 47. Ten atrybut można podać, gdy występuje roszczenie name.
name Pełne imię i nazwisko użytkownika w możliwej do wyświetlenia postaci. Można go podać, gdy:
  • Zakres żądania zawierał ciąg znaków „profile”.
  • Token identyfikatora jest zwracany podczas odświeżania tokena

Jeśli występują roszczenia name, możesz ich użyć do zaktualizowania rekordów użytkowników aplikacji. Pamiętaj, że nie ma gwarancji, że to roszczenie będzie obecne.

nonce Wartość parametru nonce dostarczona przez aplikację w żądaniu uwierzytelnienia. Zadbaj o to, aby była wyświetlana tylko raz, co zapewni ochronę przed atakami typu replay.
picture Adres URL zdjęcia profilowego użytkownika. Można go podać, gdy:
  • Zakres żądania zawierał ciąg znaków „profile”.
  • Token identyfikatora jest zwracany podczas odświeżania tokena

Gdy występują roszczenia picture, możesz ich użyć do zaktualizowania rekordów użytkowników aplikacji. Pamiętaj, że nie ma gwarancji, że to roszczenie będzie obecne.

profile Adres URL strony profilu użytkownika. Można go podać, gdy:
  • Zakres żądania zawierał ciąg znaków „profile”.
  • Token identyfikatora jest zwracany podczas odświeżania tokena

Gdy występują roszczenia profile, możesz ich użyć do zaktualizowania rekordów użytkowników aplikacji. Pamiętaj, że nie ma gwarancji, że to roszczenie będzie obecne.

6. Uwierzytelnianie użytkownika

Po uzyskaniu informacji o użytkowniku z tokena identyfikatora należy wysłać zapytanie do bazy danych użytkowników aplikacji. Jeśli użytkownik jest już w Twojej bazie danych, rozpocznij sesję aplikacji dla tego użytkownika, jeśli odpowiedź z interfejsu Google API spełnia wszystkie wymagania logowania.

Jeśli użytkownik nie istnieje w Twojej bazie danych użytkowników, przekieruj go do procesu rejestracji nowego użytkownika. Możesz automatycznie zarejestrować użytkownika na podstawie informacji otrzymanych od Google lub przynajmniej wstępnie wypełnić wiele pól wymaganych w formularzu rejestracyjnym. Oprócz informacji zawartych w tokenie identyfikatora możesz uzyskać dodatkowe informacje o profilu użytkownika w naszych punktach końcowych profilu użytkownika.

Tematy zaawansowane

W kolejnych sekcjach znajdziesz szczegółowe informacje o interfejsie Google OAuth 2.0 API. Te informacje są przeznaczone dla deweloperów, którzy mają zaawansowane wymagania dotyczące uwierzytelniania i autoryzacji.

Dostęp do innych interfejsów API Google

Jedną z zalet korzystania z OAuth 2.0 do uwierzytelniania jest to, że aplikacja może uzyskać uprawnienia do korzystania z innych interfejsów API Google w imieniu użytkownika (takich jak YouTube, Dysk Google, Kalendarz czy Kontakty) w tym samym czasie, w którym uwierzytelnia użytkownika. Aby to zrobić, w żądaniu uwierzytelnienia wysyłanym do Google uwzględnij inne zakresy, których potrzebujesz. Jeśli na przykład chcesz dodać do żądania uwierzytelniania grupę wiekową użytkownika, przekaż parametr zakresu openid email https://www.googleapis.com/auth/profile.agerange.read. Użytkownikowi wyświetla się odpowiedni komunikat na ekranie zgody. Token dostępu, który otrzymasz od Google, umożliwi Twojej aplikacji dostęp do wszystkich interfejsów API związanych z zakresami dostępu, o które prosisz i które zostały Ci przyznane.

Tokeny odświeżania

W prośbie o dostęp do interfejsu API możesz poprosić o zwrócenie tokena odświeżania podczas codewymiany. Token odświeżania zapewnia aplikacji ciągły dostęp do interfejsów API Google, gdy użytkownik nie korzysta z aplikacji. Aby poprosić o token odświeżania, ustaw parametr access_type na offlineżądaniu uwierzytelniania.

Uwagi:

  • Token odświeżania należy przechowywać w bezpiecznym i trwałym miejscu, ponieważ można go uzyskać tylko podczas pierwszego wykonania przepływu wymiany kodu.
  • Liczba wydawanych tokenów odświeżania jest ograniczona: jeden limit dotyczy kombinacji klient/użytkownik, a drugi – użytkownika we wszystkich klientach. Jeśli aplikacja będzie wysyłać zbyt wiele żądań tokenów odświeżania, może przekroczyć te limity. W takim przypadku starsze tokeny odświeżania przestaną działać.

Więcej informacji znajdziesz w artykule Odświeżanie tokena dostępu (dostęp offline).

Możesz poprosić użytkownika o ponowne autoryzowanie aplikacji, ustawiając w żądaniu uwierzytelniania parametr prompt na wartość consent. Gdy ten parametr jest uwzględniony, ekran zgody wyświetla się za każdym razem, gdy aplikacja zgłasza żądanie autoryzacji zakresów dostępu, nawet jeśli wszystkie zakresy zostały wcześniej przyznane projektowi interfejsów API Google.prompt=consent Z tego powodu uwzględniaj prompt=consent tylko wtedy, gdy jest to konieczne.

Więcej informacji o parametrze prompt znajdziesz w prompt w tabeli Parametry URI uwierzytelniania.

Parametry identyfikatora URI uwierzytelniania

W tabeli poniżej znajdziesz pełniejsze opisy parametrów akceptowanych przez interfejs API uwierzytelniania OAuth 2.0 od Google.

Parametr Wymagane Opis
client_id (Wymagane) Ciąg identyfikatora klienta, który uzyskasz z  , zgodnie z opisem w artykule Uzyskiwanie danych uwierzytelniających OAuth 2.0.
nonce (Wymagane) Losowa wartość wygenerowana przez aplikację, która umożliwia ochronę przed powtórzeniem.
response_type (Wymagane) Jeśli wartość to code, uruchamia podstawowy proces kodu autoryzacji, który wymaga wysłania POST do punktu końcowego tokena w celu uzyskania tokenów. Jeśli wartość to token id_token lub id_token token, uruchamia przepływ niejawny, który wymaga użycia JavaScriptu w identyfikatorze URI przekierowania do pobrania tokenów z identyfikatora URI #fragment.
redirect_uri (Wymagane) Określa, gdzie jest wysyłana odpowiedź. Wartość tego parametru musi być dokładnie taka sama jak jedna z autoryzowanych wartości przekierowania ustawionych w  (w tym schemat HTTP lub HTTPS, wielkość liter i końcowy znak „/”, jeśli występuje).
scope (Wymagane)

Parametr zakresu musi zaczynać się od wartości openid, a następnie zawierać wartość profile, email lub obie te wartości.

Jeśli występuje wartość zakresu profile, token identyfikatora może (ale nie musi) zawierać domyślne roszczenia profile użytkownika.

Jeśli występuje wartość zakresu email, token identyfikatora zawiera roszczenia emailemail_verified.

Oprócz tych zakresów specyficznych dla OpenID argument zakresu może też zawierać inne wartości zakresu. Wszystkie wartości zakresu muszą być rozdzielone spacjami. Jeśli na przykład chcesz uzyskać dostęp do poszczególnych plików na Dysku Google użytkownika, parametr scope może mieć wartość openid profile email https://www.googleapis.com/auth/drive.file.

Informacje o dostępnych zakresach znajdziesz w artykule Zakresy OAuth 2.0 dla interfejsów API Google lub w dokumentacji interfejsu API Google, z którego chcesz korzystać.

state (opcjonalne, ale zdecydowanie zalecane)

Nieprzejrzysty ciąg znaków, który jest przesyłany w obie strony w protokole, tzn. jest zwracany jako parametr URI w przypadku przepływu podstawowego oraz w identyfikatorze URI #fragment w przypadku przepływu niejawnego.

state może być przydatny do korelowania żądań i odpowiedzi. Ponieważ wartość redirect_uri można odgadnąć, użycie wartości state może zwiększyć pewność, że połączenie przychodzące jest wynikiem żądania uwierzytelniania zainicjowanego przez Twoją aplikację. Jeśli wygenerujesz losowy ciąg znaków lub zakodujesz w tej zmiennej state hash stanu klienta (np. pliku cookie), możesz zweryfikować odpowiedź, aby sprawdzić, czy żądanie i odpowiedź pochodzą z tej samej przeglądarki. Zapewnia to ochronę przed atakami takimi jak fałszowanie żądań z innych witryn.

access_type (Opcjonalnie) Dozwolone wartości to offlineonline. Efekt jest opisany w sekcji Dostęp offline. Jeśli klient prosi o token dostępu, nie otrzymuje tokena odświeżania, chyba że określono wartość offline.
display (Opcjonalnie) Ciąg znaków ASCII określający sposób wyświetlania przez serwer autoryzacji stron interfejsu użytkownika uwierzytelniania i zgody. Podane niżej wartości są akceptowane przez serwery Google, ale nie mają wpływu na działanie protokołu: page, popup, touchwap.
hd (Opcjonalnie)

Uprość proces logowania na konta należące do organizacji Google Cloud. Jeśli uwzględnisz domenę organizacji Google Cloud (np. mycollege.edu), możesz wskazać, że interfejs wyboru konta powinien być zoptymalizowany pod kątem kont w tej domenie. Aby zoptymalizować działanie pod kątem kont organizacji Google Cloud ogólnie, a nie tylko jednej domeny organizacji Google Cloud, ustaw wartość gwiazdki (*): hd=*.

Nie polegaj na tej optymalizacji interfejsu, aby kontrolować, kto ma dostęp do Twojej aplikacji, ponieważ żądania po stronie klienta można modyfikować. Sprawdź, czy zwrócony token identyfikatora ma wartość roszczenia hd, która jest zgodna z oczekiwaną wartością (np. mycolledge.edu). W przeciwieństwie do parametru żądania roszczenie hd tokena identyfikatora jest zawarte w tokenie zabezpieczeń od Google, więc wartość jest wiarygodna.

include_granted_scopes (Opcjonalnie) Jeśli ten parametr ma wartość true, a żądanie autoryzacji zostanie zaakceptowane, autoryzacja będzie obejmować wszystkie poprzednie autoryzacje przyznane tej kombinacji użytkownika i aplikacji w przypadku innych zakresów. Więcej informacji znajdziesz w sekcji Autoryzacja przyrostowa.

Pamiętaj, że w przypadku przepływu zainstalowanej aplikacji nie możesz przeprowadzić autoryzacji przyrostowej.

login_hint (Opcjonalnie) Gdy aplikacja wie, którego użytkownika próbuje uwierzytelnić, może podać ten parametr jako wskazówkę dla serwera uwierzytelniającego. Przekazanie tej wskazówki powoduje ukrycie selektora konta i wstępne wypełnienie pola adresu e-mail w formularzu logowania lub wybranie odpowiedniej sesji (jeśli użytkownik korzysta z wielokrotnego logowania). Może to pomóc uniknąć problemów, które występują, gdy aplikacja loguje się na nieprawidłowe konto użytkownika. Wartością może być adres e-mail lub ciąg znaków sub, który jest odpowiednikiem identyfikatora Google użytkownika.
prompt (Opcjonalnie) Lista rozdzielonych spacjami wartości tekstowych, która określa, czy serwer autoryzacji wyświetla użytkownikowi prośbę o ponowne uwierzytelnienie i wyrażenie zgody. Możliwe wartości:
  • none

    Serwer autoryzacji nie wyświetla żadnych ekranów uwierzytelniania ani zgody użytkownika. Jeśli użytkownik nie jest jeszcze uwierzytelniony i nie skonfigurował wcześniej zgody na żądane zakresy, serwer zwraca błąd. Aby sprawdzić, czy uwierzytelnianie lub zgoda użytkownika już istnieją, możesz użyć none.

  • consent

    Serwer autoryzacji prosi użytkownika o zgodę przed przekazaniem informacji do klienta.

  • select_account

    Serwer autoryzacji prosi użytkownika o wybranie konta. Umożliwia to użytkownikowi, który ma wiele kont na serwerze autoryzacji, wybór spośród wielu kont, dla których może mieć aktualne sesje.

Jeśli nie podasz żadnej wartości, a użytkownik nie autoryzował wcześniej dostępu, wyświetli mu się ekran zgody.

Weryfikowanie tokena tożsamości

Musisz zweryfikować wszystkie tokeny identyfikatora na serwerze, chyba że wiesz, że pochodzą one bezpośrednio z Google. Na przykład serwer musi weryfikować autentyczność wszystkich tokenów identyfikatora otrzymywanych z aplikacji klienckich.

Oto typowe sytuacje, w których możesz wysyłać tokeny identyfikatora na serwer:

  • wysyłanie tokenów tożsamości z żądaniami, które wymagają uwierzytelnienia; Tokeny identyfikatora informują, który użytkownik wysyła żądanie i dla którego klienta został przyznany token identyfikatora.

Tokeny identyfikatora są poufne i mogą zostać wykorzystane w niewłaściwy sposób, jeśli zostaną przechwycone. Musisz zadbać o bezpieczne przetwarzanie tych tokenów, przesyłając je tylko za pomocą protokołu HTTPS i tylko w danych POST lub w nagłówkach żądań. Jeśli przechowujesz tokeny identyfikacyjne na serwerze, musisz też zadbać o ich bezpieczeństwo.

Tokeny identyfikacyjne są przydatne, ponieważ można je przekazywać między różnymi komponentami aplikacji. Komponenty te mogą używać tokena identyfikacyjnego jako prostego mechanizmu uwierzytelniania, który uwierzytelnia aplikację i użytkownika. Zanim jednak użyjesz informacji zawartych w tokenie identyfikatora lub potraktujesz je jako potwierdzenie, że użytkownik został uwierzytelniony, musisz je zweryfikować.

Weryfikacja tokena tożsamości wymaga wykonania kilku kroków:

  1. Sprawdź, czy token identyfikatora jest prawidłowo podpisany przez wystawcę. Tokeny wydane przez Google są podpisywane przy użyciu jednego z certyfikatów znajdujących się pod adresem URI określonym w wartości metadanych jwks_uridokumencie dotyczącym wykrywania.
  2. Sprawdź, czy wartość roszczenia iss w tokenie identyfikatora jest równa https://accounts.google.com lub accounts.google.com.
  3. Sprawdź, czy wartość roszczenia aud w tokenie identyfikatora jest równa identyfikatorowi klienta aplikacji.
  4. Sprawdź, czy czas wygaśnięcia (deklaracja exp) tokena identyfikatora nie minął.
  5. Jeśli w żądaniu podano wartość parametru hd, sprawdź, czy token identyfikatora zawiera roszczenie hd, które pasuje do zaakceptowanej domeny powiązanej z organizacją Google Cloud.

Kroki 2–5 obejmują tylko porównania ciągów znaków i dat, które są dość proste, więc nie będziemy ich tutaj szczegółowo opisywać.

Pierwszy krok jest bardziej złożony i obejmuje sprawdzanie podpisu kryptograficznego. Na potrzeby debugowania możesz użyć punktu końcowego tokeninfo Google, aby porównać go z lokalnym przetwarzaniem zaimplementowanym na serwerze lub urządzeniu. Załóżmy, że wartość tokena identyfikatora to XYZ123. Następnie należy cofnąć odwołanie do identyfikatora URI https://oauth2.googleapis.com/tokeninfo?id_token=XYZ123. Jeśli podpis tokena jest prawidłowy, odpowiedzią będzie ładunek JWT w postaci zdekodowanego obiektu JSON.

Punkt końcowy tokeninfo jest przydatny do debugowania, ale w przypadku środowisk produkcyjnych pobieraj klucze publiczne Google z punktu końcowego kluczy i przeprowadzaj weryfikację lokalnie. Identyfikator URI kluczy należy pobrać z dokumentu Discovery za pomocą wartości metadanych jwks_uri. Żądania wysyłane do punktu końcowego debugowania mogą być ograniczane lub mogą w inny sposób podlegać sporadycznym błędom.

Klucze publiczne Google zmieniają się rzadko, więc możesz je buforować za pomocą dyrektyw pamięci podręcznej w odpowiedzi HTTP i w większości przypadków przeprowadzać lokalną weryfikację znacznie wydajniej niż za pomocą punktu końcowego tokeninfo. Weryfikacja wymaga pobrania i przeanalizowania certyfikatów oraz wykonania odpowiednich wywołań kryptograficznych w celu sprawdzenia podpisu. Na szczęście dostępne są dobrze przetestowane biblioteki w wielu językach, które umożliwiają wykonanie tego zadania (zobacz jwt.io).

Uzyskiwanie informacji profilowych użytkownika

Aby uzyskać dodatkowe informacje o profilu użytkownika, możesz użyć tokena dostępu (który aplikacja otrzymuje podczas procesu uwierzytelniania) i standardu OpenID Connect:

  1. Aby zachować zgodność z OpenID, musisz uwzględnić wartości zakresu openid profileżądaniu uwierzytelnienia.

    Jeśli chcesz, aby adres e-mail użytkownika był uwzględniany, możesz podać dodatkową wartość zakresu email. Aby określić zarówno profile, jak i email, możesz w identyfikatorze URI żądania uwierzytelniania umieścić ten parametr:

    scope=openid%20profile%20email
  2. Dodaj token dostępu do nagłówka autoryzacji i wyślij żądanie HTTPS GET do punktu końcowego userinfo, który należy pobrać z dokumentu Discovery za pomocą wartości metadanych userinfo_endpoint. Odpowiedź userinfo zawiera informacje o użytkowniku, zgodnie z opisem w OpenID Connect Standard Claims i wartości metadanych claims_supported w dokumencie Discovery. Użytkownicy lub ich organizacje mogą podawać lub pomijać niektóre pola, więc w przypadku autoryzowanych zakresów dostępu możesz nie uzyskać informacji o każdym polu.

Dokument opisujący

Protokół OpenID Connect wymaga używania wielu punktów końcowych do uwierzytelniania użytkowników i wysyłania żądań dotyczących zasobów, w tym tokenów, informacji o użytkowniku i kluczy publicznych.

Aby uprościć implementacje i zwiększyć elastyczność, OpenID Connect umożliwia korzystanie z „dokumentu wykrywania”, czyli dokumentu JSON znajdującego się w dobrze znanym miejscu, który zawiera pary klucz-wartość z informacjami o konfiguracji dostawcy OpenID Connect, w tym identyfikatory URI punktów końcowych autoryzacji, tokena, unieważnienia, informacji o użytkowniku i kluczy publicznych. Dokument Discovery usługi OpenID Connect Google można pobrać z tego adresu:

https://accounts.google.com/.well-known/openid-configuration

Aby korzystać z usług OpenID Connect od Google, musisz na stałe zakodować w aplikacji identyfikator URI dokumentu Discovery (https://accounts.google.com/.well-known/openid-configuration). Aplikacja pobiera dokument, stosuje reguły buforowania w odpowiedzi, a następnie w razie potrzeby pobiera z niego identyfikatory URI punktów końcowych. Aby na przykład uwierzytelnić użytkownika, Twój kod pobierze wartość metadanych authorization_endpoint (https://accounts.google.com/o/oauth2/v2/auth w poniższym przykładzie) jako podstawowy identyfikator URI dla żądań uwierzytelniania wysyłanych do Google.

Oto przykład takiego dokumentu. Nazwy pól są zgodne z nazwami podanymi w OpenID Connect Discovery 1.0 (znaczenie tych nazw znajdziesz w tym dokumencie). Wartości mają charakter wyłącznie ilustracyjny i mogą ulec zmianie, chociaż są skopiowane z najnowszej wersji rzeczywistego dokumentu Discovery Google:

{
  "issuer": "https://accounts.google.com",
  "authorization_endpoint": "https://accounts.google.com/o/oauth2/v2/auth",
  "device_authorization_endpoint": "https://oauth2.googleapis.com/device/code",
  "token_endpoint": "https://oauth2.googleapis.com/token",
  "userinfo_endpoint": "https://openidconnect.googleapis.com/v1/userinfo",
  "revocation_endpoint": "https://oauth2.googleapis.com/revoke",
  "jwks_uri": "https://www.googleapis.com/oauth2/v3/certs",
  "response_types_supported": [
    "code",
    "token",
    "id_token",
    "code token",
    "code id_token",
    "token id_token",
    "code token id_token",
    "none"
  ],
  "subject_types_supported": [
    "public"
  ],
  "id_token_signing_alg_values_supported": [
    "RS256"
  ],
  "scopes_supported": [
    "openid",
    "email",
    "profile"
  ],
  "token_endpoint_auth_methods_supported": [
    "client_secret_post",
    "client_secret_basic"
  ],
  "claims_supported": [
    "aud",
    "email",
    "email_verified",
    "exp",
    "family_name",
    "given_name",
    "iat",
    "iss",
    "locale",
    "name",
    "picture",
    "sub"
  ],
  "code_challenge_methods_supported": [
    "plain",
    "S256"
  ]
}

Możesz uniknąć podróży w obie strony HTTP, zapisując w pamięci podręcznej wartości z dokumentu Discovery. Używane są standardowe nagłówki HTTP dotyczące przechowywania w pamięci podręcznej, które należy uwzględniać.

Biblioteki klienta

Te biblioteki klienta ułatwiają wdrażanie OAuth 2.0 dzięki integracji z popularnymi platformami:

Zgodność z OpenID Connect

System uwierzytelniania OAuth 2.0 od Google obsługuje wymagane funkcje specyfikacji OpenID Connect Core. Każdy klient zaprojektowany do współpracy z OpenID Connect powinien współdziałać z tą usługą (z wyjątkiem obiektu żądania OpenID).