user14932408
user14932408

Reputation:

How to parse json from the api in flutter?

I want to parse JSON from the link in Flutter. Here is my api structure.

Here is the model.dart class which is generated using jsontodart.com.

Here is the services.dart class:

import 'dart:convert';
import 'package:get_api/model.dart';
import 'package:http/http.dart' as http;

class Services {
  //
  static const String url = 'http://...............';
  static Future<List<User>> getUsers() async {
    try {
      final response = await http.get(url);
      if (response.statusCode == 200) {
        final body = jsonDecode(response.body);
        //print(body);
        final Iterable json = body;
        return json.map((user) => User.fromJson(user)).toList();
      } else {
        return List<User>();
      }
    } catch (e) {
      return List<User>();
    }
  }
}

Here is main.dart


import 'package:flutter/material.dart';
import 'package:get_api/model.dart';
import 'package:get_api/services.dart';

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

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      debugShowCheckedModeBanner: false,
      home: JsonParseDemo(),
    );
  }
}

class JsonParseDemo extends StatefulWidget {
  //
  JsonParseDemo() : super();
  @override
  _JsonParseDemoState createState() => _JsonParseDemoState();
}

class _JsonParseDemoState extends State<JsonParseDemo> {
  //
  List<User> _users;
  bool _loading;
  @override
  void initState() {
    super.initState();
    _loading = true;
    Services.getUsers().then((users) {
      setState(() {
        _users = users;
        _loading = false;
      });
    });
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: Text(_loading ? 'Loading...' : 'Users'),
      ),
      body: Container(
        color: Colors.white,
        child: ListView.builder(
          itemCount: _users == null ? 0 : _users.length,
          itemBuilder: (context, index) {
            User user = _users[index];
            return ListTile(
              title: Text(user.clientInfos[index].cLINTNAME),
              subtitle: Text(user.clientInfos[index].cLINTEMAIL),
            );
          },
        ),
      ),
    );
  }
}

But the problem is that it only shows one list. How can I show all the list? I don't understand why it is not working.

Upvotes: 1

Views: 219

Answers (2)

danypata
danypata

Reputation: 10175

Your problem is how you compute the index for the list. In your JSON you have an array with length of 1, that is your user, now this user has 57 clientInfos that you're using. I assume you want to display those, so you should have something like this:

@override
  Widget build(BuildContext context) {
    User user;
    if(_users != null && _users.length > 0) {
       user = _users[index];
    }
    return Scaffold(
      appBar: AppBar(
        title: Text(_loading ? 'Loading...' : 'Users'),
      ),
      body: Container(
        color: Colors.white,
        child: ListView.builder(
          itemCount: user?.clientInfos?.length ?? 0,
          itemBuilder: (context, index) {
            return ListTile(
              title: Text(user.clientInfos[index].cLINTNAME),
              subtitle: Text(user.clientInfos[index].cLINTEMAIL),
            );
          },
        ),
      ),
    );
  }

Upvotes: 0

I've modified some files and created a new file, here my code:

model.dart

class User {
...

  String show() {
    if (success) {
      return '''
"clientInfos" has ${clientInfos.length} items 
"projectInfos" has ${projectInfos.length} items 
"ticketPriorityInfos" has ${ticketPriorityInfos.length} items 
"ticketTypeInfos" has ${ticketTypeInfos.length} items 
"ticketModeInfos" has ${ticketModeInfos.length} items 
"ticketStatusInfos" has ${ticketStatusInfos.length} items 
"ticketTitleInfos" has ${ticketTitleInfos.length} items 
''';
    } else {
      return "Nothing to show, what a pity!!!";
    }
  }
}

net_service.dart

import 'dart:convert';

import 'package:http/http.dart' as http;
import 'package:read_json2/models/model.dart';


class NetService {
  static Future fetchJsonData(String url) {
    return
      http.get(url)
        .then((response) => response?.statusCode == 200 ? jsonDecode(response.body) : null)
        .catchError((err) => print(err));
  }

  static Future<User> fetchTickesInfo() {
    return fetchJsonData('http://203.130.133.166/ATI-ERP2/ticket-lookup')
      .then((response) => (response != null) ? User.fromJson(response[0]) : null)
      .catchError((err) => print('OMFG!!! an error: $err'));
  }
}

home_page.dart

EDIT: forgot list items, but it is solved

import 'package:flutter/material.dart';
import 'package:read_json2/models/model.dart';
import 'package:read_json2/services/net_service.dart';


class HomePage extends StatelessWidget {
  /* ---------------------------------------------------------------------------- */
  const HomePage({Key key}) : super(key: key);
  /* ---------------------------------------------------------------------------- */
  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: Text('Hi!'),
        centerTitle: true,
      ),
      body: FutureBuilder<User>(
        future: NetService.fetchTickesInfo(),
        builder: (context, snapshot) => snapshot.hasData
          ? ListView.builder(
            itemCount: snapshot.data.clientInfos.length,
            itemBuilder: (context, index) => Card(
              child: Column(
                children: [
                  Text(snapshot.data.clientInfos[index]?.cLINTNAME ?? '--'),
                  Text(snapshot.data.clientInfos[index]?.cLINTEMAIL ?? '--'),
                ],
              ),
            ),
          )
          : snapshot.hasError
            ? Text('Something was wrong!: ${snapshot.error}')
            : Text('Loading...'),
      ),
    );
  }
}

Upvotes: 1

Related Questions