al246
al246

Reputation: 230

How to take XML data from API and extract data list from it

I am calling an API that returns XML data

I have a Class for the data to take the part of the data that I need.

The API returns the instances fine but I am having trouble extracting the data List I need to then call a function (Which is tested and works) to place a map marker.

I need to take the lat, long from the returned list vehicleactivity and use it

This is the Class

import 'package:xml/xml.dart';

class VehicleActivity {
  VehicleActivity({
    this.recordedAtTime,
    this.itemIdentifier,
    this.validUntilTime,
    this.longitude,
    this.latitude,
  });

  DateTime? recordedAtTime;
  String? itemIdentifier;
  DateTime? validUntilTime;
  double? longitude;
  double? latitude;

  factory VehicleActivity.fromElement(XmlElement vaElement) => VehicleActivity(
        recordedAtTime: DateTime.parse(
          vaElement.findElements('RecordedAtTime').first.text,
        ),
        itemIdentifier: vaElement.findElements('ItemIdentifier').first.text,
        validUntilTime: DateTime.parse(
          vaElement.findElements('ValidUntilTime').first.text,
        ),
        longitude: 
            double.tryParse(vaElement.findAllElements('Longitude').first.text),

        latitude:
            double.tryParse(vaElement.findAllElements('Latitude').first.text),
      );
}

I am calling it with this API fetch

   Future <VehicleActivity?> fetchLiveLocations() async {
    var client = http.Client();
    VehicleActivity? vehicleActivity;
    

    
  try{
    var response = await client.get(Uri.parse(
      'https_call'));   
    if (response.statusCode == 200) {

  final doc = XmlDocument.parse(utf8.decode(response.bodyBytes));
  final vehicleActivity = doc
      .findAllElements('VehicleActivity')
      .map((e) => VehicleActivity.fromElement(e))
      .toList();
  print(vehicleActivity);

  }
 } catch(e) {

  print("Exception Happened: ${e.toString()}");
}
return vehicleActivity; 
}

To then plot the marker I use this function, this is where the issue is.

Future<void> showMapMarkers() async {
    _unTiltMap();

    var vehicleActivity = await fetchLiveLocations();
  for (VehicleActivity vehicleActivity in vehicleActivity!) {
    GeoCoordinates geoCoordinates = GeoCoordinates (vehicleActivity.latitude, vehicleActivity.latitude);
    

    _addMapMarker(geoCoordinates, 1);
  
  }
}

This is the issue

     The type 'VehicleActivity' used in the 'for' loop must implement Iterable.

On this line

    for (VehicleActivity vehicleActivity in vehicleActivity!) {

update - Function to plot not recognising (I use a for method for my Json, this could be the issue but have tried other options)

        Future<void> showMapMarkers() async {
    _unTiltMap();

    var vehicleActivity = await fetchLiveLocations();
  for (VehicleActivity vehicleActivity in vehicleActivity!) {
    GeoCoordinates geoCoordinates = GeoCoordinates (vehicleActivity.latitude, vehicleActivity.latitude);
    

    _addMapMarker(geoCoordinates, 1);
  
  }
}

Upvotes: 0

Views: 786

Answers (1)

Richard Heap
Richard Heap

Reputation: 51732

To handle the issues in the comments:

  1. It should actually be returning a list (note the toList())
  2. It should return something (not null - at least for now) on exception or non-200

Rewrite this method as:

Future<List<VehicleActivity>> fetchLiveLocations() async {
  var client = http.Client();

  try {
    var response = await client.get(Uri.parse('https_call'));
    if (response.statusCode == 200) {
      final doc = XmlDocument.parse(utf8.decode(response.bodyBytes));
      return doc
          .findAllElements('VehicleActivity')
          .map((e) => VehicleActivity.fromElement(e))
          .toList();
    } else {
      // todo - fix later - for now return empty list
      return <VehicleActivity>[];
    }
  } catch (e) {
    print('Exception Happened: ${e.toString()}');
    // todo - fix later - for now return empty list
    return <VehicleActivity>[];
  }
}

Upvotes: 2

Related Questions