Dart - 类型“String”不是类型“Iterable<dynamic>”的子类型

Nad*_*eid 5 json dart flutter

我正在尝试在 dart 中解析本地 JSON 文件并显示其值。

用户.json

[
    {
        "id": 1,
        "name": "Greg",
        "imageUrl": "assets/images/greg.jpg"
    },
    {
        "id": 2,
        "name": "James",
        "imageUrl": "assets/images/james.jpg"
    }
]
Run Code Online (Sandbox Code Playgroud)

这是我的 chats.json

[
    {
        "sender": "james",
        "time": "5:30 PM",
        "text": "Hey, how's it going? What did you do today?",
        "isLiked": false,
        "unread": true
    },
    {
        "sender": "olivia",
        "time": "4:30 PM",
        "text": "Hey, how's it going? What did you do today?",
        "isLiked": true,
        "unread": false
    }
]
Run Code Online (Sandbox Code Playgroud)

这是我的消息类

class Message {
  final User sender;
  final String time;
  final String text;
  final bool isLiked;
  final bool unread;

  Message({
    this.sender,
    this.time,
    this.text,
    this.isLiked,
    this.unread,
  });

  factory Message.fromJson(Map<String, dynamic> parsedJson){
    return Message(
      sender: User.fromJson(parsedJson['sender']),
      time : parsedJson['time'],
      text : parsedJson ['text'],
      isLiked : parsedJson['isLiked'],
      unread : parsedJson ['unread'],      
    );
  }

  static List<User> parseUsers(usersJson) {
    List<User> usersList = new List<User>.from(usersJson);
    return usersList;
  }
}
Run Code Online (Sandbox Code Playgroud)

这是我的用户类别

class User {
  final int id;
  final String name;
  final String imageUrl;

  User({
    this.id,
    this.name,
    this.imageUrl,
  });

  factory User.fromJson(Map<String, dynamic> parsedJson){
    return User(
      id: parsedJson['id'],
      name : parsedJson['name'],
      imageUrl : parsedJson ['imageUrl']
    );
  }

}
Run Code Online (Sandbox Code Playgroud)

这是我的latest_chat.dart(它是StatefulWidget)

List<Message> _messages = List<Message>();

  Future<String> _loadChatsAsset() async {
    return await rootBundle.loadString('assets/json/chats.json');
  }

  Future<List<Message>> loadChats() async {
    String jsonString = await _loadChatsAsset();
    var messages = List<Message>();
    final messagesJson = json.decode(jsonString);
    for (var messageJson in messagesJson){
      messages.add(Message.fromJson(messageJson));
    }
    return messages;
  }

  @override
  void initState() {
    loadChats().then((value) {
      setState(() {
        _messages.addAll(value);
      });
    });
    super.initState();
  }
Run Code Online (Sandbox Code Playgroud)

要从 JSON 打印一些内容,我通常会执行 _messages[index].sender.name 或 _messages[index].text 等...

上述解析方法无需嵌套对象即可工作(仅适用于用户)。使用嵌套对象(消息内的用户),我无法识别以下错误的来源。

类型“String”不是类型“Iterable”的子类型

它发生在这行代码上

列表 usersList = new List.from(userJson);

我不确定我错过了什么。你能帮忙吗?提前致谢

Vir*_*iya 2

从 json 中可以看出,您只获取字符串作为发送者,但是当您创建 Message 对象时,User 类需要三个参数。

意味着,作为 json 中的发送者,应该有一个用户对象。

{
   "id" : 1
    "name" : "Viren"
    "imageUrl" : 'someurl'
}
Run Code Online (Sandbox Code Playgroud)

您的 json 和您想要的输出不匹配。

此外,您的以下行也是错误的。

  sender: parseUsers(parsedJson['sender']),
Run Code Online (Sandbox Code Playgroud)

改成这样。

 sender: User.fromJson(parsedJson['sender'])
Run Code Online (Sandbox Code Playgroud)

更新:

你的 json 应该如下所示。

[
    {
        "sender": {
            "id": 1,
            "name": "Greg",
            "imageUrl": "assets/images/greg.jpg"
        },
        "time": "5:30 PM",
        "text": "Hey, how's it going? What did you do today?",
        "isLiked": false,
        "unread": true
    },
    {
        "sender": {
            "id": 2,
            "name": "James",
            "imageUrl": "assets/images/james.jpg"
        },
        "time": "4:30 PM",
        "text": "Hey, how's it going? What did you do today?",
        "isLiked": true,
        "unread": false
    }
]
Run Code Online (Sandbox Code Playgroud)