我有一個使Http調用到外部服務的actor。有時服務會使用Http 404進行響應,並且有時也會出現http連接錯誤。再次重試時,這些都會消失。重試來自Akka Actor的http調用的正確方法是什麼
什麼是由演員重試請求的最佳方式。
什麼,我能想到的是
使用主管戰略和重啓演員
使用在重試HTTP調用演員遞歸方法, 最大重試次數次
哪一個是正確的方法,1或2.我認爲方法1對於像重試一個Http調用那樣簡單的事情來說是過度的。請分享你的建議。
我有一個使Http調用到外部服務的actor。有時服務會使用Http 404進行響應,並且有時也會出現http連接錯誤。再次重試時,這些都會消失。重試來自Akka Actor的http調用的正確方法是什麼
什麼是由演員重試請求的最佳方式。
什麼,我能想到的是
使用主管戰略和重啓演員
使用在重試HTTP調用演員遞歸方法, 最大重試次數次
哪一個是正確的方法,1或2.我認爲方法1對於像重試一個Http調用那樣簡單的事情來說是過度的。請分享你的建議。
在我看來,你的兩種方法都是有效的。
第一種方法是在我的眼睛擁抱失敗,讓演員只能做它應該做的(而不是讓它處理重試等)
有方面要做到這一點更被動的方式一個整潔的東西建在Akka監督:BackoffSupervisor
在我看來,這是一個完美的適合問題,其中演員由於外部因素失敗,它可能是有道理的等待一段時間再試一次(如在你的情況與http調用)。
從文檔:
val supervisor = BackoffSupervisor.props(
Backoff.onFailure(
childProps,
childName = "myEcho",
minBackoff = 3.seconds,
maxBackoff = 30.seconds,
randomFactor = 0.2 // adds 20% "noise" to vary the intervals slightly
))
您可以定義一個最小和最大的補償和監管當局嘗試,直到達到最大重啓演員之前兩倍的等待時間。只有這樣它纔會停止嘗試。
如果你喜歡你的第二個選擇,我不會用遞歸方法去,但會schedule a message到演員本身在一段時間後再次嘗試HTTP調用:
system.scheduler.scheduleOnce(1 seconds, self, TryAgain)
我倒是建議使用「之後」模式。這可以讓你在失敗的情況下重複你的請求。類似這樣的:
def retryRequest(ref: ActorRef, attemptsNumber: Int, step: Int)(
implicit ac: ActorSystem): Future[HttpResponse] = {
implicit val timeout = Timeout(5 seconds)
implicit val ec = ac.dispatcher
val s1 = after[HttpResponse](5 seconds, ac.scheduler) {
Http().singleRequest(HttpRequest(uri = "http://akka.io"))
}
s1 flatMap { res =>
res match {
case HttpResponse(StatusCodes.NotFound, headers, entity, _) => {
if(step < attemptsNumber)
retryRequest(ref, attemptsNumber, (step + 1))
else
s1
}
case HttpResponse(StatusCodes.OK, headers, entity, _) => s1
}
}
}
這也是一個不錯的選擇 –
感謝您的建議 –