Autoryzowanie żądań wysłania

Żądania wysyłane do FCM z serwera aplikacji lub zaufanego środowiska muszą być autoryzowane. Zwróć uwagę na te istotne różnice między wycofanymi starsza wersja interfejsów API HTTP oraz uwierzytelniania HTTP v1 API:

  • Interfejs API HTTP w wersji 1 FCM autoryzuje żądania za pomocą krótkotrwałego tokena dostępu OAuth 2.0. Aby utworzyć ten token, możesz użyć domyślnych danych logowania do aplikacji Google (w środowiskach serwerów Google) lub ręcznie uzyskać wymagane dane logowania z pliku JSON z kluczem prywatnym wygenerowanym dla konta usługi. Jeśli do wysyłania wiadomości używasz funkcji Firebase Admin SDK, biblioteka sama zajmie się tokenem.
  • Wycofane starsze protokoły mogą używać tylko długotrwałych kluczy API uzyskanych z konsoli Firebase.

Autoryzacja wysyłania żądań HTTP w wersji 1

W zależności od szczegółów środowiska serwera użyj kombinacji tych strategii, aby autoryzować żądania serwera do usług Firebase:

  • Domyślne dane logowania aplikacji Google (ADC)
  • plik JSON konta usługi;
  • Ograniczony czasowo token dostępu OAuth 2.0 utworzony na podstawie konta usługi

Jeśli aplikacja działa w systemie Compute Engine, Google Kubernetes Engine, App Engine lub Cloud Functions (w tym Cloud Functions for Firebase) używaj domyślnych danych logowania aplikacji (ADC). ADC używa istniejącej usługi domyślnej w celu uzyskania danych logowania do autoryzowania żądań, a ADC umożliwia elastyczne testy lokalne za pomocą zmiennej środowiskowej GOOGLE_APPLICATION_CREDENTIALS Aby zapewnić pełną automatyzację procesu autoryzacji, używaj ADC razem z bibliotekami serwera pakietu Admin SDK.

Jeśli aplikacja działa w środowisku serwera spoza Google, musisz pobrać plik JSON konta usługi z projektu Firebase. Jeśli masz dostęp do systemu plików zawierającego pliku klucza prywatnego, można użyć zmiennej środowiskowej GOOGLE_APPLICATION_CREDENTIALS do autoryzowania żądań za pomocą ręcznie uzyskanych danych logowania. Jeśli nie masz dostępu do takich plików, musisz w kodze odwoływać się do pliku konta usługi. Należy to robić z bardzo dużą ostrożnością, ponieważ istnieje ryzyko ujawnienia danych logowania.

Podawanie danych logowania za pomocą ADC

Domyślne uwierzytelnianie aplikacji Google (ADC) sprawdza Twoje poświadczenia w takim porządku:

  1. ADC sprawdza, czy ustawiona jest zmienna środowiskowa GOOGLE_APPLICATION_CREDENTIALS. Jeśli zmienna jest ustawiona, ADC używa pliku konta usługi, do którego ona wskazuje.

  2. Jeśli zmienna środowiskowa nie jest ustawiona, ADC używa domyślnego konta usługi, które Compute Engine, Google Kubernetes Engine, App Engine i Cloud Functions udostępniają aplikacjom działającym w tych usługach.

  3. Jeśli ADC nie może użyć tych danych, system zgłasza błąd.

Poniższy przykładowy kod pakietu Admin SDK ilustruje tę strategię. Przykład nie określa bezpośrednio danych logowania do aplikacji. Jednak ADC może znaleźć te dane logowania w sposób domyślny, o ile zmienna środowiskowa jest ustawiona lub aplikacja działa w kontekście Compute Engine, Google Kubernetes Engine, App Engine lub funkcji Cloud.

Node.js

admin.initializeApp({
  credential: admin.credential.applicationDefault(),
});

Java

FirebaseOptions options = FirebaseOptions.builder()
    .setCredentials(GoogleCredentials.getApplicationDefault())
    .setDatabaseUrl("https://<DATABASE_NAME>.firebaseio.com/")
    .build();

FirebaseApp.initializeApp(options);

Python

default_app = firebase_admin.initialize_app()

Go

app, err := firebase.NewApp(context.Background(), nil)
if err != nil {
	log.Fatalf("error initializing app: %v\n", err)
}

C#

FirebaseApp.Create(new AppOptions()
{
    Credential = GoogleCredential.GetApplicationDefault(),
});

Ręczne podawanie danych logowania

Projekty Firebase obsługują Google kont usługi, można użyć do wywołania Firebase interfejsów API serwera z serwera aplikacji lub zaufanego środowiska. Jeśli kod tworzysz lokalnie lub wdrażasz aplikację lokalnie, możesz użyć danych logowania uzyskanych za pomocą tego konta usługi, aby autoryzować żądania serwera.

Uwierzytelnienie i autoryzacja konta usługi aby uzyskać dostęp do usług Firebase, musisz wygenerować plik klucza prywatnego w formacie JSON .

Aby wygenerować plik klucza prywatnego dla konta usługi:

  1. Otwórz konsolę Firebase Ustawienia > Konta usługi.

  2. Kliknij Wygeneruj nowy klucz prywatny, a następnie potwierdź, klikając Wygeneruj klucz.

  3. Bezpiecznie przechowuj plik JSON zawierający klucz.

Podczas autoryzacji za pomocą konta usługi masz 2 możliwości przekazania danych logowania do aplikacji. Możesz ustawić GOOGLE_APPLICATION_CREDENTIALS. Możesz też bezpośrednio przekazywać w kodzie ścieżkę do klucza konta usługi. Pierwsza opcja jest bezpieczniejsza i zdecydowanie zalecana.

Aby ustawić zmienną środowiskową:

Ustaw zmienną środowiskową GOOGLE_APPLICATION_CREDENTIALS na ścieżkę do pliku JSON zawierającego klucz konta usługi. Ta zmienna ma zastosowanie tylko do bieżącej sesji powłoki, więc jeśli otworzysz w nowej sesji, ustaw zmienną ponownie.

Linux lub macOS

export GOOGLE_APPLICATION_CREDENTIALS="/home/user/Downloads/service-account-file.json"

Windows

W PowerShell:

$env:GOOGLE_APPLICATION_CREDENTIALS="C:\Users\username\Downloads\service-account-file.json"

Po wykonaniu powyższych czynności aplikacja może domyślnie określać Twoje dane logowania, co pozwala używać danych logowania konta usługi podczas testowania lub uruchamiania w środowiskach innych niż Google.

Używanie danych logowania do tworzenia tokenów dostępu

O ile nie korzystasz z Pakiet Admin SDK, które automatycznie obsługują autoryzację, musisz wygenerować token dostępu i dodają go do wysyłania żądań.

Aby pobrać krótkotrwały token dostępu OAuth 2.0, użyj danych logowania Firebase wraz z biblioteką Google Auth Library w preferowanym języku:

Node.js

 function getAccessToken() {
  return new Promise(function(resolve, reject) {
    const key = require('../placeholders/service-account.json');
    const jwtClient = new google.auth.JWT(
      key.client_email,
      null,
      key.private_key,
      SCOPES,
      null
    );
    jwtClient.authorize(function(err, tokens) {
      if (err) {
        reject(err);
        return;
      }
      resolve(tokens.access_token);
    });
  });
}

W tym przykładzie biblioteka klienta interfejsu API Google uwierzytelnia żądanie za pomocą token sieciowy JSON, czyli JWT. Więcej informacji: Tokeny sieciowe JSON.

Python

def _get_access_token():
  """Retrieve a valid access token that can be used to authorize requests.

  :return: Access token.
  """
  credentials = service_account.Credentials.from_service_account_file(
    'service-account.json', scopes=SCOPES)
  request = google.auth.transport.requests.Request()
  credentials.refresh(request)
  return credentials.token

Java

private static String getAccessToken() throws IOException {
  GoogleCredentials googleCredentials = GoogleCredentials
          .fromStream(new FileInputStream("service-account.json"))
          .createScoped(Arrays.asList(SCOPES));
  googleCredentials.refresh();
  return googleCredentials.getAccessToken().getTokenValue();
}

Po wygaśnięciu tokena dostępu wywoływana jest metoda odświeżania tokena automatycznie pobierze zaktualizowany token dostępu.

Aby autoryzować dostęp do usługi FCM, poproś o zakres https://www.googleapis.com/auth/firebase.messaging

Aby dodać token dostępu do nagłówka żądania HTTP:

Dodaj token jako wartość nagłówka Authorization w formacie Authorization: Bearer <access_token>:

Node.js

headers: {
  'Authorization': 'Bearer ' + accessToken
}

Python

headers = {
  'Authorization': 'Bearer ' + _get_access_token(),
  'Content-Type': 'application/json; UTF-8',
}

Java

URL url = new URL(BASE_URL + FCM_SEND_ENDPOINT);
HttpURLConnection httpURLConnection = (HttpURLConnection) url.openConnection();
httpURLConnection.setRequestProperty("Authorization", "Bearer " + getServiceAccountAccessToken());
httpURLConnection.setRequestProperty("Content-Type", "application/json; UTF-8");
return httpURLConnection;

Autoryzowanie żądań wysyłania w ramach starszego protokołu

W przypadku starszego protokołu HTTP każde żądanie musi zawierać klucz serwera z karty Komunikacja w chmurze w konsoli Firebase, na panelu Ustawienia. W przypadku XMPP musisz użyć tego samego klucza serwera do nawiązania połączenia.

Migracja starszych kluczy serwera

Od marca 2020 r. użytkownik FCM przestał tworzyć starsze klucze serwera. Dotychczasowe starsze klucze serwera będą nadal działać, ale zalecamy używanie nowszej wersji klucza o nazwie Klucz serwerakonsoliFirebase.

Jeśli chcesz usunąć dotychczasowy klucz serwera, możesz to zrobić w konsoli Google Cloud.

Autoryzacja żądań HTTP

Żądanie wiadomości składa się z 2 części: nagłówka HTTP i treści HTTP. Nagłówek HTTP musi zawierać te nagłówki:

  • Authorization: key=TWÓJ_KLUCZ_SERWERA
    Upewnij się, że jest to klucz serwera, którego wartość jest dostępna na karcie Cloud Messaging w panelu Ustawienia konsoli Firebase. Klucze Androida, platformy Apple oraz przeglądarki są odrzucane przez system FCM.
  • Content-Type: application/json dla JSON; application/x-www-form-urlencoded;charset=UTF-8 dla zwykłego tekstu.
    Jeśli pominiesz parametr Content-Type, zostanie domyślnie przyjęte, że format jest zwykłym tekstem.

Przykład:

Content-Type:application/json
Authorization:key=AIzaSyZ-1u...0GBYzPu7Udno5aA

{
  "to" : "bk3RNwTe3H0:CI2k_HHwgIpoDKCIZvvDMExUdFQ3P1...",
  "data" : {
    ...
  },
}

Więcej informacji o tworzeniu żądań wysyłania znajdziesz w artykule Tworzenie żądań wysyłania. Przewodnik po starszym protokole HTTP zawiera listę wszystkich parametrów, które może zawierać wiadomość.

Sprawdzanie ważności klucza serwera

Jeśli podczas wysyłania wiadomości otrzymujesz błędy uwierzytelniania, sprawdź poprawność klucza serwera. Na przykład w systemie Linux uruchom to polecenie:

api_key=YOUR_SERVER_KEY

curl --header "Authorization: key=$api_key" \
     --header Content-Type:"application/json" \
     https://fcm.googleapis.com/fcm/send \
     -d "{\"registration_ids\":[\"ABC\"]}"

Jeśli otrzymasz kod stanu HTTP 401, oznacza to, że klucz serwera jest nieprawidłowy.

Autoryzowanie połączenia XMPP

.

XMPP zapewnia trwałe, asynchroniczne, dwukierunkowe połączenie z serwerami FCM. Połączenie to umożliwia wysyłanie i odbieranie wiadomości między serwerem a urządzeniami użytkowników połączonymi z FCM.

Za pomocą większości biblioteki XMPP do zarządzania długotrwałym połączeniem z FCM. Punkt końcowy XMPP działa w czasie fcm-xmpp.googleapis.com:5235. Podczas testowania funkcji z użytkownikami spoza środowiska produkcyjnego należy połączyć się z serwerem w przedprodukcji pod adresem fcm-xmpp.googleapis.com:5236 (zwróć uwagę na inny port).

Regularne testowanie w środowisku przedprodukcyjnym (mniejszym środowisku, w którym działają najnowsze wersje FCM) jest korzystne, ponieważ pozwala oddzielić prawdziwych użytkowników od kodu testowego. Testowanie urządzeń i testowanie kodu łączenia z Aby uniknąć ryzyka, fcm-xmpp.googleapis.com:5236 powinien używać innego identyfikatora nadawcy FCM wysyłania wiadomości testowych do użytkowników produkcyjnych lub wysyłania wiadomości z ruchu produkcyjnego w przypadku połączeń testowych.

Połączenie musi spełniać 2 ważne wymagania:

  • Musisz zainicjować połączenie TLS. Pamiętaj, że FCM nie obsługuje obecnie rozszerzenia STARTTLS.
  • FCM wymaga mechanizmu uwierzytelniania SASL PLAIN za pomocą protokołu <your_FCM_Sender_Id>@fcm.googleapis.com (FCM identyfikator nadawcy) a klucz serwera jako hasła. Wartości te są dostępne w Karta Komunikacja w chmurze w panelu Ustawienia w konsoli Firebase.

Jeśli w jakimś momencie połączenie zostanie przerwane, natychmiast je nawiążesz. Po rozłączeniu, które nastąpiło po uwierzytelnieniu, nie trzeba wycofywać się z połączenia. W przypadku każdego identyfikatora nadawcyFCM dozwolone są 2500 połączeń równoległych.

Poniższe fragmenty kodu pokazują, jak przeprowadzić uwierzytelnianie autoryzacji połączenia XMPP z FCM.

Serwer XMPP

Serwer XMPP prosi o połączenie z FCM

<stream:stream to="fcm.googleapis.com"
        version="1.0" xmlns="jabber:client"
        xmlns:stream="http://etherx.jabber.org/streams">

FCM

FCM otwiera połączenie i wysyła żądanie mechanizmu uwierzytelniania, w tym Metoda PLAIN.

<stream:features>
  <mechanisms xmlns="urn:ietf:params:xml:ns:xmpp-sasl">
    <mechanism>X-OAUTH2</mechanism>
    <mechanism>X-GOOGLE-TOKEN</mechanism>
    <mechanism>PLAIN</mechanism>
  </mechanisms>
</stream:features>

Serwer XMPP

Serwer XMPP musi odpowiadać, używając metody uwierzytelniania PLAIN, podając klucz serwera z karty Komunikacja w chmurze w konsoli Firebase, w panelu Ustawienia.

<auth mechanism="PLAIN"
xmlns="urn:ietf:params:xml:ns:xmpp-sasl">MTI2MjAwMzQ3OTMzQHByb2plY3RzLmdjbS5hb
mFTeUIzcmNaTmtmbnFLZEZiOW1oekNCaVlwT1JEQTJKV1d0dw==</auth>

FCM

<success xmlns="urn:ietf:params:xml:ns:xmpp-sasl"/>

Serwer XMPP

<stream:stream to="fcm.googleapis.com"
        version="1.0" xmlns="jabber:client"
        xmlns:stream="http://etherx.jabber.org/streams">

FCM

<stream:features>
  <bind xmlns="urn:ietf:params:xml:ns:xmpp-bind"/>
  <session xmlns="urn:ietf:params:xml:ns:xmpp-session"/>
</stream:features>

Serwer XMPP

<iq type="set">
  <bind xmlns="urn:ietf:params:xml:ns:xmpp-bind"></bind>
</iq>

FCM

<iq type="result">
  <bind xmlns="urn:ietf:params:xml:ns:xmpp-bind">
    <jid>SENDER_ID@fcm.googleapis.com/RESOURCE</jid>
  </bind>
</iq>

Uwaga: podczas kierowania wiadomości aplikacja FCM nie używa zasobów powiązanych.

Zobacz Szczegółowe informacje o tworzeniu żądań wysyłania znajdziesz w sekcji Wysyłanie żądań. Informacje o starszym protokole XMPP zawiera listę wszystkich parametrów, które może zawierać wiadomość.