Su extensión puede incluir funciones de Cloud Tasks que se activan cuando una instancia de extensión pasa por cualquiera de los siguientes eventos del ciclo de vida:
- Se instala una instancia de la extensión.
- Una instancia de la extensión se actualiza a una nueva versión
- Se cambia la configuración de una instancia de extensión
Uno de los casos de uso más importantes de esta función es la reposición de datos . Por ejemplo, suponga que está creando una extensión que genera vistas previas en miniatura de las imágenes cargadas en un depósito de Cloud Storage. El trabajo principal de su extensión se realizaría en una función activada por el evento onFinalize
Cloud Storage. Sin embargo, solo se procesarán las imágenes cargadas después de instalar la extensión. Al incluir en su extensión una función activada por el evento del ciclo de vida onInstall
, también puede generar vistas previas en miniatura de cualquier imagen existente cuando se instala la extensión.
Algunos otros casos de uso de activadores de eventos del ciclo de vida incluyen:
- Automatice la configuración posterior a la instalación (creación de registros de base de datos, indexación, etc.)
- Si tiene que publicar cambios incompatibles con versiones anteriores, migre automáticamente los datos en la actualización
Controladores de eventos de ciclo de vida de ejecución corta
Si su tarea puede ejecutarse por completo dentro de la duración máxima de Cloud Functions (9 minutos con la API de primera generación), puede escribir su controlador de eventos de ciclo de vida como una sola función que se activa en el evento onDispatch
de la cola de tareas:
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).
});
Luego, en el archivo extension.yaml
de su extensión, haga lo siguiente:
Registre su función como un recurso de extensión con el conjunto de propiedades
taskQueueTrigger
. Si configurataskQueueTrigger
en el mapa vacío ({}
), su extensión aprovisionará una cola de Cloud Tasks con la configuración predeterminada; Opcionalmente, puede ajustar estos ajustes .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: {}
Registre su función como controlador para uno o más eventos del ciclo de vida:
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
Puede registrar funciones para cualquiera de los siguientes eventos:
onInstall
,onUpdate
yonConfigure
. Todos estos eventos son opcionales.Recomendado : si la tarea de procesamiento no es necesaria para que su extensión funcione, agregue un parámetro configurado por el usuario que les permita elegir habilitarla.
Por ejemplo, agregue un parámetro como el siguiente:
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
Y en su función, si el parámetro se establece en
false
, salga temprano: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. // ... });
Realización de tareas de larga duración
Si su tarea no puede completarse dentro de la duración máxima de Cloud Functions, divida la tarea en subtareas y realice cada subtarea en secuencia poniendo trabajos en cola con el método TaskQueue.enqueue()
del SDK de administración.
Por ejemplo, suponga que desea rellenar los datos de Cloud Firestore. Puede dividir la colección de documentos en fragmentos utilizando cursores de consulta . Después de procesar un fragmento, avance el desplazamiento inicial y ponga en cola otra invocación de función como se muestra a continuación:
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).
}
});
Agrega la función a tu extension.yaml
como se describe en la sección anterior .
Estado de informe
Cuando finalicen todas sus funciones de procesamiento, ya sea con éxito o con un error, informe el estado de la tarea utilizando los métodos de tiempo de ejecución de extensión del SDK de administrador. Los usuarios pueden ver este estado en la página de detalles de la extensión en Firebase console.
Finalización exitosa y errores no fatales
Para informar sobre la finalización exitosa y los errores no fatales (errores que no ponen la extensión en un estado no funcional), use el método de tiempo de ejecución de la extensión setProcessingState()
del SDK de administración:
import { getExtensions } from "firebase-admin/extensions";
// ...
getExtensions().runtime().setProcessingState(processingState, message);
Puede establecer los siguientes estados:
Estados no fatales | |
---|---|
PROCESSING_COMPLETE | Úselo para informar sobre la finalización exitosa de la tarea. Ejemplo: getExtensions().runtime().setProcessingState( "PROCESSING_COMPLETE", `Backfill complete. Successfully processed ${numSuccess} documents.` ); |
PROCESSING_WARNING | Se utiliza para informar de un éxito parcial. Ejemplo: getExtensions().runtime().setProcessingState( "PROCESSING_WARNING", `Backfill complete. ${numSuccess} documents processed successfully.` + ` ${numFailed} documents failed to process. ${listOfErrors}.` + ` ${instructionsToFixTheProblem}` ); |
PROCESSING_FAILED | Úselo para informar errores que impiden que se complete la tarea, pero no deje la extensión inutilizable. Ejemplo: getExtensions().runtime().setProcessingState( "PROCESSING_FAILED", `Backfill failed. ${errorMsg} ${optionalInstructionsToFixTheProblem}.` ); Para informar errores que dejan la extensión inutilizable, llama |
NONE | Úselo para borrar el estado de la tarea. Opcionalmente, puede usar esto para borrar el mensaje de estado de la consola (por ejemplo, después de que haya pasado una cantidad de tiempo desde que se configuró getExtensions().runtime().setProcessingState("NONE"); |
Errores fatales
Si ocurre un error que impide que la extensión funcione, por ejemplo, falla una tarea de configuración requerida, informe el error fatal con setFatalError()
:
import { getExtensions } from "firebase-admin/extensions";
// ...
getExtensions().runtime().setFatalError(`Post-installation setup failed. ${errorMessage}`);
Ajuste de la cola de tareas
Si establece la propiedad taskQueueTrigger
en {}
, su extensión aprovisionará una cola de Cloud Tasks con la configuración predeterminada cuando se instale una instancia de extensión. Como alternativa, puede ajustar los límites de simultaneidad de la cola de tareas y el comportamiento de reintento proporcionando valores específicos:
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
Consulte Configurar las colas de Cloud Tasks en los documentos de Google Cloud para obtener detalles sobre estos parámetros.
Ejemplos
Las extensiones oficiales storage-resize-images
, firestore-bigquery-export
y firestore-translate-text
utilizan controladores de eventos del ciclo de vida para rellenar los datos.