共用方式為


適用於 Java 的 Azure SDK 中長時間執行的作業

本文提供搭配 Azure SDK for Java 使用長時間執行作業的概觀。

Azure 上的某些作業可能需要較長的時間才能完成。 這些作業超出快速要求/回應流程的標準 HTTP 樣式。 例如,將數據從來源 URL 複製到記憶體 Blob,或定型模型以辨識表單,是可能需要幾秒鐘到幾分鐘的作業。 這類作業稱為「Long-Running 作業」,而且通常縮寫為 「LRO」。 LRO 可能需要幾秒鐘、分鐘、小時、天或更長的時間才能完成,視要求的作業和必須在伺服器端執行的程式而定。

在適用於 Azure 的 Java 用戶端函式庫中,有一個慣例是所有長時間執行的作業都以 begin 作為前置詞。 此前置詞表示此作業長時間執行,而且與這項作業的互動方式與一般要求/回應流程稍有不同。 除了 begin 前綴之外,作業的傳回類型也不同於一般情況,以啟用長時間運行作業功能的完整範圍。 如同適用於 Java 的 Azure SDK 中大部分項目一樣,長時間執行的作業都有同步和異步 API:

  • 在同步用戶端中,長時間執行的作業會傳回 SyncPoller 實例。
  • 在異步用戶端中,長時間執行的作業會返回一個 PollerFlux 實例。

SyncPollerPollerFlux 都是用戶端抽象概念,旨在簡化與長時間執行伺服器端作業的互動。 本文的其餘部分會概述使用這些類型的最佳做法。

同步長時運行的操作

任何回傳SyncPoller的 API 呼叫會立即啟動長時間運行的操作。 API 會立即傳回 SyncPoller ,讓您監視長時間執行的作業進度,並擷取最終結果。 下列範例示範如何使用 SyncPoller 來監視長時間執行作業的進度。

SyncPoller<UploadBlobProgress, UploadedBlobProperties> poller = syncClient.beginUploadFromUri(<URI to upload from>)
PollResponse<UploadBlobProgress> response;

do {
    response = poller.poll();
    System.out.println("Status of long running upload operation: " + response.getStatus());
    Duration pollInterval = response.getRetryAfter();
    TimeUnit.MILLISECONDS.sleep(pollInterval.toMillis());
} while (!response.getStatus().isComplete());

這個範例使用 poll() 上的 SyncPoller 方法來擷取長時間執行作業進度的相關信息。 此程式代碼會將狀態列印至控制台,但更好的實作會根據此狀態做出相關決策。

方法 getRetryAfter() 會傳回下一次輪詢之前等待多久的資訊。 大部分的 Azure 執行時間較長的作業會傳回輪詢的延遲時間作為 HTTP 回應的一部分(即常用的 retry-after 標頭)。 如果回應未包含輪詢延遲,則 getRetryAfter() 方法會在叫用長時間執行的作業時傳回指定的持續時間。

上述範例使用 do..while 迴圈重複進行輪詢,以確保長時間執行的作業完成。 如果您對這些中繼結果不感興趣,您可以改為呼叫 waitForCompletion()。 此呼叫會封鎖目前的線程,直到長時間執行的作業完成並傳回最後一個輪詢回應:

PollResponse<UploadBlobProgress> response = poller.waitForCompletion();

如果最後一個輪詢回應指出長時間執行的作業已順利完成,您可以使用getFinalResult()來擷取最終結果。

if (LongRunningOperationStatus.SUCCESSFULLY_COMPLETED == response.getStatus()) {
    UploadedBlobProperties result = poller.getFinalResult();
}

中的其他 SyncPoller 實用 API 包括:

  1. waitForCompletion(Duration):在指定的逾時期限內等候長時間執行的作業完成。
  2. waitUntil(LongRunningOperationStatus):等待收到指定長時間執行操作的狀態。
  3. waitUntil(LongRunningOperationStatus, Duration):等到收到指定的長時間執行作業狀態,或等待指定的超時期限到期。

異步長時間執行的作業

下列範例示範 如何 PollerFlux 讓您觀察長時間執行的作業。 在異步 API 中,網路呼叫發生在與呼叫 subscribe()的主要線程不同的線程中。 這表示主線程可能會在結果可用之前終止。 您必須確保應用程式不會在異步操作完成之前結束。

異步 API 會立即返回 PollerFlux,但長時間執行的操作在您訂閱 PollerFlux 之前不會啟動。 此程式是所有 Flux型 API 的運作方式。 下列範例顯示異步長時間執行的作業:

asyncClient.beginUploadFromUri(...)
    .subscribe(response -> System.out.println("Status of long running upload operation: " + response.getStatus()));

在下列範例中,您會在長時間執行的作業上取得間歇性狀態更新。 您可以使用這些更新來判斷長時間執行的作業是否仍以預期的方式運作。 此範例會將狀態列印至控制台,但較佳的實作會根據此狀態做出相關的錯誤處理決策。

如果您對中繼狀態更新不感興趣,而且只想在最終結果送達時收到通知,您可以使用類似下列範例的程式代碼:

asyncClient.beginUploadFromUri(...)
    .last()
    .flatMap(response -> {
        if (LongRunningOperationStatus.SUCCESSFULLY_COMPLETED == response.getStatus()) {
            return response.getFinalResult();
        }
        return Mono.error(new IllegalStateException("Polling completed unsuccessfully with status: "+ response.getStatus()));
    })
    .subscribe(
        finalResult -> processFormPages(finalResult),
        ex -> countDownLatch.countDown(),
        () -> countDownLatch.countDown());

在此程式代碼中,您會呼叫 last()來擷取長時間執行作業的最終結果。 此呼叫會告知PollerFlux 您想要等待所有輪詢完成,此時長時間執行的操作進入到終止狀態,您可以檢查其狀態以確定結果。 如果輪詢器指出長時間執行的作業已順利完成,您可以擷取最終結果,並將它傳遞給訂閱呼叫中的取用者。

後續步驟

現在您已熟悉適用於 Java 的 Azure SDK 中長時間執行的 API,請參閱在 適用於 Java 的 Azure SDK 中設定 Proxy ,以瞭解如何進一步自定義 HTTP 用戶端。