Die vorliegende Übersetzung wurde maschinell erstellt. Im Falle eines Konflikts oder eines Widerspruchs zwischen dieser übersetzten Fassung und der englischen Fassung (einschließlich infolge von Verzögerungen bei der Übersetzung) ist die englische Fassung maßgeblich.
Asynchrone Programmierung mit dem AWS SDK für C++
Asynchrone SDK-Methoden
Für viele Methoden bietet das SDK for C++ sowohl synchrone als auch asynchrone Versionen. Eine Methode ist asynchron, wenn sie das Async Suffix in ihrem Namen enthält. Beispielsweise PutObject ist die Amazon S3 S3-Methode synchron, während sie asynchron PutObjectAsync ist.
Wie alle asynchronen Operationen kehrt eine asynchrone SDK-Methode zurück, bevor ihre Hauptaufgabe abgeschlossen ist. Die PutObjectAsync Methode kehrt beispielsweise zurück, bevor das Hochladen der Datei in den Amazon S3 S3-Bucket abgeschlossen ist. Während der Upload-Vorgang fortgesetzt wird, kann die Anwendung andere Operationen ausführen, einschließlich des Aufrufs anderer asynchroner Methoden. Die Anwendung wird benachrichtigt, dass ein asynchroner Vorgang abgeschlossen ist, wenn eine zugehörige Callback-Funktion aufgerufen wird.
In den folgenden Abschnitten wird ein Codebeispiel beschrieben, das den Aufruf der PutObjectAsync asynchronen Methode demonstriert. Jeder Abschnitt konzentriert sich auf einzelne Teile der gesamten Quelldatei
Asynchrone SDK-Methoden werden aufgerufen
Im Allgemeinen akzeptiert die asynchrone Version einer SDK-Methode die folgenden Argumente.
-
Ein Verweis auf dasselbe Objekt vom Typ Request wie sein synchrones Gegenstück.
-
Ein Verweis auf eine Rückruffunktion für einen Antworthandler. Diese Callback-Funktion wird aufgerufen, wenn der asynchrone Vorgang abgeschlossen ist. Eines der Argumente enthält das Ergebnis der Operation.
-
Eine Option
shared_ptrfür einAsyncCallerContextObjekt. Das Objekt wird an den Callback des Antworthandlers übergeben. Es enthält eine UUID-Eigenschaft, die verwendet werden kann, um Textinformationen an den Callback zu übergeben.
Die unten gezeigte uploadFileAsync Methode richtet die Amazon S3 PutObjectAsync S3-Methode des SDK ein und ruft sie auf, um eine Datei asynchron in einen Amazon S3 S3-Bucket hochzuladen.
Die Funktion empfängt Verweise auf ein S3Client Objekt und ein PutObjectRequest Objekt. Sie empfängt sie von der Hauptfunktion, weil wir sicherstellen müssen, dass diese Objekte während der gesamten Dauer der asynchronen Aufrufe existieren.
shared_ptrEinem AsyncCallerContext Objekt wird A zugewiesen. Seine UUID Eigenschaft ist auf den Amazon S3 S3-Objektnamen gesetzt. Zu Demonstrationszwecken greift der Response-Handler-Callback auf die Eigenschaft zu und gibt ihren Wert aus.
Der Aufruf von PutObjectAsync beinhaltet ein Referenzargument für die Callback-Funktion des Antworthandlers. uploadFileAsyncFinished Diese Callback-Funktion wird im nächsten Abschnitt genauer untersucht.
bool AwsDoc::S3::uploadFileAsync(const Aws::S3::S3Client &s3Client, Aws::S3::Model::PutObjectRequest &request, const Aws::String &bucketName, const Aws::String &fileName) { request.SetBucket(bucketName); request.SetKey(fileName); const std::shared_ptr<Aws::IOStream> input_data = Aws::MakeShared<Aws::FStream>("SampleAllocationTag", fileName.c_str(), std::ios_base::in | std::ios_base::binary); if (!*input_data) { std::cerr << "Error: unable to open file " << fileName << std::endl; return false; } request.SetBody(input_data); // Create and configure the context for the asynchronous put object request. std::shared_ptr<Aws::Client::AsyncCallerContext> context = Aws::MakeShared<Aws::Client::AsyncCallerContext>("PutObjectAllocationTag"); context->SetUUID(fileName); // Make the asynchronous put object call. Queue the request into a // thread executor and call the uploadFileAsyncFinished function when the // operation has finished. s3Client.PutObjectAsync(request, uploadFileAsyncFinished, context); return true; }
Die Ressourcen für einen asynchronen Vorgang müssen vorhanden sein, bis der Vorgang abgeschlossen ist. Beispielsweise müssen die Client- und Anforderungsobjekte vorhanden sein, bis die Anwendung eine Benachrichtigung erhält, dass der Vorgang abgeschlossen wurde. Die Anwendung selbst kann erst beendet werden, wenn der asynchrone Vorgang abgeschlossen ist.
Aus diesem Grund akzeptiert die uploadFileAsync Methode Verweise auf PutObjectRequest Objekte S3Client und Objekte, anstatt sie in der uploadFileAsync Methode zu erstellen und in einer lokalen Variablen zu speichern.
In diesem Beispiel kehrt die PutObjectAsync Methode unmittelbar nach Beginn des asynchronen Vorgangs zum Aufrufer zurück, sodass die aufrufende Kette zusätzliche Aufgaben ausführen kann, während der Upload-Vorgang läuft.
Wenn der Client in einer lokalen Variablen in der uploadFileAsync Methode gespeichert würde, würde er den Gültigkeitsbereich verlassen, wenn die Methode zurückgegeben wird. Das Client-Objekt muss jedoch weiterhin existieren, bis der asynchrone Vorgang abgeschlossen ist.
Benachrichtigung über den Abschluss eines asynchronen Vorgangs
Wenn ein asynchroner Vorgang abgeschlossen ist, wird eine Callback-Funktion für den Antworthandler der Anwendung aufgerufen. Diese Benachrichtigung enthält das Ergebnis des Vorgangs. Das Ergebnis ist in derselben Klasse vom Typ Outcome enthalten, die vom synchronen Gegenstück der Methode zurückgegeben wird. Im Codebeispiel befindet sich das Ergebnis in einem Objekt. PutObjectOutcome
Die Rückruffunktion des Beispiels für den Antworthandler uploadFileAsyncFinished ist unten dargestellt. Sie prüft, ob der asynchrone Vorgang erfolgreich war oder fehlgeschlagen ist. Es verwendet astd::condition_variable, um den Anwendungsthread darüber zu informieren, dass der asynchrone Vorgang abgeschlossen ist.
// A mutex is a synchronization primitive that can be used to protect shared // data from being simultaneously accessed by multiple threads. std::mutex AwsDoc::S3::upload_mutex; // A condition_variable is a synchronization primitive that can be used to // block a thread, or to block multiple threads at the same time. // The thread is blocked until another thread both modifies a shared // variable (the condition) and notifies the condition_variable. std::condition_variable AwsDoc::S3::upload_variable;
void uploadFileAsyncFinished(const Aws::S3::S3Client *s3Client, const Aws::S3::Model::PutObjectRequest &request, const Aws::S3::Model::PutObjectOutcome &outcome, const std::shared_ptr<const Aws::Client::AsyncCallerContext> &context) { if (outcome.IsSuccess()) { std::cout << "Success: uploadFileAsyncFinished: Finished uploading '" << context->GetUUID() << "'." << std::endl; } else { std::cerr << "Error: uploadFileAsyncFinished: " << outcome.GetError().GetMessage() << std::endl; } // Unblock the thread that is waiting for this function to complete. AwsDoc::S3::upload_variable.notify_one(); }
Wenn der asynchrone Vorgang abgeschlossen ist, können die damit verbundenen Ressourcen freigegeben werden. Die Anwendung kann auch beendet werden, wenn sie dies wünscht.
Der folgende Code zeigt, wie die uploadFileAsyncFinished Methoden uploadFileAsync und von einer Anwendung verwendet werden.
Die Anwendung weist die PutObjectRequest Objekte S3Client und so zu, dass sie so lange bestehen bleiben, bis der asynchrone Vorgang abgeschlossen ist. Nach dem Aufruf uploadFileAsync kann die Anwendung alle gewünschten Operationen ausführen. Der Einfachheit halber verwendet das Beispiel ein std::mutex und, std::condition_variable um zu warten, bis der Antworthandler-Callback das Programm darüber informiert, dass der Upload-Vorgang abgeschlossen ist.
int main(int argc, char* argv[]) { if (argc != 3) { std::cout << R"( Usage: run_put_object_async <file_name> <bucket_name> Where: file_name - The name of the file to upload. bucket_name - The name of the bucket to upload the object to. )" << std::endl; return 1; } const Aws::SDKOptions options; Aws::InitAPI(options); { const Aws::String fileName = argv[1]; const Aws::String bucketName = argv[2]; // A unique_lock is a general-purpose mutex ownership wrapper allowing // deferred locking, time-constrained attempts at locking, recursive // locking, transfer of lock ownership, and use with // condition variables. std::unique_lock<std::mutex> lock(AwsDoc::S3::upload_mutex); // Create and configure the Amazon S3 client. // This client must be declared here, as this client must exist // until the put object operation finishes. const Aws::S3::S3ClientConfiguration config; // Optional: Set to the AWS Region in which the bucket was created (overrides config file). // config.region = "us-east-1"; const Aws::S3::S3Client s3Client(config); // Create the request object. // This request object must be declared here, because the object must exist // until the put object operation finishes. Aws::S3::Model::PutObjectRequest request; AwsDoc::S3::uploadFileAsync(s3Client, request, bucketName, fileName); std::cout << "main: Waiting for file upload attempt..." << std::endl << std::endl; // While the put object operation attempt is in progress, // you can perform other tasks. // This example simply blocks until the put object operation // attempt finishes. AwsDoc::S3::upload_variable.wait(lock); std::cout << std::endl << "main: File upload attempt completed." << std::endl; } Aws::ShutdownAPI(options); return 0; }
Auf GitHub finden Sie ein vollständiges Beispiel