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

Flutter网络请求获取数据失败,FutureBuilder显示异常求助

Flutter网络请求与FutureBuilder问题排查

问题概述

  • 按Flutter官方文档实现网络请求后,数据无法正常显示,怀疑问题出在FutureBuilder中,不会正确实现try-catch错误处理
  • 类声明级别使用late Future futurePrayer;时,数据能显示但出现调用错误;添加泛型late Future<Prayer> futurePrayer;后错误消失,但无数据展示
  • 当前触发NoSuchMethodError: 'call'错误,提示“对象没有实例方法'call'”

错误截图

相关代码

FutureBuilder代码

FutureBuilder(
  future: futurePrayer,
  builder: (context, snapshot) {
    if (snapshot.hasData) {
      // TODO: fix NoSuchMethodError: 'call
      // Dynamic call of object has no instance method 'call'.
      return Text(snapshot.data.ashar());
    } else if (snapshot.hasError) {
      return Text('${snapshot.error}');
    }

    // By default, show a loading spinner.
    return const CircularProgressIndicator();
  }
),

ApiBaseHelper代码

Future<Prayer> ApiBaseHelper() async {
  final response = await http
      .get(Uri.parse('https://api.myquran.com/v2/sholat/jadwal/1420/2025-01-05'));

  
  if (response.statusCode == 200) {
    // If the server did return a 200 OK response,
    // then parse the JSON.
    return Prayer.fromJson(jsonDecode(response.body) as Map<String, dynamic>);
  } else {
    // If the server did not return a 200 OK response,
    // then throw an exception.
    await ApiBaseHelper().catchError(print);
    throw Exception('Failed to load album');
  }
}

Prayer数据类代码

// this class is not used yet
class PrayerResponse {
  List<String>? prayerTime;

  PrayerResponse({
    required this.prayerTime,
  });
  PrayerResponse.fromJson(Map<String, dynamic> json) {
    prayerTime = json['data']['jadwal'];
  }
}

class Prayer {
  final int id;
  final String lokasi;
  final String  daerah;
  final String  ashar;

  Prayer(
    {
      required this.id,
      required this.lokasi,
      required this.daerah,
      required this.ashar,
    }
  );
  factory Prayer.fromJson(Map<String, dynamic> json) {
    return Prayer(
      id : json['data']['id'],
      lokasi : json['data']['lokasi'],
      daerah : json['data']['daerah'],
      ashar : json['data']['jadwal']['ashar'],
    );
  }
}

问题解决步骤

1. 修复NoSuchMethodError: 'call'错误

错误根源是将String属性当作方法调用:snapshot.data.ashar()中,ashar是Prayer类的String成员变量,不是方法,因此不需要加括号,改为:

return Text(snapshot.data.ashar);

如果使用泛型Future<Prayer>,建议给FutureBuilder指定泛型类型,避免类型转换问题:

FutureBuilder<Prayer>(
  future: futurePrayer,
  builder: (context, snapshot) {
    if (snapshot.hasData) {
      return Text(snapshot.data!.ashar); // 用!确保非空,或用?处理空值
    }
    // ... 其他代码
  }
)

2. 修正ApiBaseHelper的错误处理与命名

  • Dart函数名应遵循小驼峰命名规范,把ApiBaseHelper改为apiBaseHelper
  • 移除错误分支中的递归调用await ApiBaseHelper().catchError(print);,这会导致无限递归,直接抛出异常即可,同时建议添加try-catch包裹请求逻辑:
Future<Prayer> apiBaseHelper() async {
  try {
    final response = await http.get(Uri.parse('https://api.myquran.com/v2/sholat/jadwal/1420/2025-01-05'));
    
    if (response.statusCode == 200) {
      return Prayer.fromJson(jsonDecode(response.body) as Map<String, dynamic>);
    } else {
      throw Exception('请求失败,状态码:${response.statusCode}');
    }
  } catch (e) {
    print('网络请求错误:$e');
    throw Exception('加载祈祷时间失败');
  }
}

3. 正确初始化futurePrayer

使用泛型late Future<Prayer> futurePrayer;时,必须在合适的时机(如initState)初始化,避免每次build都重新发起请求:

late Future<Prayer> futurePrayer;

@override
void initState() {
  super.initState();
  futurePrayer = apiBaseHelper(); // 调用请求函数,赋值给futurePrayer
}

如果直接赋值futurePrayer = apiBaseHelper(不带括号),会把函数本身赋值给变量,而不是执行函数返回的Future,这会导致无数据展示。

4. FutureBuilder中的错误处理优化

可以在builder中更细致地处理快照状态,比如区分loading、error、success状态:

FutureBuilder<Prayer>(
  future: futurePrayer,
  builder: (context, snapshot) {
    switch (snapshot.connectionState) {
      case ConnectionState.waiting:
        return const CircularProgressIndicator();
      case ConnectionState.done:
        if (snapshot.hasData) {
          return Text(snapshot.data!.ashar);
        } else if (snapshot.hasError) {
          return Text('加载失败:${snapshot.error}');
        }
      default:
        return const Text('未知状态');
    }
  },
)

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.15 04:27:22