Ekstensi Anda dapat mencakup fungsi Cloud Tasks yang terpicu saat instance ekstensi melewati salah satu peristiwa siklus proses berikut:
- Instance ekstensi diinstal
- Instance ekstensi diperbarui ke versi baru
- Konfigurasi instance ekstensi diubah
Salah satu kasus penggunaan terpenting dari fitur ini adalah mengisi ulang data. Misalnya,
Anda sedang mem-build ekstensi yang menghasilkan pratinjau thumbnail gambar
yang diupload ke bucket Cloud Storage. Pekerjaan utama ekstensi Anda
akan dilakukan dalam fungsi yang dipicu oleh peristiwa Cloud Storage onFinalize
.
Namun, hanya gambar yang diupload setelah ekstensi diinstal yang akan
diproses. Dengan menyertakan fungsi yang dipicu oleh peristiwa siklus proses
onInstall
ke dalam ekstensi, Anda juga dapat membuat pratinjau thumbnail gambar yang
sudah ada saat ekstensi diinstal.
Beberapa kasus penggunaan lainnya dari pemicu peristiwa siklus proses mencakup:
- Mengotomatiskan penyiapan pascapenginstalan (membuat catatan database, pengindeksan, dll.)
- Jika Anda harus memublikasikan perubahan yang tidak kompatibel dengan versi sebelumnya, migrasikan data secara otomatis saat update
Pengendali peristiwa siklus proses jangka pendek
Jika tugas Anda dapat berjalan sepenuhnya dalam
durasi Cloud Functions maksimum (9 menit
menggunakan API generasi pertama), Anda dapat menulis pengendali peristiwa siklus
proses sebagai fungsi tunggal yang memicu peristiwa onDispatch
task queue:
export const myTaskFunction = functions.tasks.taskQueue()
.onDispatch(async () => {
// Complete your lifecycle event handling task.
// ...
// When processing is complete, report status to the user (see below).
});
Kemudian, di file extension.yaml
ekstensi, lakukan hal berikut:
Daftarkan fungsi Anda sebagai resource ekstensi dengan properti
taskQueueTrigger
yang ditetapkan. Jika Anda menetapkantaskQueueTrigger
ke peta kosong ({}
), ekstensi Anda akan menyediakan antrean Cloud Tasks menggunakan setelan default; Anda dapat secara opsional menyesuaikan setelan ini.resources: - name: myTaskFunction type: firebaseextensions.v1beta.function description: >- Describe the task performed when the function is triggered by a lifecycle event properties: location: ${LOCATION} taskQueueTrigger: {}
Daftarkan fungsi Anda sebagai pengendali untuk satu atau beberapa peristiwa siklus proses:
resources: - ... lifecycleEvents: onInstall: function: myTaskFunction processingMessage: Resizing your existing images onUpdate: function: myOtherTaskFunction processingMessage: Setting up your extension onConfigure: function: myOtherTaskFunction processingMessage: Setting up your extension
Anda dapat mendaftarkan fungsi untuk salah satu peristiwa berikut:
onInstall
,onUpdate
, danonConfigure
. Semua peristiwa ini bersifat opsional.Direkomendasikan: Jika tugas pemrosesan tidak wajib ada agar ekstensi Anda berfungsi, tambahkan parameter yang dikonfigurasi pengguna yang memungkinkan pengguna memilih apakah akan mengaktifkannya atau tidak.
Misalnya, tambahkan parameter seperti berikut:
params: - param: DO_BACKFILL label: Backfill existing images description: > Should existing, unresized images in the Storage bucket be resized as well? type: select options: - label: Yes value: true - label: No value: false
Dan di fungsi Anda, jika parameter ditetapkan ke
false
, keluar lebih awal:export const myTaskFunction = functions.tasks.taskQueue() .onDispatch(async () => { if (!process.env.DO_BACKFILL) { await runtime.setProcessingState( "PROCESSING_COMPLETE", "Existing images were not resized." ); return; } // Complete your lifecycle event handling task. // ... });
Melakukan tugas yang berjalan lama
Jika tugas Anda tidak dapat diselesaikan dalam durasi Cloud Functions maksimum,
pecah tugas ke dalam beberapa subtugas dan lakukan setiap subtugas secara berurutan
dengan mengantrekan tugas menggunakan metode TaskQueue.enqueue()
Admin SDK.
Misalnya, Anda ingin mengisi ulang data Cloud Firestore. Anda dapat membagi koleksi dokumen menjadi beberapa bagian menggunakan query cursor. Setelah memproses satu bagian, majukan offset awal ke proses selanjutnya dan antrekan pemanggilan fungsi lainnya seperti yang ditunjukkan di bawah ini:
import { getFirestore } from "firebase-admin/firestore";
import { getFunctions } from "firebase-admin/functions";
exports.backfilldata = functions.tasks.taskQueue().onDispatch(async (data) => {
// When a lifecycle event triggers this function, it doesn't pass any data,
// so an undefined offset indicates we're on our first invocation and should
// start at offset 0. On subsequent invocations, we'll pass an explicit
// offset.
const offset = data["offset"] ?? 0;
// Get a batch of documents, beginning at the offset.
const snapshot = await getFirestore()
.collection(process.env.COLLECTION_PATH)
.startAt(offset)
.limit(DOCS_PER_BACKFILL)
.get();
// Process each document in the batch.
const processed = await Promise.allSettled(
snapshot.docs.map(async (documentSnapshot) => {
// Perform the processing.
})
);
// If we processed a full batch, there are probably more documents to
// process, so enqueue another invocation of this function, specifying
// the offset to start with.
//
// If we processed less than a full batch, we're done.
if (processed.length == DOCS_PER_BACKFILL) {
const queue = getFunctions().taskQueue(
"backfilldata",
process.env.EXT_INSTANCE_ID
);
await queue.enqueue({
offset: offset + DOCS_PER_BACKFILL,
});
} else {
// Processing is complete. Report status to the user (see below).
}
});
Tambahkan fungsi ke extension.yaml
seperti yang dijelaskan di bagian sebelumnya.
Status pelaporan
Setelah semua fungsi pemrosesan selesai, baik berhasil atau mengalami error, laporkan status tugas menggunakan metode runtime ekstensi Admin SDK. Pengguna dapat melihat status ini di halaman detail ekstensi di Firebase console.
Penyelesaian yang berhasil dan error non-fatal
Untuk melaporkan keberhasilan penyelesaian dan error non-fatal (error yang tidak menempatkan ekstensi ke status tidak berfungsi), gunakan metode runtime ekstensi setProcessingState()
Admin SDK:
import { getExtensions } from "firebase-admin/extensions";
// ...
getExtensions().runtime().setProcessingState(processingState, message);
Anda dapat menetapkan status berikut:
Status non-fatal | |
---|---|
PROCESSING_COMPLETE |
Gunakan untuk melaporkan penyelesaian tugas yang berhasil. Contoh: getExtensions().runtime().setProcessingState( "PROCESSING_COMPLETE", `Backfill complete. Successfully processed ${numSuccess} documents.` ); |
PROCESSING_WARNING |
Gunakan untuk melaporkan keberhasilan sebagian. Contoh: getExtensions().runtime().setProcessingState( "PROCESSING_WARNING", `Backfill complete. ${numSuccess} documents processed successfully.` + ` ${numFailed} documents failed to process. ${listOfErrors}.` + ` ${instructionsToFixTheProblem}` ); |
PROCESSING_FAILED |
Gunakan untuk melaporkan error yang mencegah tugas diselesaikan, tetapi jangan biarkan ekstensi tidak dapat digunakan. Contoh: getExtensions().runtime().setProcessingState( "PROCESSING_FAILED", `Backfill failed. ${errorMsg} ${optionalInstructionsToFixTheProblem}.` ); Untuk melaporkan error yang memang menyebabkan ekstensi tidak dapat digunakan, panggil
|
NONE |
Gunakan untuk menghapus status tugas. Secara opsional, Anda dapat menggunakannya untuk menghapus pesan status dari konsol (misalnya, setelah beberapa waktu berlalu sejak menyiapkan getExtensions().runtime().setProcessingState("NONE"); |
Error fatal
Jika terjadi error yang mencegah ekstensi berfungsi—misalnya, tugas penyiapan yang wajib mengalami kegagalan—laporkan error fatal dengan
setFatalError()
:
import { getExtensions } from "firebase-admin/extensions";
// ...
getExtensions().runtime().setFatalError(`Post-installation setup failed. ${errorMessage}`);
Menyesuaikan task queue
Jika Anda menetapkan properti taskQueueTrigger
ke {}
, ekstensi Anda akan menyediakan antrean Cloud Tasks dengan setelan default saat instance ekstensi diinstal. Atau, Anda dapat menyesuaikan batas serentak dan perilaku percobaan ulang task queue dengan memberikan nilai tertentu:
resources:
- name: myTaskFunction
type: firebaseextensions.v1beta.function
description: >-
Perform a task when triggered by a lifecycle event
properties:
location: ${LOCATION}
taskQueueTrigger:
rateLimits:
maxConcurrentDispatches: 1000
maxDispatchesPerSecond: 500
retryConfig:
maxAttempts: 100 # Warning: setting this too low can prevent the function from running
minBackoffSeconds: 0.1
maxBackoffSeconds: 3600
maxDoublings: 16
lifecycleEvents:
onInstall:
function: myTaskFunction
processingMessage: Resizing your existing images
onUpdate:
function: myTaskFunction
processingMessage: Setting up your extension
onConfigure:
function: myOtherTaskFunction
processingMessage: Setting up your extension
Baca artikel Mengonfigurasi antrean Cloud Tasks di dokumen Google Cloud untuk mengetahui detail tentang parameter ini.
Jangan mencoba menentukan parameter task queue dengan meneruskannya ke taskQueue()
.
Setelan ini diabaikan untuk mendukung konfigurasi di extension.yaml
dan
konfigurasi default.
Misalnya, hal berikut tidak akan berfungsi:
export const myBrokenTaskFunction = functions.tasks
// DON'T DO THIS IN AN EXTENSION! THESE SETTINGS ARE IGNORED.
.taskQueue({
retryConfig: {
maxAttempts: 5,
minBackoffSeconds: 60,
},
rateLimits: {
maxConcurrentDispatches: 1000,
maxDispatchesPerSecond: 10,
},
})
.onDispatch(
// ...
);
Properti taskQueueTrigger
di extension.yaml
adalah satu-satunya cara untuk mengonfigurasi
antrean tugas ekstensi.
Contoh
Semua ekstensi storage-resize-images
,
firestore-bigquery-export
,
dan firestore-translate-text
resmi menggunakan pengendali peristiwa siklus proses untuk mengisi ulang data.