You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Flutter/Firebase Performance无法捕获网络请求问题咨询

Firebase Performance 不显示 Dio 网络请求的解决方案与已知情况

兄弟,这个问题我之前踩过坑,太懂你的感受了——Firebase Performance默认确实不会自动捕获Dio的网络请求,而且这是个挺普遍的情况,好多用Dio的Flutter开发者都遇到过。

已知情况说明

  • Firebase Performance官方只对原生网络库(比如Android的OkHttp、iOS的NSURLSession)和Flutter自带的http包提供自动捕获支持,因为http底层还是调用原生网络接口。而Dio是基于Dart独立封装的网络框架,不在默认捕获范围内,官方文档里也明确提到了这点。
  • 社区里关于这个问题的讨论很多,大家的解决方案基本都是手动通过拦截器上报性能数据。

亲测有效的解决方法

核心思路是给Dio加一个自定义拦截器,在请求发起、响应/错误返回时,用Firebase Performance的HttpMetric类手动记录并上报性能数据。

1. 编写Firebase Performance拦截器

创建一个拦截器类,实现请求生命周期的监听:

import 'package:dio/dio.dart';
import 'package:firebase_performance/firebase_performance.dart';

class FirebasePerformanceInterceptor extends Interceptor {
  final FirebasePerformance _perf = FirebasePerformance.instance;

  @override
  void onRequest(RequestOptions options, RequestInterceptorHandler handler) async {
    // 初始化请求性能指标
    final metric = _perf.newHttpMetric(
      options.uri.toString(),
      HttpMethod.values.firstWhere((e) => e.name == options.method),
    );
    await metric.start();
    // 把指标对象存到请求的extra参数里,方便后续回调使用
    options.extra['firebase_perf_metric'] = metric;
    super.onRequest(options, handler);
  }

  @override
  void onResponse(Response response, ResponseInterceptorHandler handler) async {
    final metric = response.requestOptions.extra['firebase_perf_metric'] as HttpMetric?;
    if (metric != null) {
      // 填充响应相关数据
      metric
        ..responseCode = response.statusCode
        ..responsePayloadSize = response.data?.toString().length ?? 0
        ..requestPayloadSize = response.requestOptions.data?.toString().length ?? 0;
      await metric.stop();
    }
    super.onResponse(response, handler);
  }

  @override
  void onError(DioError err, ErrorInterceptorHandler handler) async {
    final metric = err.requestOptions.extra['firebase_perf_metric'] as HttpMetric?;
    if (metric != null) {
      // 错误场景下也要记录状态码和数据大小
      metric
        ..responseCode = err.response?.statusCode ?? 0
        ..responsePayloadSize = err.response?.data?.toString().length ?? 0
        ..requestPayloadSize = err.requestOptions.data?.toString().length ?? 0;
      await metric.stop();
    }
    super.onError(err, handler);
  }
}

2. 给Dio添加拦截器

在初始化Dio的时候,把上面的拦截器加进去:

final dio = Dio();
// 添加Firebase性能监控拦截器
dio.interceptors.add(FirebasePerformanceInterceptor());

3. 额外注意事项

  • 确保Firebase Performance已经正确初始化,建议在main函数里显式开启性能收集:
    void main() async {
      WidgetsFlutterBinding.ensureInitialized();
      await Firebase.initializeApp();
      // 显式开启性能收集(默认是开启的,但避免环境问题)
      await FirebasePerformance.instance.setPerformanceCollectionEnabled(true);
      runApp(const MyApp());
    }
    
  • 数据上报有延迟,不是实时显示的,一般需要等待5-15分钟才能在Firebase控制台看到新的网络请求数据。
  • 如果是本地测试环境的请求,要确保设备能正常连接Firebase服务,否则数据无法上报。

我自己的项目里用这个方法已经稳定运行很久了,控制台里能看到所有Dio请求的耗时、状态码、请求/响应大小等完整统计数据,亲测有效。

内容的提问来源于stack exchange,提问作者fvisticot

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.11 09:06:03