Gestisci i rischi di scalabilità

Mantieni tutto organizzato con le raccolte Salva e classifica i contenuti in base alle tue preferenze.

L'infrastruttura di Google è progettata per funzionare in modo elastico su larga scala: la maggior parte dei livelli si adatta alle esigenze crescenti del traffico su vasta scala. Un pattern di progettazione principale che rende possibile tutto ciò è un livello adattivo, ovvero componenti di infrastruttura che riallocano dinamicamente il carico in base ai modelli di traffico. Questo adattamento richiede tuttavia tempo. Dato che Cloud Tasks consente di distribuire volumi molto elevati di traffico, espone i rischi di produzione in situazioni in cui il traffico può crescere più velocemente di quanto l'infrastruttura possa adattarsi.

Panoramica

Questo documento fornisce linee guida sulle best practice per mantenere prestazioni elevate di Cloud Tasks nelle code a traffico elevato. Una coda TPS elevata è una coda che contiene 500 attività create o inviate al secondo (TPS) o più. Un gruppo di code con TPS elevato è un insieme contiguo di code, ad esempio [queue0001, queue0002, ..., queue0099], con almeno 2000 attività create o inviate in totale. I TPS storici di una coda o di un gruppo di code sono visualizzabili utilizzando le metriche di Stackdriver, api/request_count per le operazioni "CreateTask" e queue/task_attempt_count per i tentativi delle attività. Le code e i gruppi di code con traffico elevato sono soggetti a due diverse classi ampie di errori:

Il sovraccarico della coda si verifica quando la creazione e l'invio delle attività in una singola coda o gruppo di code aumenta più velocemente di quanto l'infrastruttura della coda sia in grado di adattarsi. Analogamente, il sovraccarico target si verifica quando la frequenza di invio delle attività causa picchi di traffico nell'infrastruttura target a valle. In entrambi i casi, consigliamo di seguire un pattern 500/50/5: quando si scalano oltre i 500 TPS, aumenta il traffico di non più del 50% ogni 5 minuti. Questo documento esamina diversi scenari che possono introdurre rischi di scalabilità e fornisce esempi di come applicare questo pattern.

Sovraccarico della coda

Le code o i gruppi di code possono sovraccaricare ogni volta che il traffico aumenta improvvisamente. Di conseguenza, queste code possono verificarsi:

  • Aumento della latenza di creazione delle attività
  • Aumento della percentuale di errori di creazione delle attività
  • Percentuale di spedizioni ridotta

Per difenderti da questo problema, ti consigliamo di stabilire dei controlli in qualsiasi situazione in cui la frequenza di creazione o invio di una coda o di un gruppo di code possa avere un picco improvviso. Consigliamo di utilizzare un massimo di 500 operazioni al secondo a una coda fredda o a un gruppo di code, per poi aumentare il traffico del 50% ogni 5 minuti. In teoria, puoi aumentare fino a 740.000 operazioni al secondo dopo 90 minuti utilizzando questo programma di adattamento. Questo può accadere in molte circostanze.

Ad esempio:

  • Lancio di nuove funzionalità che fanno un uso intensivo di Cloud Tasks
  • Spostamento del traffico tra le code
  • Ribilanciare il traffico in più o meno code
  • Esecuzione di job batch che inseriscono un numero elevato di attività

In questi casi e in altri, segui lo schema 500/50/5.

Utilizzo della suddivisione del traffico di App Engine

Se le attività vengono create da un'app App Engine, puoi usare la suddivisione del traffico di App Engine (Standard/Flex) per aumentare il traffico senza problemi. Suddividendo il traffico tra le versioni (Standard/Flex), le richieste che devono essere gestite in base alla frequenza possono essere archiviate nel tempo per proteggere l'integrità delle code. Ad esempio, considera l'avvio del traffico verso un gruppo di code appena espanso: [queue0000, queue0199] è una sequenza di code con TPS elevate che ricevono in totale 100.000 creazioni di TPS.

Lascia che [queue0200, queue0399] sia una sequenza di nuove code. Dopo aver spostato tutto il traffico, il numero di code nella sequenza è raddoppiato e il nuovo intervallo di code riceve il 50% del traffico totale della sequenza.

Quando esegui il deployment della versione che aumenta il numero di code, incrementa gradualmente il traffico alla nuova versione, e quindi alle nuove code, utilizzando la suddivisione del traffico:

  • Inizia a spostare l'1% del traffico verso la nuova release. Ad esempio,il 50% dell'1% di 100.000 TPS restituisce 500 TPS all'insieme di nuove code.
  • Ogni 5 minuti, aumenta del 50% il traffico diretto alla nuova release, come descritto nella tabella seguente:
Minuti dall'inizio del deployment % di traffico totale spostato nella nuova versione % di traffico totale verso le nuove code % di traffico totale verso le vecchie code
0 1.0 0,5 99,5
5 1.5 0,75 99,25
10 2,3 1,15 98,85
15 3.4 1,7 98,3
20 5.1 2,55 97,45
25 7,6 3,8 96,2
30 11,4 5,7 94,3
35 17,1 8,55 91,45
40 25,6 12,8 87,2
45 38,4 19,2 80,8
50 57,7 28,85 71,15
55 86,5 43,25 56,75
60 100 50 50

Picchi di traffico basati sulle release

Quando lanci una release che aumenta in modo significativo il traffico in una coda o in un gruppo di code, l'implementazione graduale è ancora una volta un meccanismo importante per uniformare gli aumenti. Distribuisci gradualmente le istanze in modo che il lancio iniziale non superi le 500 operazioni totali alle nuove code, con un aumento di massimo il 50% ogni 5 minuti.

Nuove code o gruppi di code con TPS elevato

Le code appena create sono particolarmente vulnerabili. I gruppi di code, ad esempio [queue0000, queue0001, ..., queue0199], sono sensibili come code singole durante le fasi di implementazione iniziale. Per queste code, l'implementazione graduale è una strategia importante. Lancia servizi nuovi o aggiornati, che creano code o gruppi di code con TPS elevati, in fasi tali da far sì che il carico iniziale sia inferiore a 500 TPS e incrementi del 50% o inferiori vengano rimossi per almeno 5 minuti.

Gruppi di coda appena espansi

Quando aumenti la capacità totale di un gruppo di code, ad esempio espandi [queue0000-queue0199 a queue0000-queue0399], segui il pattern 500/50/5. È importante notare che, per le procedure di implementazione, i nuovi gruppi di code si comportano in modo diverso dalle singole code. Applica il pattern 500/50/5 al nuovo gruppo nel suo complesso, non solo alle singole code all'interno del gruppo. Per queste espansioni di gruppi di code, l'implementazione graduale è ancora una volta una strategia importante. Se la sorgente del traffico è App Engine, puoi utilizzare la suddivisione del traffico (vedi Picchi di traffico basati su release). Quando esegui la migrazione del tuo servizio per aggiungere attività al numero elevato di code, implementa gradualmente le istanze in modo che il lancio iniziale non superi le 500 operazioni totali nelle nuove code, aumentando di oltre il 50% ogni 5 minuti.

Espansione dei gruppi in coda di emergenza

A volte potresti voler espandere un gruppo di code esistente, ad esempio perché è previsto che le attività vengano aggiunte al gruppo di code più velocemente di quanto il gruppo possa inviarle. Se i nomi delle nuove code sono distribuiti in modo uniforme tra i nomi di coda esistenti quando sono ordinati in modo letterale, il traffico può essere inviato immediatamente a tali code purché non siano presenti più del 50% di nuove code interlacciate e il traffico verso ciascuna coda sia inferiore a 500 TPS. Questo metodo è un'alternativa all'uso della suddivisione del traffico e dell'implementazione graduale come descritto nelle sezioni precedenti.

Questo tipo di denominazione con interfoliazione può essere ottenuto aggiungendo un suffisso alle code che terminano con numeri pari. Ad esempio, se hai 200 code esistenti [queue0000-queue0199] e vuoi creare 100 nuove code, scegli [queue0000a, queue0002a, queue0004a, ..., queue0198a] come 02, 0

Se hai bisogno di un ulteriore aumento, puoi comunque interlacciare fino al 50% di code in più ogni 5 minuti.

Un'attività su larga scala/batch accoda

Quando è necessario aggiungere un numero elevato di attività, ad esempio milioni o miliardi, può essere utile un pattern a doppia iniezione. Invece di creare attività da un singolo job, utilizza una coda di inserimento. Ogni attività aggiunta alla coda degli iniettori si sviluppa a ventaglio e aggiunge 100 attività alla coda o al gruppo di code desiderato. La coda dell'iniettore può essere accelerata nel tempo, ad esempio a partire da 5 TPS, per poi aumentare del 50% ogni 5 minuti.

Attività con nome

Quando crei una nuova attività, Cloud Tasks assegna all'attività un nome univoco per impostazione predefinita. Puoi assegnare il tuo nome a un'attività utilizzando il parametro name. Tuttavia, ciò comporta un notevole sovraccarico delle prestazioni, con un conseguente aumento delle latenze e potenzialmente un aumento dei tassi di errore associati alle attività denominate. Questi costi possono essere notevolmente aumentati se le attività sono denominate in sequenza, come ad esempio con i timestamp. Quindi, se assegni i tuoi nomi, ti consigliamo di utilizzare un prefisso ben distribuito per i nomi delle attività, ad esempio un hash dei contenuti. Consulta la documentazione per ulteriori dettagli sulla denominazione di un'attività.

Sovraccarico target

Cloud Tasks può sovraccaricare altri servizi in uso, come App Engine, Datastore e la tua rete, se le invii da una coda aumentano drasticamente in un breve periodo di tempo. Se è stato accumulato un backlog di attività, la riattivazione di queste code potrebbe comportare un sovraccarico dei servizi. La difesa consigliata è lo stesso schema 500/50/5 suggerito per il sovraccarico della coda: se una coda invia più di 500 TPS, il traffico attivato da una coda non deve superare il 50% ogni 5 minuti. Utilizza Stackdriver Metrics per monitorare in modo proattivo gli aumenti del traffico. Gli avvisi di Stackdriver possono essere utilizzati per rilevare situazioni potenzialmente pericolose.

Riattivare o ripristinare code con TPS elevati

Quando una coda o una serie di code viene riattivata o riattivata, le code continuano a essere inviate. Se la coda contiene molte attività, la frequenza di invio della coda appena abilitata potrebbe aumentare notevolmente da 0 TPS all'intera capacità della coda. Per aumentare la velocità, la coda scaglionata riprende o controlla le frequenze di invio delle code utilizzando Cloud Tasks&39;s maxDispatchesPerSecond.

Attività programmate collettivamente

Un numero elevato di attività, di cui è prevista l'invio simultaneo, può anche comportare un rischio di sovraccarico target. Se devi avviare un numero elevato di attività in una sola volta, valuta la possibilità di utilizzare i controlli della coda di coda per aumentare la frequenza di invio gradualmente o aumentare esplicitamente la capacità target in anticipo.

Ha aumentato il fan-out

Quando aggiorni i servizi eseguiti tramite Cloud Tasks, l'aumento del numero di chiamate remote può creare rischi di produzione. Ad esempio, supponiamo che le attività in una coda con TPS elevati chiamino il gestore /task-foo. Una nuova release potrebbe aumentare in modo significativo il costo delle chiamate /task-foo se, ad esempio, la nuova release aggiunge al gestore diverse chiamate Datastore costose. Il risultato netto di questa release sarebbe un aumento enorme del traffico di Datastore immediatamente correlato alle modifiche al traffico degli utenti. Utilizza l'implementazione graduale o la suddivisione del traffico per gestire il processo di applicazione graduale.

Nuovi tentativi

Il codice potrebbe riprovare in caso di errore durante le chiamate API Cloud Tasks. Tuttavia, quando una parte significativa delle richieste non riesce a rilevare errori lato server, un numero elevato di nuovi tentativi può sovraccaricare ulteriormente le code e causare un recupero più lento. Ti consigliamo quindi di limitare il volume del traffico in uscita se il tuo client rileva che una parte significativa delle richieste non riesce con errori lato server, ad esempio utilizzando l'algoritmo di limitazione adattiva descritto nel capitolo Gestione del sovraccarico del libro di Site Reliablity Engineering. Le librerie client gRPC di Google implementano una variazione di questo algoritmo.