返回

Flutter 入门与实战(二十九):Dio 拦截器的巧妙运用

Android

Dio 拦截器:提升 Flutter HTTP 请求处理的利器

导言

在 Flutter 开发中,HTTP 客户端扮演着至关重要的角色,它负责与服务器交互、发送请求并接收响应。Dio 作为一款广泛流行的 HTTP 客户端库,其出色的拦截器功能为开发者提供了强大的请求定制和响应处理能力,本文将深入探讨 Dio 拦截器的巧妙运用,帮助你轻松驾驭常见的 HTTP 请求和响应处理场景。

拦截器的本质

Dio 拦截器本质上是 HTTP 请求和响应流中的切入点,它允许我们在请求发送到服务器或服务器响应到达应用之前或之后执行自定义操作。通过拦截器,我们可以:

  • 修改请求头和请求参数
  • 添加 Cookie 或其他凭证
  • 缓存响应以提高性能
  • 处理未经授权的错误并自动刷新令牌
  • 记录请求和响应详细信息以进行调试

拦截器的类型

Dio 提供了三种类型的拦截器:

  • 请求拦截器: 在请求发送到服务器之前执行
  • 响应拦截器: 在服务器响应到达应用之后执行
  • 错误拦截器: 在请求过程中发生错误时执行

创建拦截器

创建拦截器非常简单,只需实现 Interceptor 接口并重写以下方法:

class MyInterceptor implements Interceptor {
  @override
  void onRequest(RequestOptions options, RequestInterceptorHandler handler) {}

  @override
  void onResponse(Response response, ResponseInterceptorHandler handler) {}

  @override
  void onError(DioError err, ErrorInterceptorHandler handler) {}
}

使用拦截器

要使用拦截器,请将其添加到 Dio 实例:

Dio dio = Dio();
dio.interceptors.add(MyInterceptor());

你可以添加多个拦截器,它们将按添加到 Dio 实例的顺序执行。

常见应用场景

添加全局请求头

拦截器可以轻松地为所有 HTTP 请求添加全局请求头:

class HeaderInterceptor implements Interceptor {
  @override
  void onRequest(RequestOptions options, RequestInterceptorHandler handler) {
    options.headers['Content-Type'] = 'application/json';
    handler.next(options);
  }
}

缓存响应

拦截器可以将响应缓存到本地存储,以提高后续请求的性能:

class CacheInterceptor implements Interceptor {
  @override
  void onResponse(Response response, ResponseInterceptorHandler handler) {
    // 将响应缓存到本地存储
    CacheManager.save(response);
    handler.next(response);
  }
}

处理未经授权错误

拦截器可以处理未经授权的错误并自动刷新令牌:

class AuthInterceptor implements Interceptor {
  @override
  onError(DioError err, ErrorInterceptorHandler handler) {
    if (err.response?.statusCode == 401) {
      // 刷新令牌并重试请求
      refreshToken();
      RequestOptions options = err.requestOptions;
      options.headers['Authorization'] = 'Bearer $newToken';
      handler.retry(options);
    }
  }
}

总结

Dio 拦截器是一个强大的工具,可以极大地增强你的 Flutter HTTP 请求处理能力。通过拦截器,你可以轻松地处理各种常见的场景,提高代码的可重用性和可维护性。掌握拦截器,你将能够在 Flutter 开发中创建健壮而高效的网络层。

常见问题解答

  1. 如何为特定 URL 或请求类型创建拦截器?
    你可以通过实现 Interceptor.priority 方法并在请求处理过程中检查 RequestOptions 对象来实现此目的。

  2. 是否可以动态地添加和删除拦截器?
    是的,你可以使用 Dio.interceptors.addDio.interceptors.remove 方法动态地管理拦截器。

  3. 如何使用拦截器来记录请求和响应详细信息?
    你可以通过在 onRequestonResponse 方法中使用 debugPrintprint 函数来实现此目的。

  4. 拦截器是否可以在多个 Dio 实例中共享?
    是的,你可以通过创建自定义拦截器类并将其实例化多次来在多个 Dio 实例中共享拦截器。

  5. 如何处理拦截器中的异常?
    你可以通过实现 onError 方法并在其中处理异常来处理拦截器中的异常。