Almacena en búfer las solicitudes HTTP con Cloud Tasks

1. Introducción

c6ac6ed05292f13e.png

Cloud Tasks es un servicio de colas completamente administrado para controlar la ejecución, el envío y la entrega de una gran cantidad de tareas.

Cloud Tasks te permite separar trabajos, llamados tareas, que se pueden realizar de forma independiente (p. ej., una tarea para actualizar la entrada de una base de datos), fuera del flujo de tu aplicación principal, y enviarlos para que se procesen de manera asíncrona con los controladores que crees.

La tarea descargada se agrega a una cola, que mantiene la tarea hasta que se ejecuta correctamente o se produce una falla. Según la configuración, la cola también puede actuar como un control de flujo de despacho. Tú creas y configuras la cola, que luego administra el servicio de Cloud Tasks. Una vez que se agregan las tareas, la cola las envía y se asegura de que los trabajadores las procesen de manera confiable.

d59ffe8d34138c88.png

Estas son algunas de las funciones principales de Cloud Tasks:

  • Destinos HTTP: Agrega tareas que se orienten a cualquier servicio HTTP que se ejecute en Compute Engine, Google Kubernetes Engine, Cloud Run, Cloud Functions o sistemas locales de manera segura con la autenticación OAuth/OIDC estándar de la industria.
  • Anulación de duplicación de tareas: Las tareas agregadas varias veces solo se despacharán una vez.
  • Entrega garantizada: Se garantiza que las tareas se entregarán al menos una vez, y la mayoría de las tareas se entregarán exactamente una vez.
  • Controles de frecuencia y reintento: Para controlar la ejecución, configura la velocidad con la que se despachan las tareas, la cantidad máxima de intentos y la cantidad mínima de tiempo de espera entre intentos.
  • Programación futura: Controla la hora a la que se ejecuta una tarea.

En este codelab, primero aprenderás a crear y usar una cola normal de Cloud Tasks para tareas de destino HTTP. Luego, aprenderás a usar la anulación de URI HTTP a nivel de la cola y la nueva API de BufferTask para almacenar en búfer las solicitudes HTTP con más facilidad con Cloud Tasks.

Qué aprenderás

  • Cómo crear tareas de destino HTTP
  • Cómo crear tareas de destino HTTP con la nueva anulación de URI HTTP a nivel de la cola
  • Cómo cambiar las tareas pendientes con la nueva anulación de URI HTTP a nivel de la cola
  • Cómo almacenar solicitudes HTTP en búfer con mayor facilidad con la nueva API de BufferTask

2. Configuración y requisitos

Cómo configurar el entorno a tu propio ritmo

  1. Accede a Google Cloud Console y crea un proyecto nuevo o reutiliza uno existente. Si aún no tienes una cuenta de Gmail o de Google Workspace, debes crear una.

b35bf95b8bf3d5d8.png

a99b7ace416376c4.png

bd84a6d3004737c5.png

  • El Nombre del proyecto es el nombre visible de los participantes de este proyecto. Es una cadena de caracteres que no se utiliza en las APIs de Google. Puedes actualizarla cuando quieras.
  • El ID del proyecto es único en todos los proyectos de Google Cloud y es inmutable (no se puede cambiar después de configurarlo). La consola de Cloud genera automáticamente una cadena única. Por lo general, no importa cuál sea. En la mayoría de los codelabs, deberás hacer referencia al ID de tu proyecto (suele identificarse como PROJECT_ID). Si no te gusta el ID que se generó, podrías generar otro aleatorio. También puedes probar uno propio y ver si está disponible. No se puede cambiar después de este paso y se usa el mismo durante todo el proyecto.
  • Recuerda que hay un tercer valor, un número de proyecto, que usan algunas APIs. Obtén más información sobre estos tres valores en la documentación.
  1. A continuación, deberás habilitar la facturación en la consola de Cloud para usar las APIs o los recursos de Cloud. Ejecutar este codelab no costará mucho, tal vez nada. Para cerrar recursos y evitar que se generen cobros más allá de este instructivo, puedes borrar los recursos que creaste o borrar el proyecto. Los usuarios nuevos de Google Cloud son aptos para participar en el programa Prueba gratuita de $300.

Inicie Cloud Shell

Si bien Google Cloud y Spanner se pueden operar de manera remota desde tu laptop, en este codelab usarás Google Cloud Shell, un entorno de línea de comandos que se ejecuta en la nube.

En Google Cloud Console, haz clic en el ícono de Cloud Shell en la barra de herramientas en la parte superior derecha:

55efc1aaa7a4d3ad.png

El aprovisionamiento y la conexión al entorno deberían tomar solo unos minutos. Cuando termine el proceso, debería ver algo como lo siguiente:

7ffe5cbb04455448.png

Esta máquina virtual está cargada con todas las herramientas de desarrollo que necesitarás. Ofrece un directorio principal persistente de 5 GB y se ejecuta en Google Cloud, lo que permite mejorar considerablemente el rendimiento de la red y la autenticación. Todo tu trabajo en este codelab se puede hacer en un navegador. No es necesario que instales nada.

3. Crea una cola normal para las tareas de destino HTTP

En este primer paso, aprenderás a crear una cola normal de Cloud Tasks y a agregarle tareas HTTP para segmentar un servicio de Cloud Run.

d4f09a342c8eab.png

¿Qué son las tareas de destino HTTP?

Las tareas de destino HTTP pueden orientarse a cualquier servicio HTTP que se ejecute en Compute Engine, Google Kubernetes Engine, Cloud Run, Cloud Functions o sistemas locales de manera segura con la autenticación OAuth/OIDC estándar de la industria.

Implementa un servicio de Cloud Run

Primero, asegúrate de que estén habilitadas las APIs necesarias:

gcloud services enable \
  cloudtasks.googleapis.com \
  run.googleapis.com

Implementa un servicio de Cloud Run que sirva como destino de las tareas HTTP:

SERVICE1=hello1
REGION=us-central1

gcloud run deploy $SERVICE1 \
  --allow-unauthenticated \
  --image=gcr.io/cloudrun/hello \
  --region=$REGION

Crea una cola de Cloud Tasks

Crea una cola normal de Cloud Tasks:

QUEUE1=http-queue
LOCATION=us-central1

gcloud tasks queues create $QUEUE1 --location=$LOCATION

Pausa la cola temporalmente para que puedas observar las tareas HTTP a medida que se crean:

gcloud tasks queues pause $QUEUE1 --location=$LOCATION

4. Crea y prueba una tarea HTTP

En este paso, crearás una tarea HTTP para apuntar a la cola que creaste anteriormente.

Crea una tarea HTTP

Puedes crear tareas HTTP con gcloud:

gcloud tasks create-http-task \
    --queue=$QUEUE1 \
    --location=$LOCATION \
    --url=$SERVICE1_URL \
    --method=GET

Opcional: También puedes crear una tarea HTTP con bibliotecas cliente. Por ejemplo, puedes consultar el Program.cs de una muestra de C# en la que una solicitud HTTP se une en un Task y un TaskRequest antes de enviarse a Cloud Tasks con un CloudTasksClient:

var taskRequest = new CreateTaskRequest
{
    Parent = new QueueName(projectId, location, queue).ToString(),
    Task = new Task
    {
        HttpRequest = new HttpRequest
        {
            HttpMethod = HttpMethod.Get,
            Url = url
        }
    }
};

var client = CloudTasksClient.Create();
var response = client.CreateTask(taskRequest);

Puedes ejecutarla de la siguiente manera para crear la tarea y agregarla a la cola:

dotnet run $PROJECT_ID $LOCATION $QUEUE1 $SERVICE1_URL

Prueba la tarea HTTP

En este punto, se crea la tarea, pero aún no se ejecuta, ya que la cola está detenida. Para verificarlo, obtén una lista de las colas:

gcloud tasks queues list --location=$LOCATION

Deberías ver la cola en estado PAUSED:

QUEUE_NAME  STATE
http-queue  PAUSED

Reanuda la cola:

gcloud tasks queues resume $QUEUE --location=$LOCATION

Verifica los registros del servicio de Cloud Run:

gcloud logging read "resource.type=cloud_run_revision AND resource.labels.service_name=$SERVICE1" --limit 1

Deberías ver que el servicio de Cloud Run recibió una solicitud GET de HTTP de Cloud Tasks:

httpRequest:
  latency: 0.227597158s
  protocol: HTTP/1.1
  remoteIp: 35.243.23.192
  requestMethod: GET
  requestSize: '415'
  requestUrl: https://hello1-idcwffc3yq-uc.a.run.app/
  responseSize: '5510'
  serverIp: 216.239.32.53
  status: 200
  userAgent: Google-Cloud-Tasks

5. Crea una cola con una configuración de enrutamiento

En este paso, aprenderás a crear una cola de Cloud Tasks con una configuración de enrutamiento para agregar una anulación de URI HTTP con la función Configuración de enrutamiento de tareas a nivel de cola. Luego, agregarás tareas HTTP para orientar las tareas al primer servicio de Cloud Run y observarás que la configuración de enrutamiento anula el URI para enrutar las tareas al segundo servicio de Cloud Run.

5d1ec61a933f77.png

¿Qué es la configuración de enrutamiento de tareas a nivel de cola?

La configuración del enrutamiento de tareas a nivel de la cola cambia el enrutamiento de las tareas HTTP de toda la cola para todas las tareas pendientes y nuevas. Esto facilita la creación de tareas, ya que no es necesario establecer el destino HTTP a nivel de la tarea y transfiere más control al proveedor de servicios, ya que este puede establecer el destino de todas las tareas en una cola (p. ej., enrutar el tráfico a un backend diferente si el backend original está inactivo).

Se puede establecer la siguiente configuración en el nivel de la cola:

  • Encabezados: Los encabezados a nivel de la cola, cuando se especifican a nivel de la cola, insertarán encabezados en todas las tareas de la cola.
  • Método HTTP: Cuando se especifica a nivel de la cola, es un método HTTP, que anula el método HTTP para todas las tareas en la cola.
  • URI de destino: El host, la ruta de acceso, la consulta, el puerto y el esquema (HTTP o HTTPS) se pueden anular de forma individual.
  • Autorización: Cuando se especifique a nivel de la cola, la configuración de OIDC/OAuth anulará la configuración de OIDC/OAuth a nivel de la tarea.

Implementa un segundo servicio de Cloud Run

Implementa un segundo servicio de Cloud Run, que funcionará como destino de la anulación del URI HTTP más adelante:

SERVICE2=hello2
REGION=us-central1

gcloud run deploy $SERVICE2 \
  --allow-unauthenticated \
  --image=gcr.io/cloudrun/hello \
  --region=$REGION

Guarda el host de la URL del servicio para más adelante:

SERVICE2_URL=$(gcloud run services describe $SERVICE2 --region $REGION --format 'value(status.url)')
SERVICE2_HOST=$(echo $SERVICE2_URL | sed 's,http[s]*://,,g')

Crea una cola de Cloud Tasks con una configuración de enrutamiento

Crear una cola con una configuración de enrutamiento con anulación de URI HTTP al segundo servicio de Cloud Run

QUEUE2=http-queue-uri-override

gcloud beta tasks queues create $QUEUE2 \
  --http-uri-override=host:$SERVICE2_HOST \
  --location=$LOCATION

Ten en cuenta que la anulación del URI hace referencia al segundo servicio de Cloud Run. Cualquier tarea HTTP agregada a la cola tendrá su host de URI original anulado. Puedes ver la configuración de la cola:

gcloud beta tasks queues describe $QUEUE2 --location=$LOCATION

Deberías ver que httpTarget tiene un uriOverride que apunta al host del segundo servicio:

httpTarget:
  uriOverride:
    host: hello2-idcwffc3yq-uc.a.run.app
    pathOverride: {}
    queryOverride: {}
...

Pausa la cola temporalmente para que puedas observar las tareas HTTP a medida que se crean:

gcloud tasks queues pause $QUEUE2 --location=$LOCATION

6. Crea y prueba una tarea HTTP para la cola con la configuración de enrutamiento.

En este paso, crearás una tarea HTTP para dirigirte al primer servicio y observarás que la cola anula su URI para que apunte al segundo servicio.

Crea una tarea HTTP

Crea una tarea HTTP con la URL del primer servicio:

gcloud tasks create-http-task \
    --queue=$QUEUE2 \
    --location=$LOCATION \
    --url=$SERVICE1_URL \
    --method=GET

Prueba la tarea HTTP

Reanuda la cola:

gcloud tasks queues resume $QUEUE2 --location=$LOCATION

Deberías ver que el segundo servicio de Cloud Run (no el primero) recibió una solicitud HTTP GET de Cloud Tasks debido a la anulación:

gcloud logging read "resource.type=cloud_run_revision AND resource.labels.service_name=$SERVICE2" --limit 1
---
httpRequest:
  latency: 0.228982142s
  protocol: HTTP/1.1
  remoteIp: 35.187.132.84
  requestMethod: GET
  requestSize: '426'
  requestUrl: https://hello2-idcwffc3yq-uc.a.run.app/
  responseSize: '5510'
  serverIp: 216.239.34.53
  status: 200
  userAgent: Google-Cloud-Tasks

7. Cambia las tareas pendientes con la configuración de enrutamiento

También puedes usar la configuración de enrutamiento para cambiar el URI HTTP de todas las tareas pendientes en una cola. Esto es útil si el servicio de backend falla y quieres enrutar rápidamente a otro servicio. Veamos cómo funciona en este paso.

Vuelve a pausar la cola:

gcloud tasks queues pause $QUEUE2 --location=$LOCATION

Crea una tarea HTTP con google.com como la URL de la tarea:

gcloud tasks create-http-task \
    --queue=$QUEUE2 \
    --location=$LOCATION \
    --url=https://www.google.com \
    --method=GET

La tarea se encuentra en estado pendiente porque la cola está en pausa.

Ahora actualiza la anulación del URI de HTTP para que apunte al primer servicio. Esto anulará el host de la tarea pendiente de google.com al host del primer servicio:

SERVICE1_URL=$(gcloud run services describe $SERVICE1 --region $REGION --format 'value(status.url)')
SERVICE1_HOST=$(echo $SERVICE1_URL | sed 's,http[s]*://,,g')

gcloud beta tasks queues update $QUEUE2 \
  --http-uri-override=host:$SERVICE1_HOST \
  --location=$LOCATION

Reanuda la cola:

gcloud tasks queues resume $QUEUE2 --location=$LOCATION

Deberías ver que el primer servicio de Cloud Run recibió una solicitud GET HTTP de Cloud Tasks debido a la anulación (en lugar de google.com):

gcloud logging read "resource.type=cloud_run_revision AND resource.labels.service_name=$SERVICE1" --limit 1
---
httpRequest:
  latency: 0.228982142s
  protocol: HTTP/1.1
  remoteIp: 35.187.132.84
  requestMethod: GET
  requestSize: '426'
  requestUrl: https://hello1-idcwffc3yq-uc.a.run.app/
  responseSize: '5510'
  serverIp: 216.239.34.53
  status: 200
  userAgent: Google-Cloud-Tasks

8. Crea una cola para la API de BufferTask

Por lo general, las tareas se crean con la API de Tasks, ya sea desde gcloud o desde las bibliotecas cliente de Tasks. Esto obliga a las aplicaciones a unir solicitudes HTTP en Tasks mediante bibliotecas cliente y crea una dependencia entre las aplicaciones y las bibliotecas cliente de Tasks.

En este paso, verás cómo aprovechar la anulación de URI HTTP a nivel de la cola y la nueva API de BufferTask para crear tareas de destino HTTP con mayor facilidad con solo enviar una solicitud HTTP. Cualquier aplicación que pueda enviar solicitudes HTTP ahora puede crear tareas de destino HTTP.

b1606516297fc4b6.png

¿Qué es la API de BufferTask?

La API de CreateTask es la forma anterior de crear tareas y requiere que el cliente envíe un objeto Task a la API con todos los campos obligatorios establecidos.

La API de BufferTask es una nueva función que permite a los usuarios crear una tarea HTTP sin necesidad de proporcionar ninguna configuración de tarea (URL HTTP, encabezados, autorización), lo que te permite enviar un mensaje o el cuerpo de tu solicitud a la API de Buffer.

Esto facilita la integración en los servicios, ya que ahora se puede implementar Cloud Tasks frente a tu servicio sin necesidad de realizar cambios en el código del cliente. Cualquier solicitud HTTP arbitraria que se envíe a la API de BufferTask se unirá como un objeto Task y se entregará al destino establecido en el nivel de la cola.

Para usar la API de BufferTask, la cola debe tener establecida la configuración del URI de destino o, en otras palabras, la función Configuración de enrutamiento a nivel de cola es un requisito previo para usar la API de BufferTask.

Crea una cola de Cloud Tasks con la configuración de enrutamiento

Crea una cola con una configuración de enrutamiento que apunte al primer servicio que implementamos en el paso anterior:

SERVICE1=hello1
SERVICE1_URL=$(gcloud run services describe $SERVICE1 --region $REGION --format 'value(status.url)')
SERVICE1_HOST=$(echo $SERVICE1_URL | sed 's,http[s]*://,,g')
QUEUE3=http-queue-uri-override-buffer

gcloud beta tasks queues create $QUEUE3 \
  --http-uri-override=host:$SERVICE1_HOST \
  --location=$LOCATION

Pausa la cola temporalmente para que puedas observar las tareas HTTP a medida que se crean:

gcloud tasks queues pause $QUEUE3 --location=$LOCATION

9. Almacena solicitudes HTTP en búfer con la API de BufferTask

En este paso, almacenarás en búfer solicitudes HTTP GET o POST simples con la API de BufferTask. Cloud Tasks unirá estas solicitudes HTTP en tareas HTTP con la configuración de enrutamiento predeterminada de la cola.

Primero, accede para obtener un token de acceso y establece algunas variables:

gcloud auth application-default login
ACCESS_TOKEN=$(gcloud auth application-default print-access-token)
PROJECT_ID=$(gcloud config get-value project)
TASKS_QUEUES_API="https://cloudtasks.googleapis.com/v2beta3/projects/$PROJECT_ID/locations/$LOCATION/queues"

Crea una tarea HTTP

Crea una tarea HTTP con la API de BufferTask. Observa que se trata de una simple solicitud HTTP GET sin necesidad de crear una Task:

curl -X GET "$TASKS_QUEUES_API/$QUEUE3/tasks:buffer" \
  -H "Authorization: Bearer $ACCESS_TOKEN"

Crea otra tarea HTTP con HTTP POST y un cuerpo:

curl -X POST "$TASKS_QUEUES_API/$QUEUE3/tasks:buffer" \
  -H "Authorization: Bearer $ACCESS_TOKEN" \
  -d "{'message': 'Hello World'}"

Opcional: También puedes crear una tarea HTTP con bibliotecas cliente. Por ejemplo, puedes consultar la Program.cs para ver una muestra de C# en la que se envía una solicitud HTTP GET directamente a la API de BufferTask sin tener que unirla a una Task ni necesitar la biblioteca cliente para Cloud Tasks:

var BufferTaskApiUrl = $"https://cloudtasks.googleapis.com/v2beta3/projects/{ProjectId}/locations/{Location}/queues/{Queue}/tasks:buffer";

using (var client = new HttpClient())
{
    client.DefaultRequestHeaders.Add("Authorization", $"Bearer {AccessToken}");
    var response = await client.GetAsync(BufferTaskApiUrl);
    var content = await response.Content.ReadAsStringAsync();
    Console.WriteLine($"Response: {content}");
}

Puedes ejecutarlo de la siguiente manera:

dotnet run $PROJECT_ID $LOCATION $QUEUE3 $ACCESS_TOKEN

La API de BufferTask se encarga de crear una tarea a partir de las solicitudes HTTP y agrega la URL de los ajustes de configuración de enrutamiento de la cola para el URI.

Prueba la tarea HTTP

Reanuda la cola:

gcloud tasks queues resume $QUEUE3 --location=$LOCATION

Deberías ver que el servicio de Cloud Run recibió solicitudes HTTP GET y POST de Cloud Tasks:

gcloud logging read "resource.type=cloud_run_revision AND resource.labels.service_name=$SERVICE1" --limit 4
---
httpRequest:
  latency: 0.002279292s
  protocol: HTTP/1.1
  remoteIp: 35.243.23.42
  requestMethod: POST
  requestSize: '777'
  requestUrl: https://hello1-idcwffc3yq-uc.a.run.app/
  responseSize: '5450'
  serverIp: 216.239.32.53
  status: 200
  userAgent: Google-Cloud-Tasks
...
httpRequest:
  latency: 0.228982142s
  protocol: HTTP/1.1
  remoteIp: 35.187.132.84
  requestMethod: GET
  requestSize: '426'
  requestUrl: https://hello1-idcwffc3yq-uc.a.run.app/
  responseSize: '5510'
  serverIp: 216.239.34.53
  status: 200
  userAgent: Google-Cloud-Tasks

10. Felicitaciones

¡Felicitaciones! Completaste el codelab.

A modo de seguimiento, puedes probar Cloud Tasks como búfer entre Pub/Sub y Cloud Run para ver un ejemplo real de cómo estas nuevas funciones de Cloud Tasks pueden ayudar a crear fácilmente una cola de búfer entre servicios.

Realiza una limpieza (opcional)

Para evitar incurrir en cargos, es una buena idea limpiar los recursos.

Si no necesitas el proyecto, simplemente puedes borrarlo:

gcloud projects delete $PROJECT_ID

Si lo necesitas, puedes borrar recursos de forma individual.

Borra los servicios de Cloud Run:

gcloud run services delete $SERVICE1 --region $REGION
gcloud run services delete $SERVICE2 --region $REGION

Borra las colas de Cloud Tasks:

gcloud tasks queues delete $QUEUE1 --location=$LOCATION
gcloud tasks queues delete $QUEUE2 --location=$LOCATION
gcloud tasks queues delete $QUEUE3 --location=$LOCATION

Temas abordados

  • Cómo crear tareas de destino HTTP
  • Cómo crear tareas de destino HTTP con la nueva anulación de URI HTTP a nivel de la cola
  • Cómo cambiar las tareas pendientes con la nueva anulación de URI HTTP a nivel de la cola
  • Cómo almacenar solicitudes HTTP en búfer con mayor facilidad con la nueva API de BufferTask