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

Flutter解析JSON时抛出‘type 'Null' is not a subtype of type 'String'’异常排查

问题描述

在Flutter中尝试获取用户列表接口数据并格式化JSON时,抛出异常:type 'Null' is not a subtype of type 'String'。

以下是相关代码:

user_model.dart

class User {
  int    id;
  String email;
  String firstName;
  String lastName;
  String avator;
  User({
    required this.id,
    required this.email,
    required this.firstName,
    required this.lastName,
    required this.avator
  });

  factory User.fromJson(Map<String, dynamic> json) => User(
    id        : json['id'],
    email     : json['email'],
    firstName : json['first_name'],
    lastName  : json['last_name'],
    avator    : json['avator']
  );
}

user_api.dart

...
class UserApi {
  Future<List<User>?> getUsers() async {
    final url = Uri.parse('https://reqres.in/api/users?page=2');
    try {
      final res = await http.get(url);
      if (res.statusCode == 200) {
        final Map<String, dynamic> body  = jsonDecode(res.body);
        final List<User> users = body['data'].map((dynamic userData) => {
          print('userData : $userData');
          User.fromJson(userData) // There seems to be an error here.
        }).toList();
        return users;
      } else {
        return null;
      }
    } catch (e) {
      print(e.toString());
    }
    return null;
  }
}

控制台输出的userData内容:

flutter: userData : {id: 7, email: michael.lawson@reqres.in, first_name: Michael, last_name: Lawson, avatar: https://reqres.in/img/faces/7-image.jpg}

明明userData不为Null,为何会触发该异常?


问题原因及解决方案

1. 字段名拼写错误(核心原因)

观察控制台输出的userData,头像字段的键是avatar,但你的User模型类中字段名写成了avator,并且在fromJson方法中尝试获取json['avator']——这个键在返回的JSON中不存在,所以会返回null。而你的User类中avator是required的非空String类型,将null赋值给非空字符串就会触发type 'Null' is not a subtype of type 'String'异常。

2. Map转换语法错误

在body['data'].map(...)中,你使用了大括号{}包裹代码,这会让闭包返回一个Map对象而非User实例,导致后续toList()得到的是List<Map>而非List<User>,同样会引发类型错误。


修正后的代码

修正后的user_model.dart

class User {
  int id;
  String email;
  String firstName;
  String lastName;
  String avatar; // 修正字段名拼写
  User({
    required this.id,
    required this.email,
    required this.firstName,
    required this.lastName,
    required this.avatar // 修正构造函数参数
  });

  factory User.fromJson(Map<String, dynamic> json) => User(
        id: json['id'],
        email: json['email'],
        firstName: json['first_name'],
        lastName: json['last_name'],
        avatar: json['avatar'] // 修正JSON键名
      );
}

修正后的user_api.dart

...
class UserApi {
  Future<List<User>?> getUsers() async {
    final url = Uri.parse('https://reqres.in/api/users?page=2');
    try {
      final res = await http.get(url);
      if (res.statusCode == 200) {
        final Map<String, dynamic> body = jsonDecode(res.body);
        // 去掉大括号,指定泛型<User>确保类型安全
        final List<User> users = body['data'].map<User>((dynamic userData) => 
          User.fromJson(userData)
        ).toList();
        return users;
      } else {
        return null;
      }
    } catch (e) {
      print(e.toString());
    }
    return null;
  }
}

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.02 08:45:21