Wiederholungsstrategie

Auf dieser Seite werden Wiederholungsstrategien wie abgeschnittener exponentieller Backoff für fehlgeschlagene Anfragen an Cloud Storage beschrieben. Die meisten Cloud Storage-Tools bieten automatische Wiederholungsversuche, sodass Sie keine eigene Wiederholungsstrategie implementieren müssen.

Wie Cloud Storage-Tools Wiederholungsstrategien implementieren

Console

Die Google Cloud Console sendet in Ihrem Namen Anfragen an Cloud Storage und sorgt für die Bearbeitung aller erforderlichen Backoffs.

gsutil

gsutil wiederholt die im Abschnitt Antwort aufgeführten Fehler, ohne dass Sie etwas zusätzlich unternehmen müssen. Bei anderen Fehlern müssen Sie unter Umständen z. B. folgende Maßnahmen ergreifen:

  • Ungültige Anmeldedaten oder unzureichende Berechtigungen.

  • Das Netzwerk ist nicht erreichbar, da Probleme mit der Proxykonfiguration aufgetreten sind.

  • Einzelne Vorgänge, die in einem Befehl fehlschlagen, wenn das Top-Level-Flag -m verwendet wird.

Bei wiederholbaren Fehlern wiederholt gsutil Anfragen nach der Strategie eines abgeschnittenen binären exponentiellen Backoffs: Standardmäßig führt gsutil Wiederholungsversuche 23 Mal im Verlauf von 1+2+4+8+16+32+60… Sekunden durch, was ungefähr 10 Minuten entspricht.

  • Wenn eine Anfrage fehlschlägt, warten Sie einen zufälligen Zeitraum zwischen [0....1] Sekunden und wiederholen Sie den Vorgang.
  • Wenn die Anfrage noch einmal fehlschlägt, warten Sie einen zufälligen Zeitraum zwischen [0...2] Sekunden und versuchen Sie es noch einmal.
  • Wenn die Anfrage noch einmal fehlschlägt, warten Sie einen zufälligen Zeitraum zwischen [0...4] Sekunden und wiederholen Sie den Vorgang.
  • Und so weiter, bis zu 23 Wiederholungen, wobei jeder Wiederholungszeitraum durch einen Standardmaximalwert von 60 Sekunden begrenzt ist.

Bearbeiten Sie die Konfigurationsvariablen num_retries und max_retry_delay im Abschnitt "[Boto]" der .boto-Konfigurationsdatei, um die Anzahl der Wiederholungsversuche und die maximale Verzögerung jeder einzelnen Wiederholung zu konfigurieren.

Clientbibliotheken

C++

Standardverhalten bei Wiederholungsversuchen

Standardmäßig unterstützen die Vorgänge Wiederholungsversuche für die folgenden HTTP-Fehlercodes sowie für alle Socket-Fehler, die darauf hinweisen, dass die Verbindung verloren gegangen ist oder nie erfolgreich hergestellt wurde.

  • 408 Request Timeout
  • 429 Too Many Requests
  • 500 Internal Server Error
  • 502 Bad Gateway
  • 503 Service Unavailable
  • 504 Gateway Timeout

Alle Einstellungen für exponentielle Backoffs und Wiederholungsversuche in der C++-Bibliothek sind konfigurierbar. Wenn die in der Bibliothek implementierten Algorithmen Ihre Anforderungen nicht unterstützen, können Sie benutzerdefinierten Code bereitstellen, um Ihre eigenen Strategien zu implementieren.

Einstellung Standardwert
Automatische Wiederholung Wahr
Maximale Dauer, die eine Anfrage wiederholt wird 15 Minuten
Erste Wartezeit (Backoff) 1 Sekunde
Multiplikator für die Wartezeit pro Ausführung 2
Maximale Wartezeit 5 Minuten

Standardmäßig wiederholt die C++-Bibliothek alle Operationen mit wiederholbaren Fehlern, auch solche, die nie idempotent sind und bei erfolgreicher Wiederholung mehrere Ressourcen löschen oder erstellen können. Wenn Sie nur idempotente Vorgänge wiederholen möchten, verwenden Sie google::cloud::storage::StrictIdempotencyPolicy.

Wiederholungsversuche anpassen

Zum Anpassen des Wiederholungsverhaltens geben Sie Werte für die folgenden Optionen an, wenn Sie das Objekt google::cloud::storage::Client initialisieren:

  • google::cloud::storage::RetryPolicyOption: Die Bibliothek bietet die Klassen google::cloud::storage::LimitedErrorCountRetryPolicy und google::cloud::storage::LimitedTimeRetryPolicy. Sie können Ihre eigene Klasse angeben, die die Schnittstelle google::cloud::RetryPolicy implementieren muss.

  • google::cloud::storage::BackoffPolicyOption: Die Bibliothek bietet die Klasse google::cloud::storage::ExponentialBackoffPolicy. Sie können Ihre eigene Klasse angeben, die die Schnittstelle google::cloud::storage::BackoffPolicy implementieren muss.

  • google::cloud::storage::IdempotencyPolicyOption: Die Bibliothek stellt die Klassen google::cloud::storage::StrictIdempotencyPolicy und google::cloud::storage::AlwaysRetryIdempotencyPolicy bereit. Sie können Ihre eigene Klasse angeben, die die Schnittstelle google::cloud::storage::IdempotencyPolicy implementieren muss.

namespace gcs = ::google::cloud::storage;
// Create the client configuration:
auto options = google::cloud::Options{};
// Retries only idempotent operations.
options.set<gcs::IdempotencyPolicyOption>(
    gcs::StrictIdempotencyPolicy().clone());
// On error, it backs off for 1 second, then 3 seconds, then 9 seconds, etc.
// The backoff time never grows larger than 1 minute. The strategy introduces
// jitter around the backoff delay.
options.set<gcs::BackoffPolicyOption>(
    gcs::ExponentialBackoffPolicy(
        /*initial_delay=*/std::chrono::seconds(1),
        /*maximum_delay=*/std::chrono::minutes(1),
        /*scaling=*/3.0)
        .clone());
// Retries all operations for up to 5 minutes, including any backoff time.
options.set<gcs::RetryPolicyOption>(
    gcs::LimitedTimeRetryPolicy(std::chrono::minutes(5)).clone());
return gcs::Client(std::move(options));

C#

In der C#-Clientbibliothek wird exponentieller Backoff standardmäßig verwendet.

Go

Standardverhalten bei Wiederholungsversuchen

Standardmäßig unterstützen Vorgänge Wiederholungsversuche für die folgenden Fehler:

  • Verbindungsfehler:
    • io.ErrUnexpectedEOF: Dies kann aufgrund vorübergehender Netzwerkprobleme auftreten.
    • url.Error mit connection refused: Dies kann aufgrund vorübergehender Netzwerkprobleme auftreten.
    • url.Error mit connection reset by peer: Dies bedeutet, dass die GCP die Verbindung zurückgesetzt hat.
    • net.ErrClosed: Dies bedeutet, dass die GCP die Verbindung geschlossen hat.
  • HTTP-Codes:
    • 408 Request Timeout
    • 429 Too Many Requests
    • 500 Internal Server Error
    • 502 Bad Gateway
    • 503 Service Unavailable
    • 504 Gateway Timeout
  • Fehler, die die Schnittstelle Temporary() implementieren und den Wert err.Temporary() == true angeben
  • Alle oben genannten Fehler, die mit Go 1.13-Fehlerverpackung verpackt wurden

Alle Einstellungen für exponentielle Backoffs in der Go-Bibliothek können konfiguriert werden. Standardmäßig verwenden Vorgänge in Go die folgenden Einstellungen für den exponentiellen Backoff (Standardeinstellungen werden von gax übernommen):

Einstellung Standardwert (in Sekunden)
Automatische Wiederholung Wahr, wenn idempotent
Maximale Anzahl an Versuchen Kein Limit
Verzögerung für erste Wiederholung: 1 Sekunde
Multiplikator für die Verzögerung der Wiederholung 2.0
Maximale Wiederholungsverzögerung 30 Sekunden
Gesamtzeitüberschreitung (fortsetzbarer Uploadblock) 32 Sekunden
Gesamtzeitüberschreitung (alle anderen Vorgänge) Kein Limit

Der Wiederholungsversuch wird in der Regel unbegrenzt fortgesetzt, es sei denn, der Steuerungskontext wird abgebrochen, der Client wird geschlossen oder ein nicht vorübergehender Fehler wird empfangen. Verwenden Sie Kontextzeitüberschreitungen oder einen Abbruch, um zu verhindern, dass Wiederholungsversuche fortgesetzt werden. Die einzige Ausnahme bei diesem Verhalten ist, wenn fortsetzbare Uploads mit Writer durchgeführt werden, wobei die Daten groß genug sind, dass mehrere Anfragen erforderlich sind. In diesem Szenario tritt bei jedem Block eine Zeitüberschreitung auf und beendet die Wiederholung standardmäßig nach 32 Sekunden. Sie können das Standardzeitlimit anpassen, indem Sie Writer.ChunkRetryDeadline ändern.

Es gibt eine Teilmenge von Go-Vorgängen, die bedingt idempotent sind (bedingt sicher bei erneuter Wiederholung). Diese Vorgänge werden nur dann wiederholt, wenn sie bestimmte Bedingungen erfüllen:

  • GenerationMatch oder Generation

    • Wiederholen Sie den Vorgang, wenn die Vorbedingung GenerationMatch auf den Aufruf angewendet wurde oder wenn ObjectHandle.Generation festgelegt wurde.
  • MetagenerationMatch

    • Wiederholen Sie den Vorgang, wenn die Vorbedingung MetagenerationMatch auf den Aufruf angewendet wurde.
  • Etag

    • Es kann wiederholt werden, wenn die Methode etag in den JSON-Anfragetext einfügt. Wird nur in HMACKeyHandle.Update verwendet, wenn HmacKeyMetadata.Etag festgelegt wurde.

RetryPolicy ist standardmäßig auf RetryPolicy.RetryIdempotent festgelegt. Im Abschnitt Wiederholungen anpassen weiter unten finden Sie Beispiele zum Ändern des Standardverhaltens bei Wiederholungsversuchen.

Wiederholungsversuche anpassen

Wenn Sie einen Storage-Client initialisieren, wird eine Standardkonfiguration für Wiederholungsversuche festgelegt. Sofern sie nicht überschrieben werden, werden die Optionen in der Konfiguration auf die Werte in der obigen Tabelle festgelegt. Nutzer können ein nicht standardmäßiges Wiederholungsverhalten für einen einzelnen Bibliotheksaufruf (mit BucketHandle.Retryer und ObjectHandle.Retryer) oder für alle Aufrufe konfigurieren, die von einem Client (mit Client.SetRetry) gemacht werden. Um das Wiederholungsverhalten zu ändern, übergeben Sie die gewünschten RetryOptions an eine dieser Methoden.

Im folgenden Codebeispiel erfahren Sie, wie Sie das Wiederholungsverhalten anpassen.

import (
	"context"
	"fmt"
	"io"
	"time"

	"cloud.google.com/go/storage"
	"github.com/googleapis/gax-go/v2"
)

// configureRetries configures a custom retry strategy for a single API call.
func configureRetries(w io.Writer, bucket, object string) error {
	// bucket := "bucket-name"
	// object := "object-name"
	ctx := context.Background()
	client, err := storage.NewClient(ctx)
	if err != nil {
		return fmt.Errorf("storage.NewClient: %v", err)
	}
	defer client.Close()

	// Configure retries for all operations using this ObjectHandle. Retries may
	// also be configured on the BucketHandle or Client types.
	o := client.Bucket(bucket).Object(object).Retryer(
		// Use WithBackoff to control the timing of the exponential backoff.
		storage.WithBackoff(gax.Backoff{
			// Set the initial retry delay to a maximum of 2 seconds. The length of
			// pauses between retries is subject to random jitter.
			Initial: 2 * time.Second,
			// Set the maximum retry delay to 60 seconds.
			Max: 60 * time.Second,
			// Set the backoff multiplier to 3.0.
			Multiplier: 3,
		}),
		// Use WithPolicy to customize retry so that all requests are retried even
		// if they are non-idempotent.
		storage.WithPolicy(storage.RetryAlways),
	)

	// Use context timeouts to set an overall deadline on the call, including all
	// potential retries.
	ctx, cancel := context.WithTimeout(ctx, 500*time.Second)
	defer cancel()

	// Delete an object using the specified retry policy.
	if err := o.Delete(ctx); err != nil {
		return fmt.Errorf("Object(%q).Delete: %v", object, err)
	}
	fmt.Fprintf(w, "Blob %v deleted with a customized retry strategy.\n", object)
	return nil
}

Java

Standardverhalten bei Wiederholungsversuchen

Standardmäßig unterstützen Vorgänge Wiederholungsversuche für die folgenden Fehler:

  • Verbindungsfehler:
    • Connection reset by peer: Dies bedeutet, dass die GCP die Verbindung zurückgesetzt hat.
    • Unexpected connection closure: Dies bedeutet, dass die GCP die Verbindung geschlossen hat.
  • HTTP-Codes:
    • 408 Request Timeout
    • 429 Too Many Requests
    • 500 Internal Server Error
    • 502 Bad Gateway
    • 503 Service Unavailable
    • 504 Gateway Timeout

Alle Einstellungen für exponentielle Backoffs in der Java-Bibliothek können konfiguriert werden. Standardmäßig verwenden Vorgänge über Java für den exponentiellen Backoff die folgenden Einstellungen:

Einstellung Standardwert (in Sekunden)
Automatische Wiederholung Wahr, wenn idempotent
Maximale Anzahl an Versuchen 6
Verzögerung für erste Wiederholung: 1 Sekunde
Multiplikator für die Verzögerung der Wiederholung 2.0
Maximale Wiederholungsverzögerung 32 Sekunden
Zeitüberschreitung insgesamt 50 Sekunden
Anfängliche RPC-Zeitüberschreitung 50 Sekunden
RPC-Zeitüberschreitungsmultiplikator 1,0
Maximales RPC-Zeitlimit 50 Sekunden
Zeitüberschreitung beim Verbindungsaufbau 20 Sekunden
Lesezeitüberschreitung 20 Sekunden

Weitere Informationen zu den oben genannten Parametern finden Sie in der Java-Referenzdokumentation für RetrySettings.Builder und HttpTransportOptions.Builder.

Es gibt eine Teilmenge von Java-Vorgängen, die bedingt idempotent sind (bedingt sicher bei erneutem Versuch). Diese Vorgänge werden nur dann wiederholt, wenn sie bestimmte Argumente enthalten:

  • ifGenerationMatch oder generation

    • Sicher für Wiederholung, wenn ifGenerationMatch oder generation als Option an die Methode übergeben wurde.
  • ifMetagenerationMatch

    • Wiederholen Sie den Vorgang, wenn ifMetagenerationMatch als Option übergeben wurde.

StorageOptions.setStorageRetryStrategy ist standardmäßig auf StorageRetryStrategy#getDefaultStorageRetryStrategy festgelegt. Im Abschnitt Wiederholungen anpassen weiter unten finden Sie Beispiele zum Ändern des Standardverhaltens bei Wiederholungsversuchen.

Wiederholungsversuche anpassen

Beim Initialisieren von Storage wird auch eine Instanz von RetrySettings initialisiert. Wenn die Optionen nicht überschrieben werden, werden sie in RetrySettings auf die Werte in der obigen Tabelle gesetzt. Um das Standardverhalten für die automatische Wiederholung zu ändern, übergeben Sie die benutzerdefinierte StorageRetryStrategy an die StorageOptions, die zum Erstellen der Storage-Instanz verwendet werden. Um einen der anderen skalaren Parameter zu ändern, übergeben Sie benutzerdefinierte RetrySettings an die StorageOptions, die zum Erstellen der Storage-Instanz verwendet werden.

Im folgenden Beispiel erfahren Sie, wie Sie das Wiederholungsverhalten anpassen:


import com.google.api.gax.retrying.RetrySettings;
import com.google.cloud.storage.BlobId;
import com.google.cloud.storage.Storage;
import com.google.cloud.storage.StorageOptions;
import com.google.cloud.storage.StorageRetryStrategy;
import org.threeten.bp.Duration;

public final class ConfigureRetries {
  public static void main(String[] args) {
    String bucketName = "my-bucket";
    String blobName = "blob/to/delete";
    deleteBlob(bucketName, blobName);
  }

  static void deleteBlob(String bucketName, String blobName) {
    // Customize retry behavior
    RetrySettings retrySettings =
        StorageOptions.getDefaultRetrySettings()
            .toBuilder()
            // Set the max number of attempts to 10 (initial attempt plus 9 retries)
            .setMaxAttempts(10)
            // Set the backoff multiplier to 3.0
            .setRetryDelayMultiplier(3.0)
            // Set the max duration of all attempts to 5 minutes
            .setTotalTimeout(Duration.ofMinutes(5))
            .build();

    StorageOptions alwaysRetryStorageOptions =
        StorageOptions.newBuilder()
            // Customize retry so all requests are retried even if they are non-idempotent.
            .setStorageRetryStrategy(StorageRetryStrategy.getUniformStorageRetryStrategy())
            // provide the previously configured retrySettings
            .setRetrySettings(retrySettings)
            .build();

    // Instantiate a client
    Storage storage = alwaysRetryStorageOptions.getService();

    // Delete the blob
    BlobId blobId = BlobId.of(bucketName, blobName);
    boolean success = storage.delete(blobId);

    System.out.printf(
        "Deletion of Blob %s completed %s.%n", blobId, success ? "successfully" : "unsuccessfully");
  }
}

Node.js

Standardverhalten bei Wiederholungsversuchen

Standardmäßig unterstützen Vorgänge Wiederholungsversuche für die folgenden Fehlercodes:

  • Verbindungsfehler:
    • EAI_again: Dies ist ein DNS-Lookup-Fehler. Weitere Informationen finden Sie hier.
    • Connection reset by peer: Dies bedeutet, dass die GCP die Verbindung zurückgesetzt hat.
    • Unexpected connection closure: Dies bedeutet, dass die GCP die Verbindung geschlossen hat.
  • HTTP-Codes:
    • 408 Request Timeout
    • 429 Too Many Requests
    • 500 Internal Server Error
    • 502 Bad Gateway
    • 503 Service Unavailable
    • 504 Gateway Timeout

Alle Einstellungen für exponentielle Backoffs in der Node.js-Bibliothek können konfiguriert werden. Standardmäßig verwenden Vorgänge über Node.js die folgenden Einstellungen für den exponentiellen Backoff:

Einstellung Standardwert (in Sekunden)
Automatische Wiederholung Wahr, wenn idempotent
Maximale Anzahl an Wiederholungen 3
Anfängliche Wartezeit 1 Sekunde
Multiplikator für die Wartezeit pro Ausführung 2
Maximale Wartezeit 64 Sekunden
Standardfrist 600 Sekunden

Es gibt eine Teilmenge von Node.js-Vorgängen, die bedingt idempotent sind und unter bestimmten Bedingungen wiederholt werden können. Diese Vorgänge werden nur dann wiederholt, wenn sie bestimmte Argumente enthalten:

  • ifGenerationMatch oder generation

    • Sicher für Wiederholung, wenn ifGenerationMatch oder generation als Option an die Methode übergeben wurde. Häufig akzeptieren Methoden nur einen dieser beiden Parameter.
  • ifMetagenerationMatch

    • Wiederholen Sie den Vorgang, wenn ifMetagenerationMatch als Option übergeben wurde.

retryOptions.idempotencyStrategy ist standardmäßig auf IdempotencyStrategy.RetryConditional festgelegt. Im Abschnitt Wiederholungen anpassen weiter unten finden Sie Beispiele zum Ändern des Standardverhaltens bei Wiederholungsversuchen.

Wiederholungsversuche anpassen

Beim Initialisieren von Cloud Storage wird auch eine retryOptions-Konfigurationsdatei initialisiert. Sofern sie nicht überschrieben werden, werden die Optionen in der Konfiguration auf die Werte in der obigen Tabelle festgelegt. Um das Standardverhalten für Wiederholungsversuche zu ändern, übergeben Sie bei der Initialisierung die benutzerdefinierte Wiederholungskonfiguration retryOptions an den Speicherkonstruktor. Die Node.js-Clientbibliothek kann automatisch Backoff-Strategien verwenden, um Anfragen mit dem Parameter autoRetry noch einmal zu senden.

Im folgenden Codebeispiel erfahren Sie, wie Sie das Wiederholungsverhalten anpassen.

/**
 * TODO(developer): Uncomment the following lines before running the sample.
 */
// The ID of your GCS bucket
// const bucketName = 'your-unique-bucket-name';

// The ID of your GCS file
// const fileName = 'your-file-name';

// Imports the Google Cloud client library
const {Storage} = require('@google-cloud/storage');

// Creates a client
const storage = new Storage({
  retryOptions: {
    // If this is false, requests will not retry and the parameters
    // below will not affect retry behavior.
    autoRetry: true,
    // The multiplier by which to increase the delay time between the
    // completion of failed requests, and the initiation of the subsequent
    // retrying request.
    retryDelayMultiplier: 3,
    // The total time between an initial request getting sent and its timeout.
    // After timeout, an error will be returned regardless of any retry attempts
    // made during this time period.
    totalTimeout: 500,
    // The maximum delay time between requests. When this value is reached,
    // retryDelayMultiplier will no longer be used to increase delay time.
    maxRetryDelay: 60,
    // The maximum number of automatic retries attempted before returning
    // the error.
    maxRetries: 5,
    // Will respect other retry settings and attempt to always retry
    // conditionally idempotent operations, regardless of precondition
    idempotencyStrategy: IdempotencyStrategy.RetryAlways,
  },
});
console.log(
  'Functions are customized to be retried according to the following parameters:'
);
console.log(`Auto Retry: ${storage.retryOptions.autoRetry}`);
console.log(
  `Retry delay multiplier: ${storage.retryOptions.retryDelayMultiplier}`
);
console.log(`Total timeout: ${storage.retryOptions.totalTimeout}`);
console.log(`Maximum retry delay: ${storage.retryOptions.maxRetryDelay}`);
console.log(`Maximum retries: ${storage.retryOptions.maxRetries}`);
console.log(
  `Idempotency strategy: ${storage.retryOptions.idempotencyStrategy}`
);

async function deleteFileWithCustomizedRetrySetting() {
  await storage.bucket(bucketName).file(fileName).delete();
  console.log(`File ${fileName} deleted with a customized retry strategy.`);
}

deleteFileWithCustomizedRetrySetting();

PHP

In der PHP-Clientbibliothek wird exponentieller Backoff standardmäßig verwendet.

Python

Standardverhalten bei Wiederholungsversuchen

Standardmäßig unterstützen Vorgänge Wiederholungsversuche für die folgenden Fehlercodes:

  • Verbindungsfehler:
    • requests.exceptions.ConnectionError
    • requests.exceptions.ChunkedEncodingError (nur für Vorgänge, die Nutzlastdaten abrufen oder an Objekte senden, z. B. Uploads und Downloads)
    • ConnectionError
  • HTTP-Codes:
    • 408 Request Timeout
    • 429 Too Many Requests
    • 500 Internal Server Error
    • 502 Bad Gateway
    • 503 Service Unavailable
    • 504 Gateway Timeout

Für Vorgänge über Python werden die folgenden Standardeinstellungen für exponentielle Backoffs verwendet:

Einstellung Standardwert (in Sekunden)
Automatische Wiederholung Wahr, wenn idempotent
Anfängliche Wartezeit 1
Multiplikator für die Wartezeit pro Ausführung 2
Maximale Wartezeit 60
Standardfrist 120

Es gibt eine Teilmenge von Python-Vorgängen, die bedingt idempotent sind und unter bestimmten Bedingungen wiederholt werden können, wenn sie bestimmte Argumente enthalten. Diese Vorgänge werden nur dann wiederholt, wenn ein Bedingungsfall erfolgreich ist:

  • DEFAULT_RETRY_IF_GENERATION_SPECIFIED

    • Sicher für Wiederholung, wenn generation oder if_generation_match als Argument an die Methode übergeben wurde. Häufig akzeptieren Methoden nur einen dieser beiden Parameter.
  • DEFAULT_RETRY_IF_METAGENERATION_SPECIFIED

    • Sicher für Wiederholung, wenn if_metageneration_match als Argument an die Methode übergeben wurde.
  • DEFAULT_RETRY_IF_ETAG_IN_JSON

    • Es kann wiederholt werden, wenn die Methode etag in den JSON-Anfragetext einfügt. Für HMACKeyMetadata.update() bedeutet dies, dass das ETag für das HMACKeyMetadata-Objekt selbst festgelegt werden muss. Für die set_iam_policy()-Methode in anderen Klassen bedeutet dies, dass das ETag im Argument "policy" festgelegt werden muss, das an die Methode übergeben wird.

Wiederholungsversuche anpassen

Zum Ändern des Standardverhaltens für Wiederholungsversuche erstellen Sie eine Kopie des google.cloud.storage.retry.DEFAULT_RETRY-Objekts. Dazu rufen Sie es mit der Methode with_XXX auf. Die Python-Clientbibliothek verwendet automatisch Backoff-Strategien, um Anfragen zu wiederholen, wenn Sie den Parameter DEFAULT_RETRY einfügen.

Beachten Sie, dass with_predicate nicht für Vorgänge unterstützt wird, die Nutzlastdaten abrufen oder senden, z. B. Uploads und Downloads. Es wird empfohlen, Attribute einzeln zu ändern. Weitere Informationen finden Sie in der google-api-core Retry-Referenz.

Zum Konfigurieren Ihrer eigenen bedingten Wiederholungsversuche erstellen Sie ein ConditionalRetryPolicy-Objekt und verpacken das benutzerdefinierte Retry-Objekt mit DEFAULT_RETRY_IF_GENERATION_SPECIFIED, DEFAULT_RETRY_IF_METAGENERATION_SPECIFIED oder DEFAULT_RETRY_IF_ETAG_IN_JSON.

Im folgenden Codebeispiel erfahren Sie, wie Sie das Wiederholungsverhalten anpassen.

from google.cloud import storage
from google.cloud.storage.retry import DEFAULT_RETRY

def configure_retries(bucket_name, blob_name):
    """Configures retries with customizations."""
    # The ID of your GCS bucket
    # bucket_name = "your-bucket-name"
    # The ID of your GCS object
    # blob_name = "your-object-name"

    storage_client = storage.Client()
    bucket = storage_client.bucket(bucket_name)
    blob = bucket.blob(blob_name)

    # Customize retry with a deadline of 500 seconds (default=120 seconds).
    modified_retry = DEFAULT_RETRY.with_deadline(500.0)
    # Customize retry with an initial wait time of 1.5 (default=1.0).
    # Customize retry with a wait time multiplier per iteration of 1.2 (default=2.0).
    # Customize retry with a maximum wait time of 45.0 (default=60.0).
    modified_retry = modified_retry.with_delay(initial=1.5, multiplier=1.2, maximum=45.0)

    # blob.delete() uses DEFAULT_RETRY_IF_GENERATION_SPECIFIED by default.
    # Override with modified_retry so the function retries even if the generation
    # number is not specified.
    print(
        f"The following library method is customized to be retried according to the following configurations: {modified_retry}"
    )

    blob.delete(retry=modified_retry)
    print(f"Blob {blob_name} deleted with a customized retry strategy.")

Ruby

In der Ruby-Clientbibliothek wird exponentieller Backoff standardmäßig verwendet.

REST APIs

Wenn Sie die JSON- oder XML API direkt aufrufen, sollten Sie mit dem exponentiellen Backoff Ihre eigene Wiederholungsstrategie implementieren.

Eigene Wiederholungsstrategie implementieren

In diesem Abschnitt wird beschrieben, wie Sie Ihre eigene Wiederholungsstrategie implementieren können. Außerdem finden Sie hier Anleitungen zur Verwendung des exponentiellen Backoff-Algorithmus.

Es gibt zwei Faktoren, die bestimmen, ob eine Anfrage wiederholt werden kann:

  1. Die Antwort, die Sie von der Anfrage erhalten.
  2. Die Idempotenz der Anfrage.

Antwort

Die Antwort, die Sie von Ihrer Anfrage erhalten, gibt an, ob es sinnvoll ist, die Anfrage zu wiederholen. Antworten auf vorübergehende Probleme sind in der Regel wiederholbar. Andererseits zeigen Antworten auf permanente Fehler, dass Sie Änderungen wie Autorisierungs- oder Konfigurationsänderungen vornehmen müssen, bevor es sinnvoll ist, die Anfrage noch einmal zu senden. Die folgenden Antworten weisen auf vorübergehende Probleme hin, die wiederholt werden können:

  • HTTP-Antwortcodes 408, 429 und 5xx.
  • Socket-Zeitüberschreitungen und getrennte TCP-Verbindungen

Weitere Informationen finden Sie in den Status- und Fehlercodes für JSON und XML-Code.

Idempotenz

Eine idempotente Anfrage bedeutet, dass sie wiederholt ausgeführt werden kann und die ausgewählte Ressource immer im selben Endzustand belässt. Zum Beispiel sind Auflistungsanfragen immer idempotent, weil solche Anfragen keine Ressourcen ändern. Andererseits ist das Erstellen einer neuen Pub/Sub-Benachrichtigung niemals idempotent, da bei jeder erfolgreichen Anfrage eine neue Benachrichtigungs-ID erstellt wird.

Die folgenden Beispiele zeigen Bedingungen, die einen Vorgang idempotent machen:

  • Der Vorgang hat auch dann sichtbare Auswirkungen auf die Zielressource, wenn er kontinuierlich angefragt wird.

  • Der Vorgang ist nur einmal erfolgreich.

  • Der Vorgang hat keine sichtbaren Auswirkungen auf den Status der Zielressource.

Wenn Sie eine wiederholbare Antwort erhalten, sollten Sie die Idempotenz der Anfrage berücksichtigen, da Wiederholungsanfragen, die nicht idempotent sind, zu Race-Bedingungen und anderen Konflikten führen können.

Bedingte Idempotenz

Teilmengen von Anfragen sind bedingt idempotent. Das bedeutet, dass sie nur idempotent sind, wenn sie bestimmte optionale Argumente enthalten. Vorgänge, für die ein bedingter Versuch wiederholt werden muss, sollten nur dann wiederholt werden, wenn der Bedingungsfall erfolgreich ist. Cloud Storage akzeptiert Vorbedingungen und ETags als Bedingungsfälle für Anfragen.

Idempotenz von Vorgängen

In der folgenden Tabelle sind die Cloud Storage-Vorgänge aufgeführt, die unter die einzelnen Kategorien der Idempotenz fallen.

Idempotenz Vorgänge
Immer idempotent
  • Alle get- und list-Anfragen
  • Buckets einfügen oder löschen
  • IAM-Richtlinien und -Berechtigungen für Test-Buckets
  • Aufbewahrungsrichtlinien sperren
  • HMAC-Schlüssel oder Pub/Sub-Benachrichtigungen löschen
Bedingt idempotent
  • Update-/Patch-Anfragen für Buckets mit IfMetagenerationMatch oder ETag als HTTP-Vorbedingung
  • Aktualisierungs-/Patchanfragen für Objekte mit IfMetagenerationMatch oder ETag als HTTP-Vorbedingung
  • Bucket-IAM-Richtlinie mit ETag als HTTP-Vorbedingung oder im Ressourcentext festlegen
  • HMAC-Schlüssel mit ETag als HTTP-Vorbedingung oder im Ressourcentext aktualisieren
  • Mit ifGenerationMatch Objekte einfügen, kopieren, verfassen oder neu schreiben
  • Objekt mit ifGenerationMatch löschen (oder mit einer Generierungsnummer für Objektversionen)
Nie idempotent
  • HMAC-Schlüssel erstellen
  • Pub/Sub-Benachrichtigung erstellen
  • Patch-/Updateanfragen für Bucket- und Objekt-ACLs oder Standard-Objekt-ACLs erstellen, löschen oder senden

Exponentieller Backoff-Algorithmus

Für Anfragen, die sowohl die Antwort- als auch die Idempotenzkriterien erfüllen, sollten Sie im Allgemeinen den abgeschnittenen exponentiellen Backoff verwenden.

Ein abgeschnittener exponentieller Backoff ist eine Standardstrategie zur Fehlerbehebung für Netzwerkanwendungen, bei der ein Client eine fehlgeschlagene Anfrage regelmäßig noch einmal sendet, wobei die Abstände zwischen den Anfragen immer länger werden.

Ein exponentieller Backoff-Algorithmus wiederholt Anfragen exponentiell und verlängert dabei die Wartezeit zwischen zwei Wiederholungen bis zur maximalen Backoff-Zeit. Das folgende Workflow-Beispiel zeigt, wie der exponentielle Backoff funktioniert:

  1. Sie stellen eine Anfrage an Cloud Storage.

  2. Wenn die Anfrage fehlschlägt, wartet das System 1 + random_number_milliseconds Sekunden und wiederholt dann die Anfrage.

  3. Wenn die Anfrage fehlschlägt, wartet das System 2 + random_number_milliseconds Sekunden und wiederholt dann die Anfrage.

  4. Wenn die Anfrage fehlschlägt, wartet das System 4 + random_number_milliseconds Sekunden und wiederholt dann die Anfrage.

  5. Und so weiter bis zur maximum_backoff-Zeit.

  6. Setzen Sie die Wartezeit fort und wiederholen Sie den Vorgang bis zu einer maximalen Frist (deadline). Erhöhen Sie jedoch nicht die Wartezeit von maximum_backoff zwischen Wiederholungsversuchen.

wobei

  • Die Wartezeit beträgt min((2n +random_number_milliseconds), maximum_backoff), wobei n bei jeder Ausführung (Anfrage) um 1 erhöht wird.

  • random_number_milliseconds steht für eine zufällige Anzahl von Millisekunden, deren Wert größer oder gleich 1.000 ist. So lassen sich Situationen vermeiden, in denen viele Clients synchronisiert werden und alle gleichzeitig Anfragen wiederholen und diese in synchronisierten Wellen senden. Der Wert von random_number_milliseconds wird nach jeder Anfragewiederholung neu berechnet.

  • maximum_backoff ist normalerweise 32 oder 64 Sekunden lang. Der geeignete Wert hängt vom jeweiligen Anwendungsfall ab.

Sie können den Vorgang nach Ablauf der maximum_backoff-Zeit fortsetzen. Es wird jedoch empfohlen, die Anfrage nach einer bestimmten Zeit abzubrechen, damit die Anwendung nicht mehr reagiert. Angenommen, ein Client verwendet eine maximum_backoff-Zeit von 64 Sekunden. Nachdem dieser Wert erreicht wurde, kann der Client den Vorgang alle 64 Sekunden wiederholen. Der Client beendet dann den Vorgang nach einer deadline von 600 Sekunden.

Wie lange Clients zwischen Wiederholungen warten sollten und wie oft sie versuchen sollten, eine Anfrage ein weiteres Mal zu senden, hängt von Ihrem Anwendungsfall und den Netzwerkbedingungen ab. Mobile Clients einer Anwendung müssen unter Umständen mehr Wiederholungen mit längeren Intervallen ausführen als Desktopclients derselben Anwendung.

Wenn die Anfragewiederholungen nach Überschreiten des Werts maximum_backoff plus einer zusätzlichen Frist für Wiederholungen fehlschlagen, melden oder protokollieren Sie einen Fehler dem Support.

Nächste Schritte