A value of type 'List<Data>?' can't be assigned to a variable of type 'List<Data>'

230

Solution 1

The meaning of List? means that this list can be null.

But List means that this list can not be null, but could be empty as [];

Solutions: Make List be List? This will make your List nullable, and you will have to refactor your code anywhere where it is used to perform null checks. For this, edit your builder method line to this:

List<Data>? data = snapshot.data;

I'd not recommend this though, because you shall have to perform manual nullity checks in your code, which is not that beautiful

Check for nullity of List? I'd recommend using this, you have to change your builder method to this for null checking..

List<Data> data = snapshot.data ?? <Data>[];

What this code means is it will try snapshot.data, if it returns null, it will assign <Data>[] to the data array. Making it an empty array.

This is more easy to deal with(based on my views) than a nullable array!

Solution 2

This error can be solved by updating your code like this,

List<Data> data = snapshot.data ?? <Data>[];

or like this,

List<Data> data = snapshot.data!;

Solution 3

snapshot.data could be null, you already know it is not null because of this line

if (snapshot.hasData)

But dart doesn't know that yet... To let it know, you can use the ! operator after data

List<Data> data = snapshot.data!;
Share:
230
Artur Uvarov
Author by

Artur Uvarov

Updated on December 30, 2022

Comments

  • Artur Uvarov
    Artur Uvarov over 1 year

    I'm trying to fetch data in Flutter from test API using this tutorial - https://flutterforyou.com/how-to-fetch-data-from-api-and-show-in-flutter-listview/

    When I copy the code VS Code throws this error, and I do not understand, what I need to do enter image description here

    Thank for your responses, and sorry in advance for dummy question, code example

        Future <List<Data>> fetchData() async {
      
      final response =
          await http.get(Uri.parse('https://jsonplaceholder.typicode.com/albums'));
      if (response.statusCode == 200) {
        List jsonResponse = json.decode(response.body);
          return jsonResponse.map((data) => Data.fromJson(data)).toList();
      } else {
        throw Exception('Unexpected error occured!');
      }
    }
    
    class Data {
      final int userId;
      final int id;
      final String title;
    
      Data({required this.userId, required this.id, required this.title});
    
      factory Data.fromJson(Map<String, dynamic> json) {
        return Data(
          userId: json['userId'],
          id: json['id'],
          title: json['title'],
        );
      }
    }
    class _MyAppState extends State<MyApp> {
      late Future <List<Data>> futureData;
    
      @override
      void initState() {
        super.initState();
        futureData = fetchData();
      }
    
      @override
      Widget build(BuildContext context) {
        return MaterialApp(
          title: 'Flutter API and ListView Example',
          home: Scaffold(
            appBar: AppBar(
              title: Text('Flutter ListView'),
            ),
            body: Center(
              child: FutureBuilder <List<Data>>(
                future: futureData,
                builder: (context, snapshot) {
                  if (snapshot.hasData) {
                    List<Data> data = snapshot.data;
                    return 
                    ListView.builder(
                    itemCount: data.length,
                    itemBuilder: (BuildContext context, int index) {
                      return Container(
                        height: 75,
                        color: Colors.white,
                        child: Center(child: Text(data[index].title),
                      ),);
                    }
                  );
                  } else if (snapshot.hasError) {
                    return Text("${snapshot.error}");
                  }
                  // By default show a loading spinner.
                  return CircularProgressIndicator();
                },
              ),
            ),
          ),
        );
      }
    }
    
    • Yashraj
      Yashraj over 2 years
      Change this : List<Data>? data = snapshot.data;
  • emanuel sanga
    emanuel sanga over 2 years
    since it might return null, wont null be data in snapshot.hasData?
  • h8moss
    h8moss over 2 years
    @emanuelsanga Sorry, not sure I understand your question, snapshot.hasData will only be true if snapshot.data is not null, even if the future is completed.
  • emanuel sanga
    emanuel sanga over 2 years
    I get this, what am asking is, will flutter not treat null as data, given that the function passed can be nullable?
  • Artur Uvarov
    Artur Uvarov over 2 years
    Thank you, it helped! But I have one more question I tried tutorial to get an access to API on this link - filehost.feelsoftware.com/jsonplaceholder/cars-api.php I changed my code to this class Data { ... factory Data.fromJson(Map<String, dynamic> json) { return Data( number: json['cars']['number'], date: json['cars']['date'], state: json['cars']['state'], ); } } it throws _internallinkhashmap<string, dynamic> is not a subtype of List<dynamic>
  • emanuel sanga
    emanuel sanga over 2 years
    if you have telegram, ping me with t.me/lightema, I will be able to help you there more
  • h8moss
    h8moss over 2 years
    no, as you can see in the documentation data will never be null as long as snapshot.hasData is true, even if the future is completed and the function is nullable
  • emanuel sanga
    emanuel sanga over 2 years
    thanks for that @hmoss, I missed something there