簡體   English   中英

如何在另一個線程的函數中拋出異常?

[英]How to throw an exception in a function from another thread?

我遇到了一個非常奇怪的問題:基本上,我在 Java 中實現了一個服務器流式 grpc 客戶端,並且我使用微配置文件作為庫/結構。 當涉及到自動重試和回退時,Microprofiles 有非常方便的攔截器,但它依賴於在攔截注釋函數中拋出的異常,否則不會觸發重試。

對於一元 grpc 調用,這很好用,它的工作原理與普通的 REST 調用非常相似。 但是當讓一個客戶端到 grpc 服務器端流時,protobuf 將創建它自己的線程並請求回調來處理 onNext、onError 和 onCompleted。 因此,當在流作用域中調用 onError 時,拋出的任何異常都不會被發送回用於啟動流的任何函數,因此不會拋出異常來觸發 @Retry。

無法更改異步流的處理方式,也無法更改 @Retry 的觸發方式。 grpc是生成代碼,@Retry觸發器基於microprofile庫。

例子:

  @Retry(
          retryOn = {IOException.class, TimeoutException.class, StatusRuntimeException.class},
          maxDuration = 10,
          durationUnit =  ChronoUnit.SECONDS,
          maxRetries = 1,
          delay = 10,
          delayUnit = ChronoUnit.SECONDS
  )
  public void subscribeToLocations() {
    // --> Throwing an exception here triggers the @Retry <--
    SubscribeRequest locSubscribeRequest = SubscribeRequest.newBuilder().build();
    streamObserver = grpcStreamHandler();
    grpcBlockingstub.subscribeServerStreaming(locSubscribeRequest, streamObserver); // Can't change this.
  }

  private StreamObserver<SubscribeResponse> grpcStreamHandler() {
    return new StreamObserver<SubscribeResponse>() {
      @Override
      public void onNext(SubscribeResponse value) {
        // Handle grpc response
      }

      @Override
      public void onError(Throwable t) {
        // --> ERROR: Here, it should trigger the @Retry somehow. <--
      }

      @Override
      public void onCompleted() {
        // Handle oncomplete
      }
    };
  }

我試圖找到解決方案的時間比我想承認的要長,但我仍然不知所措。 有沒有辦法在一個范圍內拋出異常而在另一個范圍內結束? 還有其他解決方案嗎?

您在這里混合使用同步和異步操作,因此您需要清楚地定義什么是“成功”,並且不需要引發重試。 這可能取決於您的邏輯,流媒體的幾個選項:

  • 至少收到一個 onNext 更新,然后完成或出錯
  • onCompleted 收到有或沒有任何更新
  • 等等

定義“成功”規則后,您可以將訂閱包裝到 Future 中並等待它在提供的超時時間內得到解決。 如果未解決,則從原始調用中拋出異常。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM