type list dynamic is not a subtype of type map string dynamic

Issue

This is show type list dynamic is not a subtype of type map string dynamic" Now when i run emulator is show "type list dynamic is not a subtype of type map string dynamic" on my emulator how can i fix it ?

Now i want to create program about find api id form my emulator use text field and button when i put some number and click button is will show data or title of that ID , but I’m just beginner so if anyone thing my code is correct or not or you have some recommend pls tell me
My JSON

import 'dart:async';
import 'dart:convert';
import 'package:flutter/material.dart';
import 'package:http/http.dart' as http;

Future<Album> fetchAlbum() async {
  final response =
  await http.get(Uri.parse('http://192.168.176.131:3000/api/courses/'));

  if (response.statusCode == 200) {
    // If the server did return a 200 OK response,
    // then parse the JSON.
    return Album.fromJson(jsonDecode(response.body));

  } else {
    // If the server did not return a 200 OK response,
    // then throw an exception1
    throw Exception('Failed to load album');
  }
}

class Album {
  final int userId;
  final int id;
  final String title;

  Album({
    required this.userId,
    required this.id,
    required this.title,
  });

  factory Album.fromJson(Map<String, dynamic> json) {
    return Album(
      userId: json['userId'],
      id: json['id'],
      title: json['title'],
    );
  }
}

void main() => runApp(MyApp());

class MyApp extends StatefulWidget {
  MyApp({Key? key}) : super(key: key);


  @override
  _MyAppState createState() => _MyAppState();
}

class _MyAppState extends State<MyApp> {
  late Future<Album> futureAlbum;

  @override
  void initState() {
    super.initState();
    futureAlbum = fetchAlbum();
  }

  Widget build(BuildContext context) {
    TextEditingController searchController = new TextEditingController();
    return MaterialApp(
      title: 'Fetch Data Example',
      theme: ThemeData(
        primarySwatch: Colors.blue,
      ),
      home: Scaffold(
          appBar: AppBar(
            title: Text('Fetch Data Example'),
          ),

          body: Column(children: [
            Container(
                child: Row(children: [
                  Expanded(
                      flex: 2,
                      child: TextField(
                          controller: searchController
                      )
                  ),
                  Expanded(
                      flex: 1,
                      child: FlatButton(
                        onPressed: () {
                          print(
                              "this is the text to search for => ${searchController
                                  .text}");
                        },
                        child: Text("Search"),
                      )
                  )
                ],)
            ),
            Center(
              child: FutureBuilder<Album>(
                future: futureAlbum,
                builder: (context, snapshot) {
                  if (snapshot.hasData) {
                    return Text(snapshot.data!.title);
                  } else if (snapshot.hasError) {
                    return Text("${snapshot.error}");
                  }
                  // By default, show a loading spinner.
                  return CircularProgressIndicator();
                },
              ),
            ),
          ],)

      ),
    );
  }
}

JSON Code

const Joi = require('joi');
const express = require('express');
const app = express();

app.use(express.json());

const courses = [
    { userId:1, id:1, title:'course 1'},
    { userId:2, id:2, title:'course 2'},
    { userId:3, id:3, title:'course 3'},
]; 

app.get('/', (req,res)  => {
    res.send('Hello world');

});

app.get('/api/courses',(req, res) => {
    res.send(courses);
});

app.post('/api/courses', (req, res) => {   
    const { error }  = validateCourse(req.body);
    if (error)return res.status(400).send(error.details[0].message);


    const course = {
        id: courses.length +1,
        name: req.body.name
    };
    courses.push(course);
    res.send(course);
});

app.put('/api/courses/:id', (req, res) => {
    const course = courses.find(c => c.id === parseInt(req.params.id));
    if (!course) return res.status(404).send('The course with the given ID was not found.');

    const {error} = validateCourse(req.body); //result.eror
    if (error) return res.status(400).send(error.details[0].message);
        
    
    //Update course
    course.name = req.body.name;
    res.send(course);
    //Return the updated course

});



app.delete('/api/courses/:id', (req, res) => {
    const course = courses.find(c => c.id === parseInt(req.params.id));
    if (!course) return res.status(404).send('The course with the given ID was not found.');

    const index = courses.indexOf(course);
    courses.splice(index, 1);
    res.send(course);
});
function validateCourse(course){
    const schema = {
        name: Joi.string().min(3).required()
    };

    return Joi.validate(course, schema);
}

app.get(‘/api/courses/:id’, (req, res) => {
const course = courses.find(c => c.id === parseInt(req.params.id));
if (!course) return res.status(404).send(‘The course with the given ID was not found.’);
res.send(course);
});

const port = process.env.PORT || 3000;
//app.listen(port, () => console.log(Listening on port ${port} ..));
app.listen(3000, ‘0.0.0.0’);

Solution

You should cast the returned value from the jsonDecode to a Map <String, dynamic>.
jsonDecode returns a dynamic value, not a Map <String, dynamic> as the Album.fromJson expects.

Answered By – Ricardo Parra

Answer Checked By – Willingham (FlutterFixes Volunteer)

Leave a Reply

Your email address will not be published. Required fields are marked *