---
title: "Dio Integration"
description: "Learn more about the Sentry Dio integration for the Flutter SDK."
url: https://docs.sentry.io/platforms/dart/guides/flutter/integrations/dio/
---

# Dio Integration for Flutter

References to "transactions" on this page apply to the default transaction mode. In stream mode, this integration creates service spans instead, and Sentry sends them as they finish. See [Streamed Spans](https://docs.sentry.io/platforms/dart/guides/flutter/tracing/streamed-spans.md) for more information.

The `sentry_dio` library provides [Dio](https://pub.dev/packages/dio) support for Sentry using the [HttpClientAdapter](https://pub.dev/documentation/dio/latest/dio/HttpClientAdapter-class.html). It is able to collect breadcrumbs, run tracing for HTTP requests, and capture events for failed requests.

## [Install](https://docs.sentry.io/platforms/dart/guides/flutter/integrations/dio.md#install)

To add the Dio integration, add the `sentry_dio` dependency. Version 10 requires Dio `5.8.0` or later within the v5 series. Match the Sentry integration package version to your core SDK version.

```yml
dependencies:
  sentry: ^10.0.0
  sentry_dio: ^10.0.0
  dio: ^5.8.0
```

## [Configure](https://docs.sentry.io/platforms/dart/guides/flutter/integrations/dio.md#configure)

Configuration should happen as early as possible in your application's lifecycle. In Flutter apps, initialize with `SentryFlutter.init` instead of the core `Sentry.init` shown below.

```dart
import 'package:sentry_dio/sentry_dio.dart';
import 'package:sentry/sentry.dart';

Future<void> main() async {
  await Sentry.init(
    (options) {
      options.dsn = 'https://<key>@o<orgId>.ingest.sentry.io/<projectId>';
    },
    appRunner: initApp, // Init your App.
  );
}

final dio = Dio();

// This *must* be the last initialization step of the Dio setup.
dio.addSentry(...);
```

## [Reporting Bad HTTP Requests as Errors](https://docs.sentry.io/platforms/dart/guides/flutter/integrations/dio.md#reporting-bad-http-requests-as-errors)

The `Interceptors` can also catch exceptions that may occur during requests — for example [DioException](https://pub.dev/documentation/dio/latest/dio/DioException-class.html).

```dart
import 'package:sentry_dio/sentry_dio.dart';

final dio = Dio();

dio.addSentry();

final response = await dio.get<String>('https://wrong-url.dev/');
```

This is an opt-out feature. The following example shows how to disable it:

```dart
await Sentry.init((options) {
  options.captureFailedRequests = false;
});
```

### [Failed Request Status Codes](https://docs.sentry.io/platforms/dart/guides/flutter/integrations/dio.md#failed-request-status-codes)

You can customize which status codes should be considered failed requests by setting the `failedRequestStatusCodes` option when calling `addSentry()`.

```dart
import 'package:sentry_dio/sentry_dio.dart';

final dio = Dio();

dio.addSentry(
  failedRequestStatusCodes: [
    SentryStatusCode.range(400, 404), // Capture 400-404
    SentryStatusCode(500),             // Capture 500
  ],
);
```

**Default Behavior:**

By default, `failedRequestStatusCodes` is set to `[SentryStatusCode.range(500, 599)]`, which captures server errors (status codes 500-599). Connection failures without a status code, such as timeouts, DNS failures, and certificate errors, are also captured when the target matches. Caller-initiated cancellations without a status code are excluded.

### [Failed Request Targets](https://docs.sentry.io/platforms/dart/guides/flutter/integrations/dio.md#failed-request-targets)

To control which URLs should have failed requests captured, use the `failedRequestTargets` option. This is useful when you only want to capture errors from specific APIs or domains.

The SDK matches targets against the resolved full URL, including the host. Requests to the configured Sentry DSN host are excluded to prevent recursive reporting. The SDK will only capture HTTP client errors if the URL matches one of the provided targets. Targets can be:

* Strings that appear anywhere in the URL
* Regular expression patterns

```dart
import 'package:sentry_dio/sentry_dio.dart';

final dio = Dio();

// Capture failed requests only from specific domains
dio.addSentry(
  failedRequestTargets: [
    'api.example.com',      // Matches any URL containing this string
    'myapi.com',            // Another domain to track
  ],
);
```

**Default Behavior:**

By default, `failedRequestTargets` is set to `['.*']`, which matches all URLs. HTTP responses are subject to `failedRequestStatusCodes`; connection failures follow the rules above.

### [Error Details](https://docs.sentry.io/platforms/dart/guides/flutter/integrations/dio.md#error-details)

Captured Dio errors use the stable type `DioException`, including in obfuscated builds. Default values are `HTTP Client Error with status code: <code>` for responses or `HTTP Client Error: <failure>` for connection failures. Custom Dio string builders are preserved.

Response status and metadata are attached to `event.contexts.response`. Response bodies remain on `hint.response` for inspection in `beforeSend`; they are not automatically attached to the event.

## [Tracing for HTTP Requests](https://docs.sentry.io/platforms/dart/guides/flutter/integrations/dio.md#tracing-for-http-requests)

The Dio integration also provides insight into tracing for your HTTP requests done with Dio.

### [Instrumentation Behaviour](https://docs.sentry.io/platforms/dart/guides/flutter/integrations/dio.md#instrumentation-behaviour)

* The created spans attach to the active span. In transaction mode, that's the transaction bound to the scope; in stream mode, it's the span started with `Sentry.startSpan()`. If no span is active, the span won't be sent to Sentry.
* The SDK sets the span operation to `http.client` and the description to request `$METHOD $url`. For example, `GET https://sentry.io`.
* The span finishes once the request has been executed.
* The span status depends on either the HTTP response code or `SpanStatus.internalError()` if the code does not match any of Sentry's SpanStatus options.
* When the HTTP request throws an Exception, Sentry's SDK associates this exception to the running span. If you haven't set the SDK to swallow the exception and capture it, the span and `SentryEvent` will be linked when viewing it on the Issue Details page in sentry.io.

### [Prerequisites](https://docs.sentry.io/platforms/dart/guides/flutter/integrations/dio.md#prerequisites)

Before starting, ensure:

1. The Sentry Flutter SDK is initialized. Learn more [here](https://docs.sentry.io/platforms/dart/guides/flutter.md#configure).
2. Tracing is set up. Learn more [here](https://docs.sentry.io/platforms/dart/guides/flutter/tracing.md).

### [Configure](https://docs.sentry.io/platforms/dart/guides/flutter/integrations/dio.md#configure-1)

Call `addSentry()` on your instance of `Dio`:

```dart
import 'package:sentry_dio/sentry_dio.dart';

final dio = Dio();

dio.addSentry();
```

### [Verify](https://docs.sentry.io/platforms/dart/guides/flutter/integrations/dio.md#verify)

#### [1. Execute the Code](https://docs.sentry.io/platforms/dart/guides/flutter/integrations/dio.md#1-execute-the-code)

To use the Transaction Mode tab, set `options.traceLifecycle = SentryTraceLifecycle.static` during SDK initialization.

**Stream Mode (Default)**

```dart
import 'package:sentry_dio/sentry_dio.dart';

Future<void> makeWebRequestWithDio() async {
  final dio = Dio();
  dio.addSentry();

  // Start a root span — the Dio integration attaches a span for the request
  await Sentry.startSpan('dio-web-request', (span) async {
    try {
      final response = await dio.get<String>(exampleUrl);
    } catch (exception, stackTrace) {
      await Sentry.captureException(exception, stackTrace: stackTrace);
    }
  }, parentSpan: null);
}
```

**Transaction Mode**

```dart
import 'package:sentry_dio/sentry_dio.dart';

Future<void> makeWebRequestWithDio() async {
  final dio = Dio();
  dio.addSentry();

  // If there is no active transaction, start one
  final transaction = Sentry.startTransaction(
    'dio-web-request',
    'request',
    bindToScope: true,
  );
  final span = transaction.startChild(
    'dio',
    description: 'desc',
  );
  Response<String>? response;
  try {
    response = await dio.get<String>(exampleUrl);
      span.status = const SpanStatus.ok();
    } catch (exception, stackTrace) {
      span.throwable = exception;
      span.status = const SpanStatus.internalError();
      await Sentry.captureException(exception, stackTrace: stackTrace);
    } finally {
      await span.finish();
      await transaction.finish();
    }
}
```

#### [2. View the Transaction on Sentry.io](https://docs.sentry.io/platforms/dart/guides/flutter/integrations/dio.md#2-view-the-transaction-on-sentryio)

To view the recorded transaction, log into [sentry.io](https://sentry.io) and open your project. Clicking **Performance** will open a page with transactions, where you can select the just recorded transaction with the name `dio-web-request`.
