Sunday, November 4, 2018

Flutter - Parse local JSON file in Flutter.

To make a big mobile application, we always need API's to get dynamic JSON data from the server. JSON is text-based, human-readable data interchange format that is used for representing simple data structures and objects. By using text-based JSON, we can create a list of objects in mobile and web application.

Flutter local json parse
But sometimes in the mobile applications, we have to put JSON file in the application package rather than get it from the server. In the mobile application, we can put it in anywhere in the application directory as per platform guideline. Such as in Android and Flutter, we can put a JSON file in the assets folder and parse it on runtime to get the data and use it accordingly.
In this post, we'll create a Flutter application and see how to parse a JSON locally within our app. The final output of app looks like below:
  
Flutter local json parse



Let's dive into Flutter app development with the help of following steps.


Creating a new Project
1. Create a new project from File ⇒ New Flutter Project with your development IDE.

2. Create a assets folder in the root directory of the project and put country.json in the assets folder. To access this file in the Flutter application, we have to declare it in the pubspecs.yaml file. As we have did:

3. After that, create a list.dart file. In this file, we'll pass a list of countries array as a param and displaying it in the build method by using the listview.
list.dart
import 'package:flutter/foundation.dart'; import 'package:flutter/material.dart'; import 'package:flutter_load_local_json/country.dart'; class CountyList extends StatelessWidget { final List<Country> country; CountyList({Key key, this.country}) : super(key: key); @override Widget build(BuildContext context) { return new ListView.builder( itemCount: country == null ? 0 : country.length, itemBuilder: (BuildContext context, int index) { return new Card( child: new Container( child: new Center( child: new Column( // Stretch the cards in horizontal axis crossAxisAlignment: CrossAxisAlignment.stretch, children: <Widget>[ new Text( // Read the name field value and set it in the Text widget country[index].name, // set some style to text style: new TextStyle( fontSize: 20.0, color: Colors.lightBlueAccent), ), new Text( // Read the name field value and set it in the Text widget "Capital:- " + country[index].capital, // set some style to text style: new TextStyle( fontSize: 20.0, color: Colors.amber), ), ], )), padding: const EdgeInsets.all(15.0), ), ); }); } }
4. Now, create a PODO model country.dart file. It'll represent a country detail that we used to parse JSON.
country.dart
class Country { final String name; final String flag; final String capital; Country({this.name, this.flag, this.capital}); factory Country.fromJson(Map<String, dynamic> json) { return new Country( name: json['name'] as String, flag: json['flag'] as String, capital: json['capital'] as String, ); } }
5. At the end, open main.dart file and write main logic to get JSON from assets folder and parse it for display. As you can see below, to get json from the assets folder, we using the DefaultAssetBundle widget.
 future: DefaultAssetBundle.of(context)
                    .loadString('assets/country.json'),
in the builder param snapshot.data.toString() represent a string of JSON. We pass it to parseJson() method for parse it.
 List<Country> countries =
                      parseJson(snapshot.data.toString());
the parseJson() method make a list of countries.
List<Country> parseJosn(String response) {
    if(response==null){
      return [];
    }
    final parsed =
        json.decode(response.toString()).cast<Map<String, dynamic>>();
    return parsed.map<Country>((json) => new Country.fromJson(json)).toList();
  }
Here, you can see the complete main.dart file. Now merge all above snippet and run the app.
main.dart
import 'dart:convert'; import 'package:flutter/material.dart'; import 'package:flutter_load_local_json/country.dart'; import 'package:flutter_load_local_json/list.dart'; void main() { runApp(new MaterialApp( debugShowCheckedModeBanner: false, theme: new ThemeData( primaryColor: const Color(0xFF02BB9F), primaryColorDark: const Color(0xFF167F67), accentColor: const Color(0xFF167F67), ), home: new MyApp(), )); } class MyApp extends StatefulWidget { @override MyAppState createState() => new MyAppState(); } class MyAppState extends State<MyApp> { List data; @override Widget build(BuildContext context) { return new Scaffold( appBar: new AppBar( title: new Text("Load local JSON file", style: new TextStyle(color: Colors.white),), ), body: new Container( child: new Center( // Use future builder and DefaultAssetBundle to load the local JSON file child: new FutureBuilder( future: DefaultAssetBundle.of(context) .loadString('assets/country.json'), builder: (context, snapshot) { List<Country> countries = parseJosn(snapshot.data.toString()); return !countries.isEmpty ? new CountyList(country: countries) : new Center(child: new CircularProgressIndicator()); }), ), )); } List<Country> parseJosn(String response) { if(response==null){ return []; } final parsed = json.decode(response.toString()).cast<Map<String, dynamic>>(); return parsed.map<Country>((json) => new Country.fromJson(json)).toList(); } }
If you have followed the article carefully, you can see the app running very smoothly as shown in the above. The raw JSON displaying a list of countries. But if you are facing any problem and have quires, please feel free to ask it from below comment section and you can ask it on SLACK.
Share:

8 comments:

  1. Hi, thank you for the article, it's really helpful to understand the logic of this process which is rather hard for beginners.
    But Flutter shows 1 informal message in the console saying for this line "return !albums.isEmpty" that:
    "Use `isNotEmpty` for Iterables and Maps."
    Anyway the App builds and works fine. What does this message mean? :) When I change it to the suggested line there is infinity CircularProgressIndicator displayed :)
    I also found a small recommendation to replace this line:
    itemCount: country == null ? 0 : country.length,

    with this one:
    itemCount: country.length ?? 0,

    "Instead of the ternary operator, you can use null - aware operators".

    Thank you for any feedback. :)

    ReplyDelete
    Replies
    1. Warning is saying, you should use "return albums.isNotEmpty" instead of "return !albums.isEmpty" and manage your CircularProgressIndicator accordingly.

      Delete
  2. the methode 'cast' was called on null

    ReplyDelete
  3. People keep using 'POJO' in posts about Dart. POJO is a Java object.

    ReplyDelete
  4. can we save response in json file?

    ReplyDelete
  5. can we save response in json file?

    ReplyDelete
  6. the njson var in the parseJson method is'nt defined

    ReplyDelete

We're Social

Categories

Ad here

  • Cover art Blend

    Blend app is very advanced app there are lots of features like shayari, status, chat, feed....