summaryrefslogtreecommitdiff
path: root/cli/util/retry.rs
diff options
context:
space:
mode:
authorhaturau <135221985+haturatu@users.noreply.github.com>2024-11-20 01:20:47 +0900
committerGitHub <noreply@github.com>2024-11-20 01:20:47 +0900
commit85719a67e59c7aa45bead26e4942d7df8b1b42d4 (patch)
treeface0aecaac53e93ce2f23b53c48859bcf1a36ec /cli/util/retry.rs
parent67697bc2e4a62a9670699fd18ad0dd8efc5bd955 (diff)
parent186b52731c6bb326c4d32905c5e732d082e83465 (diff)
Merge branch 'denoland:main' into main
Diffstat (limited to 'cli/util/retry.rs')
-rw-r--r--cli/util/retry.rs41
1 files changed, 41 insertions, 0 deletions
diff --git a/cli/util/retry.rs b/cli/util/retry.rs
new file mode 100644
index 000000000..a8febe60d
--- /dev/null
+++ b/cli/util/retry.rs
@@ -0,0 +1,41 @@
+// Copyright 2018-2024 the Deno authors. All rights reserved. MIT license.
+
+use std::future::Future;
+use std::time::Duration;
+
+pub fn retry<
+ F: FnMut() -> Fut,
+ T,
+ E,
+ Fut: Future<Output = Result<T, E>>,
+ ShouldRetry: FnMut(&E) -> bool,
+>(
+ mut f: F,
+ mut should_retry: ShouldRetry,
+) -> impl Future<Output = Result<T, E>> {
+ const WAITS: [Duration; 3] = [
+ Duration::from_millis(100),
+ Duration::from_millis(250),
+ Duration::from_millis(500),
+ ];
+
+ let mut waits = WAITS.into_iter();
+ async move {
+ let mut first_result = None;
+ loop {
+ let result = f().await;
+ match result {
+ Ok(r) => return Ok(r),
+ Err(e) if !should_retry(&e) => return Err(e),
+ _ => {}
+ }
+ if first_result.is_none() {
+ first_result = Some(result);
+ }
+ let Some(wait) = waits.next() else {
+ return first_result.unwrap();
+ };
+ tokio::time::sleep(wait).await;
+ }
+ }
+}