Flutter转换API JSON报错:'Null'非'Map<String,dynamic>'子类型
解决Flutter中JSON转Dart对象的"Null is not a subtype of Map<String,dynamic>"错误
这个错误的核心是你在尝试将null值当作Map<String,dynamic>类型解析,通常是网络请求返回null、解析前未判空,或是API返回格式不符合预期导致的。以下是针对性的解决步骤:
1. 修复网络请求类的返回逻辑
检查你的Network请求方法,确保请求失败或无数据时不会直接返回null,避免后续解析出错:
错误示例(可能返回null)
Future<Map<String, dynamic>?> fetchTweet() async { final response = await http.get(Uri.parse('your_api_url')); if (response.statusCode == 200) { return json.decode(response.body); } else { return null; // 这里返回null会导致后续解析崩溃 } }
修正方案
- 方案一:请求失败时抛出异常,让上层处理
Future<Map<String, dynamic>> fetchTweet() async { final response = await http.get(Uri.parse('your_api_url')); if (response.statusCode == 200) { return json.decode(response.body); } else { throw Exception('请求失败,状态码:${response.statusCode}'); } }
- 方案二:兜底返回空Map(适合无需抛出异常的场景)
Future<Map<String, dynamic>> fetchTweet() async { final response = await http.get(Uri.parse('your_api_url')); if (response.statusCode == 200) { return json.decode(response.body) ?? {}; } else { return {}; } }
2. 完善数据模型类的解析逻辑
给CleanTweets的fromJson方法添加空值处理,避免传入null时崩溃:
修正后的模型类示例
class CleanTweets { final String? id; final String? text; // 其他字段 CleanTweets({this.id, this.text}); factory CleanTweets.fromJson(Map<String, dynamic>? json) { json ??= {}; // 若json为null,用空Map兜底 return CleanTweets( id: json['id'] ?? '', // 给每个字段设置默认值 text: json['text'] ?? '无内容', ); } }
3. 主页面中添加空值判断
在使用请求数据时,必须先判断数据是否为null,再进行解析。以FutureBuilder为例:
FutureBuilder<Map<String, dynamic>>( future: fetchTweet(), builder: (context, snapshot) { if (snapshot.connectionState == ConnectionState.waiting) { return const CircularProgressIndicator(); } else if (snapshot.hasError) { return Text('加载失败:${snapshot.error}'); } else if (!snapshot.hasData || snapshot.data!.isEmpty) { return const Text('暂无数据'); } else { final tweet = CleanTweets.fromJson(snapshot.data!); return Column( children: [ Text('ID: ${tweet.id}'), Text('内容: ${tweet.text}'), ], ); } }, )
4. 验证API返回格式
确认API确实返回单个JSON对象(而非数组或其他格式),正确格式示例:
{ "id": "12345", "text": "这是一条测试推文", "author": "测试用户" }
若API返回的是数组(如[ {...} ]),则需改为用List<CleanTweets>解析,否则会触发类型不匹配错误。
内容的提问来源于stack exchange,提问作者Faiz Hassan
相关产品推荐
相关产品推荐

