Un evento se puede rechazar por varios motivos. Por ejemplo, el servicio de receptor de eventos puede no estar disponible temporalmente debido a una interrupción, el servicio puede encontrar un error al procesar un evento o los recursos del servicio pueden agotarse. Los errores transitorios como este se pueden volver a intentar.
También puede ocurrir que un evento no se entregue al receptor. Por ejemplo, puede que el evento no coincida con el esquema configurado o que la mediación del evento falle antes de que el mensaje del evento se pueda enrutar a su destino final. En estos casos, se producen errores persistentes.
Errores transitorios
Eventarc Advanced te permite gestionar errores transitorios. Estos errores transitorios se pueden volver a intentar e incluyen los que tienen los siguientes códigos de error:
- HTTP
408 Request Timeout
- HTTP
409 Conflict
- HTTP
429 Too Many Requests
- HTTP
500 Internal Server Error
- HTTP
502 Bad Gateway
- HTTP
503 Service Unavailable
- HTTP
504 Gateway Time-out
Errores persistentes
A diferencia de los errores transitorios, los errores persistentes incluyen los siguientes:
- Errores que se producen cuando se agota el número de reintentos configurados
- Errores que se producen cuando un evento falla antes de que se pueda enrutar a su destino.
- Errores que dan como resultado un código de error que se considera que no se puede volver a intentar. Por ejemplo, códigos de error distintos de los que se indican en los errores transitorios.
Puedes identificar manualmente los errores persistentes y gestionarlos de forma adecuada.
Reintentar errores transitorios
Eventarc Advanced usa un retraso de tiempo de espera exponencial para gestionar los errores que se pueden volver a intentar. La política de reintento predeterminada empieza con un retraso de un segundo y el retraso se duplica después de cada intento fallido (hasta un máximo de 60 segundos y cinco intentos).
Puedes cambiar la política de reintentos predeterminada mediante la consola Google Cloud o el comando gcloud eventarc pipelines update
.
Ten en cuenta que el factor de espera predeterminado de 2
no se puede cambiar.
Consola
En la Google Cloud consola, ve a la página Eventarc > Pipelines.
Haz clic en el nombre de la canalización.
En la página Detalles de la canalización, haz clic en Editar.
En la página Editar canalización, en la sección Política de reintentos, modifique los siguientes campos:
- Número máximo de intentos: número de reintentos. El valor predeterminado es
5
intentos. Puede ser cualquier número real positivo. Si se asigna el valor1
, no se aplica ninguna política de reintento y solo se hace un intento para entregar un mensaje. - Retraso mínimo (segundos): el retraso inicial en segundos. El valor predeterminado es
1
segundo. Debe ser un valor entre1
y600
. - Retraso máximo (segundos): el retraso máximo en segundos. El valor predeterminado es
60
segundos. Debe ser un valor entre1
y600
.
Puedes configurar un retroceso lineal asignando el mismo valor a los retrasos mínimo y máximo.
- Número máximo de intentos: número de reintentos. El valor predeterminado es
Haz clic en Guardar.
gcloud
gcloud eventarc pipelines update PIPELINE_NAME \
--min-retry-delay=MIN_DELAY \
--max-retry-delay=MAX_DELAY \
--max-retry-attempts=MAX_ATTEMPTS
Haz los cambios siguientes:
PIPELINE_NAME
: el ID o el identificador completo del flujo de trabajo.MIN_DELAY
: el retraso inicial en segundos. El valor predeterminado es1
segundo. Debe ser un valor entre1
y600
.MAX_DELAY
: el retraso máximo en segundos. El valor predeterminado es60
segundos. Debe ser un valor entre1
y600
.MAX_ATTEMPTS
: número de reintentos. El valor predeterminado es5
intentos. Puede ser cualquier número real positivo. Si se define como1
, no se aplica ninguna política de reintentos y solo se hace un intento para entregar un mensaje.
En el siguiente ejemplo se configura un retroceso lineal asignando el mismo valor a los retrasos mínimo y máximo:
gcloud eventarc pipelines update my-pipeline \
--min-retry-delay=4 \
--max-retry-delay=4 \
--max-retry-attempts=5
Archivar mensajes para gestionar errores persistentes
Puedes escribir mensajes en una tabla de BigQuery a medida que se reciben. De esta forma, puedes identificar manualmente los errores persistentes y gestionarlos de forma adecuada.
A continuación, se ofrece una descripción general de los pasos necesarios para archivar los mensajes de eventos, identificar los errores persistentes y volver a intentar los eventos afectados.
- Crea un autobús. Configurar el bus correctamente; por ejemplo, para publicar eventos de fuentes de Google.
- Crea un tema de Pub/Sub. Este tema de Pub/Sub será el destino de tu canalización.
- Crea una suscripción de BigQuery para el tema de Pub/Sub. Una suscripción de BigQuery es un tipo de suscripción de exportación que escribe mensajes en una tabla de BigQuery a medida que se reciben. También puedes crear la tabla al crear la suscripción a BigQuery.
Crea una canalización y un registro que dirija todos los mensajes recibidos por el bus (con
--cel-match="true"
) al tema de Pub/Sub. Configura una política de reintentos para la canalización.Por ejemplo, los siguientes comandos crean una canalización y un registro:
gcloud eventarc pipelines create my-archive-pipeline \ --destinations=pubsub_topic='my-archive-topic' \ --min-retry-delay=1 \ --max-retry-delay=20 \ --max-retry-attempts=6 \ --location=us-central1
gcloud eventarc enrollments create my-archive-enrollment \ --cel-match="true" \ --destination-pipeline=my-archive-pipeline \ --message-bus=my-message-bus \ --message-bus-project=my-google-cloud-project \ --location=us-central1
Dirige los registros de tu flujo de procesamiento a otro conjunto de datos de BigQuery.
Ahora debería tener dos conjuntos de datos de BigQuery independientes: uno que almacene todos los mensajes recibidos por su bus avanzado de Eventarc y otro que almacene los registros de su canalización.
Para identificar los mensajes que han fallado, usa una instrucción de consulta para combinar ambos conjuntos de datos de BigQuery en el campo
message_uid
.Una vez que haya identificado los mensajes fallidos, puede volver a publicarlos en su bus mediante la API Eventarc Publishing. Por ejemplo, puedes desplegar un servicio o un trabajo de Cloud Run para leer los mensajes de BigQuery y publicarlos directamente en el bus avanzado de Eventarc.
Hacer que los controladores de eventos sean idempotentes
Los controladores de eventos que se pueden volver a intentar deben ser idempotentes y seguir estas directrices generales:
- Muchas APIs externas te permiten proporcionar una clave de idempotencia como parámetro. Si usas una API de este tipo, debes usar la fuente y el ID del evento como clave de idempotencia. Los productores deben asegurarse de que source + id sea único para cada evento distinto.
- Además, puedes usar el atributo
xgooglemessageuid
de CloudEvents para proporcionar idempotencia. El valor de este atributo es el mismo que el del campomessage_uid
de los mensajes avanzados de Eventarc. Identifica de forma única la acción de publicar un evento. Por ejemplo, si el mismo evento se publica dos veces en un bus, cada evento tendrá un valorxgooglemessageuid
diferente cuando se envíe a un controlador de eventos. - La idempotencia funciona bien con la entrega al menos una vez, ya que permite reintentar la operación de forma segura. Por lo tanto, una práctica recomendada general para escribir código fiable es combinar la idempotencia con los reintentos.
- Asegúrate de que tu código sea idempotente internamente. Por ejemplo:
- Asegúrate de que las mutaciones puedan producirse más de una vez sin cambiar el resultado.
- Consulta el estado de la base de datos en una transacción antes de mutar el estado.
- Asegúrate de que todos los efectos secundarios sean idempotentes.
- Imponer una comprobación transaccional fuera de tu servicio, independientemente del código. Por ejemplo, persiste el estado en algún lugar registrando que ya se ha procesado un ID de evento determinado.
- Gestiona las llamadas duplicadas fuera de banda. Por ejemplo, puedes tener un proceso de limpieza independiente que se ejecute después de las llamadas duplicadas.