# Retries with backoff

> Learn how to configure automatic retries with exponential backoff in Fern SDKs. Control retry limits and customize retryable status codes.

<Warning title="Pro and Enterprise feature">
  This feature is available only for the [Pro and Enterprise plans](https://buildwithfern.com/pricing). To get started, reach out to [support@buildwithfern.com](mailto:support@buildwithfern.com).
</Warning>

Fern SDKs will automatically retry failed requests with exponential backoff. A request will be retried as
long as the request is deemed retryable and the number of retry attempts has
not grown larger than the configured retry limit.

### Retryable status codes

A request is deemed retryable when any of the following HTTP status codes is returned:

* [408](https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/408) (Timeout)
* [429](https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/429) (Too Many Requests)
* [5XX](https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/500) (Internal Server Errors)

Note that you can configure the list of retryable status codes as well. For example,
if you want to remove the `429` status code from the list of retryable status codes, you can do so.

### Overriding the retry limit

By default, the SDK will retry a failed request up to 2 times. SDK users can override the global
default retry limit when instantiating the client.

<CodeBlocks>
  <CodeBlock title="TypeScript">
    ```ts {4}
    import { ImdbClient } from "imdb";

    const client = new ImdbClient({
      maxRetries: 1 // overrides the default retry limit to 1
    });
    ```
  </CodeBlock>

  <CodeBlock title="Python">
    ```python {4, 8}
    from imdb.client import Imdb, AsyncImdb

    client = Imdb({
      max_retries: 1 # overrides the default retry limit to 1
    })

    async_client = AsyncImdb({
      max_retries: 1 # overrides the default retry limit to 1
    })
    ```
  </CodeBlock>

  <CodeBlock title="Java">
    ```java {4}
    import com.imdb.ImdbClient;

    ImdbClient client = new ImdbClient.Builder()
      .maxRetries(1) // overrides the default retry limit to 1
      .build();
    ```
  </CodeBlock>

  <CodeBlock title="Go">
    ```go {7}
      import (
        imdbclient "github.com/fern-workos/workos-go/client"
        "github.com/fern-workos/workos-go/option"
      )

      client := imdbclient.NewClient(
        option.WithMaxAttempts(1), // overrides the default retry limit to 1
      )
    ```
  </CodeBlock>

  <CodeBlock title="C#">
    ```csharp {4}
    using Imdb;

    var client = new ImdbClient(new ClientOptions {
      MaxRetries = 1 // overrides the default retry limit to 1
    });
    ```
  </CodeBlock>

  <CodeBlock title="Swift">
    ```swift {5}
    import Imdb

    let client = ImdbClient(
      baseURL: "https://api.imdb.com",
      maxRetries: 1 // overrides the default retry limit to 1
    )
    ```
  </CodeBlock>

  <CodeBlock title="PHP">
    ```php {4}
    use Imdb\ImdbClient;

    $client = new ImdbClient([
      "maxRetries" => 1 // overrides the default retry limit to 1
    ]);
    ```
  </CodeBlock>
</CodeBlocks>

It's also possible to override the retry limit on a per-request basis.

<CodeBlocks>
  <CodeBlock title="TypeScript">
    ```ts {2}
      client.movie.get("tt0111161", {
        maxRetries: 3 // overrides the default retry limit to 3
      });
    ```
  </CodeBlock>

  <CodeBlock title="Python">
    ```python {2}
      client.movie.get("tt0111161", {
        max_retries: 3 // overrides the default retry limit to 3
      })
    ```
  </CodeBlock>

  <CodeBlock title="Java">
    ```java {2}
      client.movie().get("tt0111161", RequestOptions.builder()
        .maxRetries(3) // overrides the default retry limit to 3
        .build());
    ```
  </CodeBlock>

  <CodeBlock title="Go">
    ```go {4}
      response, err := client.Movies.Get(
        ctx,
        "tt0111161",
        option.WithMaxAttempts(1),
      )
    ```
  </CodeBlock>

  <CodeBlock title="C#">
    ```csharp {2}
      var movie = await client.Movie.GetAsync("tt0111161", new RequestOptions {
        MaxRetries = 3 // overrides the default retry limit to 3
      });
    ```
  </CodeBlock>

  <CodeBlock title="Swift">
    ```swift {2}
      let movie = try await client.movie.get("tt0111161", requestOptions: RequestOptions(
        maxRetries: 3 // overrides the default retry limit to 3
      ))
    ```
  </CodeBlock>

  <CodeBlock title="PHP">
    ```php {2}
      $movie = $client->movie->get("tt0111161", [
        "maxRetries" => 3 // overrides the default retry limit to 3
      ]);
    ```
  </CodeBlock>
</CodeBlocks>