Bermigrasi dari HTTP lama ke HTTP v1

Aplikasi yang menggunakan HTTP API lama dari FCM harus dipertimbangkan untuk bermigrasi ke HTTP v1 API menggunakan petunjuk dalam panduan ini. Dibandingkan dengan API lama, HTTP v1 API memiliki beberapa keunggulan berikut:

  • Keamanan yang lebih baik melalui token akses HTTP v1 API menggunakan token akses yang berlaku singkat sesuai dengan model keamanan OAuth2. Jika suatu token akses terungkap ke publik, token tersebut hanya dapat digunakan secara tidak bertanggung jawab selama sekitar satu jam sebelum masa berlakunya berakhir. Token refresh tidak akan dikirim sesering kunci keamanan yang digunakan di API lama, sehingga kemungkinannya untuk diambil lebih kecil.

  • Penyesuaian pesan yang lebih efisien di seluruh platform. Untuk isi pesan, HTTP v1 API memiliki kunci umum yang diterapkan ke semua instance yang ditargetkan, ditambah kunci khusus platform yang dapat digunakan untuk menyesuaikan pesan di seluruh platform. Dengan begitu, Anda dapat membuat "penggantian" yang mengirimkan payload yang sedikit berbeda ke berbagai platform klien dalam satu pesan.

  • Dapat terus diupdate dan tidak akan ketinggalan zaman untuk versi platform klien yang baru. HTTP v1 API sepenuhnya mendukung opsi messaging yang tersedia di iOS, Android, dan Web. Karena setiap platform memiliki bloknya sendiri dalam payload JSON, FCM dapat memperpanjang API ke versi dan platform baru sesuai kebutuhan.

Mengupdate endpoint server

URL endpoint untuk HTTP v1 API berbeda dengan endpoint lama dalam beberapa hal berikut:

  • URL ini tersimpan sesuai versinya, dengan /v1 tercantum di jalurnya.
  • Jalur tersebut berisi project ID dari project Firebase untuk aplikasi Anda, dalam format /projects/myproject-ID/. ID ini tersedia di tab Setelan project umum di Firebase console.
  • URL ini secara eksplisit menentukan metode send sebagai :send.

Guna mengupdate endpoint server untuk HTTP v1, tambahkan elemen berikut ke endpoint di header permintaan kirim Anda.

Sebelum

POST https://fcm.googleapis.com/fcm/send

Setelah

POST https://fcm.googleapis.com/v1/projects/myproject-b5ae1/messages:send

Mengupdate otorisasi permintaan kirim

Sebagai pengganti string kunci server yang digunakan dalam permintaan lama, permintaan kirim HTTP v1 memerlukan token akses OAuth 2.0. Jika Anda menggunakan Admin SDK untuk mengirim pesan, library akan menangani token untuk Anda. Jika Anda menggunakan protokol mentah, dapatkan token seperti yang dijelaskan di bagian ini lalu tambahkan ke header sebagai Authorization: Bearer <valid Oauth 2.0 token>.

Sebelum

Authorization: key=AIzaSyZ-1u...0GBYzPu7Udno5aA

Setelah

Authorization: Bearer ya29.ElqKBGN2Ri_Uz...HnS_uNreA

Tergantung detail lingkungan server Anda, gunakan kombinasi strategi ini untuk mengizinkan permintaan server ke layanan Firebase:

  • Kredensial Default Aplikasi (ADC) Google
  • File JSON akun layanan
  • Token akses OAuth 2.0 yang berlaku singkat berasal dari akun layanan

Jika aplikasi Anda berjalan pada Compute Engine, Kubernetes Engine, App Engine, atau Cloud Functions (termasuk Cloud Functions for Firebase), gunakan Kredensial Default Aplikasi (ADC). ADC menggunakan akun layanan default yang sudah ada untuk mendapatkan kredensial guna mengizinkan permintaan, dan ADC mengaktifkan pengujian lokal fleksibel melalui variabel lingkungan GOOGLE_APPLICATION_CREDENTIALS. Untuk otomatisasi penuh alur otorisasi, gunakan ADC bersama dengan library server Admin SDK.

Jika aplikasi Anda berjalan di lingkungan server non-Google, Anda harus mendownload file JSON akun layanan dari project Firebase Anda. Selama Anda memiliki akses ke sistem file yang berisi file kunci pribadi, Anda dapat menggunakan variabel lingkungan GOOGLE_APPLICATION_CREDENTIALS untuk mengizinkan permintaan dengan kredensial yang diperoleh secara manual ini. Jika Anda tidak memiliki akses file seperti itu, Anda harus merujuk file akun layanan dalam kode Anda - yang harus dilakukan dengan sangat hati-hati karena bisa menampilkan kredensial Anda.

Memberikan kredensial dengan ADC

Kredensial Default Aplikasi (ADC) Google memeriksa kredensial Anda dengan urutan sebagai berikut:

  1. ADC memeriksa apakah variabel lingkungan GOOGLE_APPLICATION_CREDENTIALS ditetapkan atau tidak. Jika variabel ditetapkan, ADC menggunakan file akun layanan yang ditunjuk variabel.

  2. Jika variabel lingkungan tidak ditetapkan, ADC menggunakan akun layanan default yang disediakan Compute Engine, Kubernetes Engine, App Engine, dan Cloud Functions untuk aplikasi yang berjalan pada layanan tersebut.

  3. Jika ADC tidak dapat menggunakan salah satu dari kredensial di atas, sistem akan memunculkan error.

Contoh kode Admin SDK berikut menggambarkan strategi ini. Contoh ini tidak secara eksplisit menentukan kredensial aplikasi. Namun, ADC secara implisit dapat menemukan kredensial selama variabel lingkungan ditetapkan, atau selama aplikasi berjalan pada Compute Engine, Kubernetes Engine, App Engine, atau Cloud Functions.

Node.js

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

Java

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

FirebaseApp.initializeApp(options);

Python

default_app = firebase_admin.initialize_app()

Buka

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(),
});

Memberikan kredensial secara manual

Project Firebase mendukung akun layanan Google, yang dapat Anda gunakan untuk memanggil API server Firebase dari server aplikasi atau lingkungan tepercaya. Jika Anda mengembangkan kode secara lokal atau men-deploy aplikasi secara lokal, gunakan kredensial yang diperoleh melalui akun layanan ini untuk menyetujui permintaan server.

Untuk mengautentikasi akun layanan dan memberinya akses ke layanan Firebase, Anda harus membuat file kunci pribadi dalam format JSON.

Untuk membuat file kunci pribadi untuk akun layanan Anda:

  1. Di Firebase console, buka Setelan > Akun Layanan.

  2. Klik Buat Kunci Pribadi Baru, lalu konfirmasikan dengan mengklik Buat Kunci.

  3. Simpan dengan aman file JSON yang memuat kunci tersebut.

Saat mengotorisasi melalui akun layanan, Anda diberikan dua pilihan untuk memberikan kredensial ke aplikasi. Anda dapat menetapkan variabel lingkungan GOOGLE_APPLICATION_CREDENTIALS, atau Anda dapat secara eksplisit meneruskan jalur ke kunci akun layanan dalam kode. Opsi pertama lebih aman dan sangat disarankan.

Untuk menetapkan variabel lingkungan:

Tetapkan variabel lingkungan GOOGLE_APPLICATION_CREDENTIALS ke jalur file JSON yang berisi kunci akun layanan Anda. Variabel ini hanya berlaku untuk sesi shell Anda saat ini. Jadi, jika Anda membuka sesi baru, tetapkan variabel lagi.

Linux atau macOS

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

Windows

Dengan PowerShell:

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

Setelah Anda menyelesaikan langkah-langkah di atas, Kredensial Default Aplikasi (ADC) secara implisit dapat menentukan kredensial Anda, sehingga Anda dapat menggunakan kredensial akun layanan saat menguji atau menjalankannya di lingkungan non-Google.

Menggunakan kredensial untuk membuat token akses

Gunakan kredensial Firebase Anda beserta Library Klien Google API untuk bahasa pilihan Anda saat mengambil token akses OAuth 2.0 yang berlaku singkat:

node.js

 function getAccessToken() {
  return new Promise(function(resolve, reject) {
    var key = require('./service-account.json');
    var 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);
    });
  });
}

Dalam contoh ini, library klien Google API mengautentikasi permintaan dengan token web JSON atau JWT. Untuk mengetahui informasi lebih lanjut, baca artikel token web JSON.

Python

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

  :return: Access token.
  """
  credentials = ServiceAccountCredentials.from_json_keyfile_name(
      'service-account.json', SCOPES)
  access_token_info = credentials.get_access_token()
  return access_token_info.access_token

Java

private static String getAccessToken() throws IOException {
  GoogleCredential googleCredential = GoogleCredential
      .fromStream(new FileInputStream("service-account.json"))
      .createScoped(Arrays.asList(SCOPES));
  googleCredential.refreshToken();
  return googleCredential.getAccessToken();
}

Setelah masa berlaku token akses berakhir, metode refresh token akan otomatis dipanggil untuk mengambil token yang telah diupdate.

Untuk mengotorisasi akses ke FCM, minta cakupan https://www.googleapis.com/auth/firebase.messaging.

Untuk menambahkan token akses ke header permintaan HTTP:

Tambahkan token sebagai nilai header Authorization dalam format 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 " + getAccessToken());
httpURLConnection.setRequestProperty("Content-Type", "application/json; UTF-8");
return httpURLConnection;

Mengupdate payload permintaan pengiriman

FCM HTTP v1 menghadirkan perubahan signifikan dalam pengaturan struktur payload pesan JSON. Pada dasarnya, perubahan ini memastikan bahwa pesan akan ditangani dengan benar saat diterima di berbagai platform klien. Selain itu, dengan perubahan ini, Anda dapat lebih leluasa menyesuaikan atau "mengganti" kolom pesan per platform.

Selain memeriksa contoh di bagian ini, baca bagian Menyesuaikan pesan di seluruh platform dan pelajari referensi API untuk memahami HTTP v1.

Contoh: pesan notifikasi sederhana

Berikut adalah perbandingan payload notifikasi yang sangat sederhana — yang hanya berisi kolom title, body dan data — yang menunjukkan perbedaan mendasar antara payload lama dan payload HTTP v1.

Sebelum

{
  "to": "/topics/news",
  "notification": {
    "title": "Breaking News",
    "body": "New news story available."
  },
  "data": {
    "story_id": "story_12345"
  }
}

Setelah

{
  "message": {
    "topic": "news",
    "notification": {
      "title": "Breaking News",
      "body": "New news story available."
    },
    "data": {
      "story_id": "story_12345"
    }
  }
}

Contoh: menargetkan beberapa platform

Untuk mengaktifkan penargetan multi-platform, API lama melakukan penggantian di backend. Sebaliknya, HTTP v1 memberikan blok kunci khusus platform yang membuat perbedaan antara platform menjadi eksplisit dan terlihat oleh developer. Dengan demikian, Anda dapat menargetkan beberapa platform selalu dengan satu permintaan, seperti yang ditunjukkan dalam contoh berikut.

Sebelum

// Android
{
  "to": "/topics/news",
  "notification": {
    "title": "Breaking News",
    "body": "New news story available.",
    "click_action": "TOP_STORY_ACTIVITY"
  },
  "data": {
    "story_id": "story_12345"
  }
}
// iOS
{
  "to": "/topics/news",
  "notification": {
    "title": "Breaking News",
    "body": "New news story available.",
    "click_action": "HANDLE_BREAKING_NEWS"
  },
  "data": {
    "story_id": "story_12345"
  }
}

Setelah

{
  "message": {
    "topic": "news",
    "notification": {
      "title": "Breaking News",
      "body": "New news story available."
    },
    "data": {
      "story_id": "story_12345"
    }
    "android": {
      "notification": {
        "click_action": "TOP_STORY_ACTIVITY"
      }
    },
    "aps": {
      "payload": {
        "aps": {
          "category" : "NEW_MESSAGE_CATEGORY"
        }
      }
    }
  }
}

Contoh: menyesuaikan pesan dengan penggantian platform

Selain menyederhanakan penargetan pesan lintas platform, HTTP v1 API memberikan fleksibilitas untuk menyesuaikan pesan per platform.

Sebelum

// Android
{
  "to": "/topics/news",
  "notification": {
    "title": "Breaking News",
    "body": "Check out the Top Story.",
    "click_action": "TOP_STORY_ACTIVITY"
  },
  "data": {
    "story_id": "story_12345"
  }
}
// iOS
{
  "to": "/topics/news",
  "notification": {
    "title": "Breaking News",
    "body": "New news story available.",
    "click_action": "HANDLE_BREAKING_NEWS"
  },
  "data": {
    "story_id": "story_12345"
  }
}

Setelah

{
  "message": {
    "topic": "news",
    "notification": {
      "title": "Breaking News",
      "body": "New news story available."
    },
    "data": {
      "story_id": "story_12345"
    },
    "android": {
      "notification": {
        "click_action": "TOP_STORY_ACTIVITY",
        "body": "Check out the Top Story"
      }
    },
    "apns": {
      "payload": {
        "aps": {
          "category" : "NEW_MESSAGE_CATEGORY"
        }
      }
    }
  }
}

Untuk mengetahui contoh dan informasi lainnya tentang FCM HTTP v1 API, baca bagian Blog Firebase.