Home > front end >  Why isn't my API data showing in a list view, when the GET request is successful?
Why isn't my API data showing in a list view, when the GET request is successful?

Time:12-26

I am working with flutter for the first time and having issues understanding why my data will not show. For context, the API returns a list of (physical) libraries and their current occupancy. I have correctly implemented an API get request, got the data outputted in the terminal (printed) and thus I know my API call is working. I also implemented the data received from the JSON as a list using my data model, and then I created a body with the library name and occupancy as a ListTile. Nothing is shown when compiled on the device screen, just a blank screen, no circular progress indicator either.

Here is my home page:

import 'package:flutter/material.dart';

import '../models/post.dart';
import '../services/remote_service.dart';

class HomePage extends StatefulWidget {
  @override
  _HomePageState createState() => _HomePageState();
}

class _HomePageState extends State<HomePage> {
  // Declare a list of Libraries
  List<Libraries> _libraries = [];

  @override
  void initState() {
    super.initState();
    // Call the getPosts function when the HomePage is initialized
    _getPosts();
  }

  // Function to make the GET request and store the response in a list of Libraries
  void _getPosts() async {
    var api = getDataAPI();
    var librariesJson = await api.getPosts();
    // Use the librariesFromJson function to convert the JSON string to a list of Libraries
    setState(() {
      _libraries = librariesFromJson(librariesJson!) as List<Libraries>;
    });
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: const Text('Library Occupancy'),
      ),
      body: _libraries == null
          ? const Center(
              child: CircularProgressIndicator(),
            )
          : ListView.builder(
              itemCount: _libraries.length,
              itemBuilder: (context, index) {
                // Display the library name and occupancy in a ListTile
                return ListTile(
                  title: Text(_libraries[index].webster.occupancy),
                  subtitle:
                      Text(_libraries[index].webster.lastRecordTime.toString()),
                );
              },
            ),
    );
  }
}

Here is my API request code (remote_service.dart):

// ignore_for_file: camel_case_types
import 'dart:convert';
import 'package:http/http.dart' as http;
import 'package:xconcordia/models/post.dart';

class getDataAPI {
  Future<String?> getPosts() async {
    var credentials = '520:276377ba5206683e51d50fb86c378dc5';
// Encode the credentials in base64 format
    var base64Credentials = base64Encode(utf8.encode(credentials));

    var headers = {'Authorization': 'Basic $base64Credentials'};

    var request = http.Request('GET',
        Uri.parse('https://opendata.concordia.ca/API/v1/library/occupancy/'));
    request.headers.addAll(headers);

    http.StreamedResponse response = await request.send();

    if (response.statusCode == 200) {
      String json = await response.stream.bytesToString();
      // ignore: await_only_futures
      Libraries library = await librariesFromJson(json);
      print("webster: "   library.webster.occupancy);
      return library.webster.occupancy;
    } else {
      print(response.statusCode);
    }
    return null;
  }
}

And finally, here is my JSON data model:

import 'dart:convert';

Libraries librariesFromJson(String str) => Libraries.fromJson(json.decode(str));
String librariesToJson(Libraries data) => json.encode(data.toJson());

class Libraries {
  Libraries({
    required this.webster,
    required this.vanier,
    required this.greyNuns,
  });

  GreyNuns webster;
  GreyNuns vanier;
  GreyNuns greyNuns;

  factory Libraries.fromJson(Map<String, dynamic> json) => Libraries(
        webster: GreyNuns.fromJson(json["Webster"]),
        vanier: GreyNuns.fromJson(json["Vanier"]),
        greyNuns: GreyNuns.fromJson(json["GreyNuns"]),
      );

  Map<String, dynamic> toJson() => {
        "Webster": webster.toJson(),
        "Vanier": vanier.toJson(),
        "GreyNuns": greyNuns.toJson(),
      };
}

class GreyNuns {
  GreyNuns({
    required this.occupancy,
    required this.lastRecordTime,
  });

  String occupancy;
  DateTime lastRecordTime;

  factory GreyNuns.fromJson(Map<String, dynamic> json) => GreyNuns(
        occupancy: json["Occupancy"],
        lastRecordTime: DateTime.parse(json["LastRecordTime"]),
      );

  Map<String, dynamic> toJson() => {
        "Occupancy": occupancy,
        "LastRecordTime": lastRecordTime.toIso8601String(),
      };
}

Also, when I run this code, here is the terminal output:

Performing hot restart...                                               
Restarted application in 302ms.
flutter: webster: .0000
[VERBOSE-2:dart_vm_initializer.cc(41)] Unhandled Exception: FormatException: Unexpected character (at character 1)
.0000
^

#0      _ChunkedJsonParser.fail (dart:convert-patch/convert_patch.dart:1383:5)
#1      _ChunkedJsonParser.parseNumber (dart:convert-patch/convert_patch.dart:1250:9)
#2      _ChunkedJsonParser.parse (dart:convert-patch/convert_patch.dart:915:22)
#3      _parseJson (dart:convert-patch/convert_patch.dart:35:10)
#4      JsonDecoder.convert (dart:convert/json.dart:612:36)
#5      JsonCodec.decode (dart:convert/json.dart:216:41)
#6      librariesFromJson (package:xconcordia/models/post.dart:3:68)
#7      _HomePageState._getPosts.<anonymous closure> (package:xconcordia/views/home_page.dart:28:20)
#8      State.setState (package:flutter/src/widgets/framework.dart:1114:30)
#9      _HomePageState._getPosts (package:xconcordia/views/home_page.dart:27:5)
<asynchronous suspension>

CodePudding user response:

Modify Your Model Class 

convert the data to  String in modal class :

  factory GreyNuns.fromJson(Map<String, dynamic> json) => GreyNuns(
        occupancy: json["Occupancy"].toString(),
        lastRecordTime: DateTime.parse(json["LastRecordTime"].toString()),
      );
  • Related