扑朔迷离地解析JSON数据

时间:2020-05-11 23:33:05

标签: flutter

在扑朔迷离地解析JSON数据时出现错误,

我使用了这个API

https://api.covid19api.com/summary

并使用此网站创建JSON类

https://javiercbk.github.io/json_to_dart/

和这段代码来解析JSON数据

Future<List<ListCountries>> _getUsers() async {

var data = await http.get("https://api.covid19api.com/summary");
var jsonData = json.decode(data.body);
if (data.statusCode == 200 ) { 

  jsonData.forEach((element) {
    countries.add(ListCountries.fromJson(element));
  });

  return countries;
  }

但是它不起作用,您能帮我吗?

这是所有代码: https://github.com/faress123/json/blob/master/json

3 个答案:

答案 0 :(得分:1)

首先,在确定没有错误之后,应该解码json,这意味着您应该在if var jsonData = json.decode(data.body);下替换(data.statusCode == 200 )


您的jsonData不是List,它是Map,国家/地区列表位于其中,键为countries。因此,您无需在那里使用forEach


您的_getUsers函数应该是这样;

Future<ListCountries> _getUsers() async {    
  var data = await http.get("https://api.covid19api.com/summary");

  if (data.statusCode == 200 ) { 
    var jsonData = json.decode(data.body);    

    return ListCountries.fromJson(jsonData);
  } else {
    return null;
  }
}

您的FutureBuilder应该是这样;

FutureBuilder<ListCountries>(
  future: _getUser(),
  builder: (BuildContext context, AsyncSnapshot asyncSnapshot) {
    if (asyncSnapshot.hasData) {
      return ListView.builder(
        itemCount: asyncSnapshot.data.countries.length,
        itemBuilder: (BuildContext context, int index) {
          return Card(
            color: Colors.white70,
            child: ListTile(
              title: Text(
                "${asyncSnapshot.data.countries[index].country} ",
                style: TextStyle(
                  fontSize: SizeConfig.heightMultiplier * 3,
                ),
              ),
              /* leading: Image.network(
                "https://www.countryflags.io/${asyncSnapshot.data.countries[index].country}/shiny/64.png",
              ), */
              subtitle: Text(
                "he is with driver ${asyncSnapshot.data.countries[index].todayDeaths}",
                style: TextStyle(
                  fontSize: SizeConfig.textMultiplier * 2.0,
                ),
              ),
              onTap: () {
                Navigator.pushReplacement(
                  context,
                  MaterialPageRoute(
                    builder: (context) => TheCasess(
                      asyncSnapshot.data.countries[index].iSO2,
                    ),
                  ),
                );
              },
            ),
          );
        },
      );
    }
    return Center(child: CircularProgressIndicator());
  },
)

答案 1 :(得分:0)

您可以在下面复制粘贴运行完整代码
您可以在完整代码中看到类定义
您可以使用payloadFromJson

解析json字符串

代码段

Future<Payload> _getUsers() async {
    var data = await http.get("https://api.covid19api.com/summary");
    //var jsonData = json.decode(data.body);
    if (data.statusCode == 200) {
      Payload payload = payloadFromJson(data.body);

      return payload;
    }
  }

工作演示

enter image description here

完整代码

import 'package:flutter/material.dart';
import 'package:http/http.dart' as http;
import 'dart:convert';

class List_sammry extends StatefulWidget {
  @override
  _List_sammryState createState() => _List_sammryState();
}

class _List_sammryState extends State<List_sammry> {
  Future<Payload> _future;
  //List<ListCountries> countries = [];
  bool isempty;

  void initState() {
    // TODO: implement initState
    super.initState();
    initial();
  }

  void initial() async {
    _future = _getUsers();
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
        body: FutureBuilder(
            future: _future,
            builder:
                (BuildContext context, AsyncSnapshot<Payload> asyncSnapshot) {
              switch (asyncSnapshot.connectionState) {
                case ConnectionState.none:
                  return Text('none');
                case ConnectionState.waiting:
                  return Center(child: CircularProgressIndicator());
                case ConnectionState.active:
                  return Text('');
                case ConnectionState.done:
                  if (asyncSnapshot.hasError) {
                    return Text(
                      '${asyncSnapshot.error}',
                      style: TextStyle(color: Colors.red),
                    );
                  } else {
                    return ListView.builder(
                        itemCount: asyncSnapshot.data.countries.length,
                        itemBuilder: (BuildContext context, int index) {
                          return Card(
                            color: Colors.white70,
                            child: ListTile(
                              title: Text(
                                "${asyncSnapshot.data.countries[index].country} ",
                                //    style: TextStyle(fontSize: 1.0 * 3)
                              ),
                              /*                      leading: Image.network(
                              "https://www.countryflags.io/${asyncSnapshot.data[index].country}/shiny/64.png",
                            ),*/
                              subtitle: Text(
                                "he is with driver ${asyncSnapshot.data.countries[index].totalDeaths}",
                                //style: TextStyle(fontSize: 1.0 * 2.0)
                              ),
                              onTap: () {
                                /*Navigator.pushReplacement(
                                context,
                                MaterialPageRoute(
                                    builder: (context) =>
                                        TheCasess(
                                            asyncSnapshot.data[index].iSO2)));*/
                                print("ok");
                              },
                            ),
                          );
                        });
                  }
              }
            }));
  }

  Future<Payload> _getUsers() async {
    var data = await http.get("https://api.covid19api.com/summary");
    //var jsonData = json.decode(data.body);
    if (data.statusCode == 200) {
      Payload payload = payloadFromJson(data.body);

      return payload;
    }
  }
}

Payload payloadFromJson(String str) => Payload.fromJson(json.decode(str));

String payloadToJson(Payload data) => json.encode(data.toJson());

class Payload {
  Global global;
  List<Country> countries;
  DateTime date;

  Payload({
    this.global,
    this.countries,
    this.date,
  });

  factory Payload.fromJson(Map<String, dynamic> json) => Payload(
        global: Global.fromJson(json["Global"]),
        countries: List<Country>.from(
            json["Countries"].map((x) => Country.fromJson(x))),
        date: DateTime.parse(json["Date"]),
      );

  Map<String, dynamic> toJson() => {
        "Global": global.toJson(),
        "Countries": List<dynamic>.from(countries.map((x) => x.toJson())),
        "Date": date.toIso8601String(),
      };
}

class Country {
  String country;
  String countryCode;
  String slug;
  int newConfirmed;
  int totalConfirmed;
  int newDeaths;
  int totalDeaths;
  int newRecovered;
  int totalRecovered;
  DateTime date;

  Country({
    this.country,
    this.countryCode,
    this.slug,
    this.newConfirmed,
    this.totalConfirmed,
    this.newDeaths,
    this.totalDeaths,
    this.newRecovered,
    this.totalRecovered,
    this.date,
  });

  factory Country.fromJson(Map<String, dynamic> json) => Country(
        country: json["Country"],
        countryCode: json["CountryCode"],
        slug: json["Slug"],
        newConfirmed: json["NewConfirmed"],
        totalConfirmed: json["TotalConfirmed"],
        newDeaths: json["NewDeaths"],
        totalDeaths: json["TotalDeaths"],
        newRecovered: json["NewRecovered"],
        totalRecovered: json["TotalRecovered"],
        date: DateTime.parse(json["Date"]),
      );

  Map<String, dynamic> toJson() => {
        "Country": country,
        "CountryCode": countryCode,
        "Slug": slug,
        "NewConfirmed": newConfirmed,
        "TotalConfirmed": totalConfirmed,
        "NewDeaths": newDeaths,
        "TotalDeaths": totalDeaths,
        "NewRecovered": newRecovered,
        "TotalRecovered": totalRecovered,
        "Date": date.toIso8601String(),
      };
}

class Global {
  int newConfirmed;
  int totalConfirmed;
  int newDeaths;
  int totalDeaths;
  int newRecovered;
  int totalRecovered;

  Global({
    this.newConfirmed,
    this.totalConfirmed,
    this.newDeaths,
    this.totalDeaths,
    this.newRecovered,
    this.totalRecovered,
  });

  factory Global.fromJson(Map<String, dynamic> json) => Global(
        newConfirmed: json["NewConfirmed"],
        totalConfirmed: json["TotalConfirmed"],
        newDeaths: json["NewDeaths"],
        totalDeaths: json["TotalDeaths"],
        newRecovered: json["NewRecovered"],
        totalRecovered: json["TotalRecovered"],
      );

  Map<String, dynamic> toJson() => {
        "NewConfirmed": newConfirmed,
        "TotalConfirmed": totalConfirmed,
        "NewDeaths": newDeaths,
        "TotalDeaths": totalDeaths,
        "NewRecovered": newRecovered,
        "TotalRecovered": totalRecovered,
      };
}

void main() {
  runApp(MyApp());
}

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      title: 'Flutter Demo',
      theme: ThemeData(
        primarySwatch: Colors.blue,
        visualDensity: VisualDensity.adaptivePlatformDensity,
      ),
      home: List_sammry(),
    );
  }
}

答案 2 :(得分:0)

我建议使用以下网页:quick_type将json字符串转换为对象模型类。选择语言为dart并粘贴您的json字符串。就这么简单。