Flutter解析API返回JSON时出现transform类型不匹配错误如何解决
错误产生原因
- 核心原因是
json.decode()返回值为dynamic类型,你直接调用.map()方法时,Dart运行时阶段如果推断该值为Map类型,就会触发Map的map方法,该方法要求入参是(String, dynamic) => MapEntry类型的函数,而你传入的是(dynamic) => Product类型的转换函数,类型不匹配就抛出了该错误。即便你接口返回的是数组,没有显式强转的情况下也可能触发类型推断异常。 - 模型类存在字段不匹配问题:
Product类中diet字段声明为非空required String,但你在fromJson方法中允许赋值为null,同时部分JSON返回中没有diet字段,会触发空安全报错。 - 嵌套列表转换未做类型强转:
dishes和offerIds字段的转换同样直接对dynamic类型的值调用.map(),也存在同类潜在报错风险。
解决方案
第一步:修正模型类的空安全声明和转换逻辑
首先把Product类的diet字段改为可空类型,同时所有列表转换前先显式强转为List<dynamic>:
// 修正productFromJson方法,先强转成List再map List<Product> productFromJson(String str) => List<Product>.from( (json.decode(str) as List<dynamic>).map((x) => Product.fromJson(x)) ); String productToJson(List<Product> data) => json.encode(List<dynamic>.from(data.map((x) => x.toJson()))); class Product { Product({ required this.id, required this.name, required this.image, required this.description, required this.isFavourite, required this.dishes, this.diet, // 改为可选可空字段 }); String id; String name; String image; String description; bool isFavourite; List<Dish> dishes; String? diet; // 改为可空类型 factory Product.fromJson(Map<String, dynamic> json) => Product( id: json["_id"], name: json["name"], image: json["image"], description: json["description"], isFavourite: json["isFavourite"], // 先把dishes强转为List<dynamic>再map dishes: List<Dish>.from((json["dishes"] as List<dynamic>).map((x) => Dish.fromJson(x))), diet: json["diet"], ); Map<String, dynamic> toJson() => { "_id": id, "name": name, "image": image, "description": description, "isFavourite": isFavourite, "dishes": List<dynamic>.from(dishes.map((x) => x.toJson())), "diet": diet, }; } class Dish { Dish({ required this.name, required this.price, required this.offerIds, required this.id, }); String name; double price; List<dynamic> offerIds; String id; factory Dish.fromJson(Map<String, dynamic> json) => Dish( name: json["name"], price: double.parse(json["price"].toString()), // 强转offerIds为List<dynamic> offerIds: List<dynamic>.from((json["offerIds"] as List<dynamic>).map((x) => x)), id: json["_id"], ); Map<String, dynamic> toJson() => { "name": name, "price": price, "offerIds": List<dynamic>.from(offerIds.map((x) => x)), "_id": id, }; }
第二步:可选优化(异常拦截)
可以在API请求中增加类型判断,避免接口返回结构变化导致崩溃:
if (response.statusCode == 200) { final dynamic jsonData = json.decode(response.body); if (jsonData is List) { final List<Product> specials = productFromJson(response.body); _specialsList = specials; } else { _specialsList = []; debugPrint("接口返回结构非预期数组类型"); } }
内容的提问来源于stack exchange,提问作者stryker
相关产品推荐
相关产品推荐

