Parse json data from flask api to flutter lists

十年热恋 提交于 2020-06-29 03:43:07

问题


I'm working on a project using Flutter & Flask api. I have to grab the data from flask api and save into the lists in a flutter. I'm a beginner for Flutter just getting started, so bear with me for this, please!

Here's what I have done so far:

import 'dart:convert';

import 'package:flutter/foundation.dart';
import 'package:http/http.dart' as http;

List<String> images = [
  "assets/image_04.jpg",
  "assets/image_03.jpg",
  "assets/image_02.jpg",
  "assets/image_06.jpg",
];
List<String> title = [];

class Ayah {
  final String text;
  final String translation;
  final String sound;
  final String ref;

  Ayah({this.text, this.translation, this.sound, this.ref});

  factory Ayah.fromJson(Map<String, dynamic> json) {
    return Ayah(
        text: json['text'],
        translation: json['translation'],
        sound: json['sound'],
        ref: json['ref']);
  }
}

// A function that converts a response body into a List<Photo>.
List<Ayah> parseAyahs(String responseBody) {
  final parsed = json.decode(responseBody).cast<Map<String, dynamic>>();
  List<Ayah> mylist = parsed.map<Ayah>((json) => Ayah.fromJson(json)).toList();
  print('this is here:');
  for (int i = 0; i < parsed.length; i++) {
    print(parsed[i]);
    title.add(parsed[i]['ref']);
  }
  return mylist;
}

Future<List<Ayah>> fetchAyahs(http.Client client) async {
  final response =
      await client.get('https://jsonplaceholder.typicode.com/photos');

  // return compute(parseAyahs, response.body);
  return parseAyahs(response.body);
}

and here's the Widget where I want to use this data:

class CardScrollWidget extends StatelessWidget {
  var currentPage;
  var padding = 20.0;
  var verticalInset = 20.0;

  CardScrollWidget(this.currentPage);

  @override
  Widget build(BuildContext context) {
    return new AspectRatio(
      aspectRatio: widgetAspectRatio,
      child: LayoutBuilder(builder: (context, contraints) {
        var width = contraints.maxWidth;
        var height = contraints.maxHeight;

        var safeWidth = width - 2 * padding;
        var safeHeight = height - 2 * padding;

        var heightOfPrimaryCard = safeHeight;
        var widthOfPrimaryCard = heightOfPrimaryCard * cardAspectRatio;

        var primaryCardLeft = safeWidth - widthOfPrimaryCard;
        var horizontalInset = primaryCardLeft / 2;

        List<Widget> cardList = new List();

        for (var i = 0; i < images.length; i++) {
          var delta = i - currentPage;
          bool isOnRight = delta > 0;

          var start = padding +
              max(
                  primaryCardLeft -
                      horizontalInset * -delta * (isOnRight ? 15 : 1),
                  0.0);

          var cardItem = Positioned.directional(
            top: padding + verticalInset * max(-delta, 0.0),
            bottom: padding + verticalInset * max(-delta, 0.0),
            start: start,
            textDirection: TextDirection.rtl,
            child: ClipRRect(
              borderRadius: BorderRadius.circular(16.0),
              child: Container(
                decoration: BoxDecoration(color: Colors.white, boxShadow: [
                  BoxShadow(
                      color: Colors.black12,
                      offset: Offset(3.0, 6.0),
                      blurRadius: 10.0)
                ]),
                child: AspectRatio(
                  aspectRatio: cardAspectRatio,
                  child: Stack(
                    fit: StackFit.expand,
                    children: <Widget>[
                      Image.asset(images[i], fit: BoxFit.cover),
                      Align(
                        alignment: Alignment.bottomLeft,
                        child: Column(
                          mainAxisSize: MainAxisSize.min,
                          crossAxisAlignment: CrossAxisAlignment.start,
                          children: <Widget>[
                            Padding(
                              // padding: EdgeInsets.symmetric(
                              //     horizontal: 16.0, vertical: 18.0),
                              padding: const EdgeInsets.only(
                                  bottom: 60, left: 20, right: 8),
                              child: Text(title[i],
                                  style: TextStyle(
                                      color: Colors.white,
                                      fontSize: 25.0,
                                      fontFamily: "SF-Pro-Text-Regular")),
                            ),
                            SizedBox(
                              height: 20.0,
                            ),
                            Padding(
                              padding: const EdgeInsets.only(
                                  left: 22.0, bottom: 72.0),
                              child: Container(
                                padding: EdgeInsets.symmetric(
                                    horizontal: 22.0, vertical: 6.0),
                                decoration: BoxDecoration(
                                    color: Colors.blueAccent,
                                    borderRadius: BorderRadius.circular(20.0)),
                                child: Text("Read Later",
                                    style: TextStyle(color: Colors.white)),
                              ),
                            )
                          ],
                        ),
                      )
                    ],
                  ),
                ),
              ),
            ),
          );
          cardList.add(cardItem);
        }
        return Stack(
          children: cardList,
        );
      }),
    );
  }
}

I'm not able to get the data into the title list. The JSON response has 5 JSON objects in an array.


回答1:


MY SCENARIO

I also had similar requirement where Flutter app need to fetch data from flask backend.

  1. Backend is running in the local machine
  2. Flutter app running in external mobile app.

Main Idea

  • if we want to make HTTP requests to our API from other computers or devices connected to our LAN, we should use the development computer IP address, 0.0.0.0 (for IPv4 configurations) or :: (for IPv6 configurations) as the desired IP address for our development server.
  • If we specify 0.0.0.0 as the desired IP address for IPv4 configurations, the development server will listen on every interface on port 5000.

Steps

  1. So add a host argument for the call to app.run in the flask backend
    if __name__ == '__main__': 
         app.run(host='0.0.0.0', debug=True)
  1. Now all the devices in the local network can access it using your computer's local IP. eg : 192.168.1.101

You can check local IP with ipconfig on Windows or ifconfig on Linux/Mac

  1. Following is a sample get call from Flutter end
class MovieApiService {

  static List<Movie> parseProducts(String responseBody) {
    final parsed = json.decode(responseBody);
    print(parsed);
    return parsed.map<Movie>((json) =>Movie.fromJson(json)).toList();
  }

  static Future<List<Movie>> getMovies() async {
    final response = await http.get('http://192.168.1.101:5000/movies');
    if (response.statusCode == 200) {
      return parseProducts(response.body);
    } else {
      return null;
    }
  }

}

For additional reference : https://subscription.packtpub.com/book/application_development/9781789532227/1/ch01lvl1sec23/making-http-requests-to-the-flask-api

https://www.tutorialspoint.com/flutter/flutter_accessing_rest_api.htm



来源:https://stackoverflow.com/questions/60636328/parse-json-data-from-flask-api-to-flutter-lists

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!