【问题标题】:Error: type 'String' is not a subtype of type 'List<dynamic>'错误:“String”类型不是“List<dynamic>”类型的子类型
【发布时间】:2021-03-17 18:52:02
【问题描述】:

我想从某个 API 中获取数据并将其数据解析为模型。

我的模特:

class SetupIdeaModel {
  String id;
  String userId;
  String typeIdea = "Implemented Idea";
  String category; //Or Industry
  String experienceYear;
  String experienceMonth;
  String ideaHeadline;
  String ideaText;
  Map timeline = {
    "timelineType": "date",
    "details": null,
  };
  List documents = [];
  Map uploadVideo;
  String location;
  String estimatedPeople;
  Map whitePaper;
  bool needServiceProvider = false;
  bool needInvestor = true;
  }
}

然后我使用 getIdeaList 方法从 API 获取数据: getIdeaList 方法

Future getIdeaList(String token) async {
    Response response = await APIRequest().get(
      myUrl: "$baseUrl/innovator/idea/list",
      token: token,
    );

    //Parsing ideaList to SetupIdeaModel
    ideas = List();
    try {
      (response.data as List).forEach((element) {
        SetupIdeaModel idea = new SetupIdeaModel();
        var months = int.parse(element["industryExperienceInMonth"]);
        var year = (months / 12).floor();
        var remainderMonths = months % 12;
        print("$year year and $remainderMonths months");
        idea.id = element["_id"];
        idea.userId = element["userId"];
        idea.typeIdea = element["ideaType"];
        idea.category = element["industry"];
        idea.experienceYear = year.toString();
        idea.experienceMonth = remainderMonths.toString();
        idea.ideaHeadline = element["headline"];
        idea.ideaText = element["idea"];
        idea.estimatedPeople = element["estimatedPeople"].toString();
        print("Documents ${element["uploadDocuments"]}");
        idea.location = element["targetAudience"];
        idea.documents = element["uploadDocuments"];
        // idea.timeline = element["timeline"];
        // idea.uploadVideo = element["uploadVideo"];
        ideas.add(idea);
      });
    } catch (e) {
      print("Error: $e");
    }

    print("ideas $ideas");
    notifyListeners();
  }

一切正常,但是当我添加以下行之一时:

        idea.documents = element["uploadDocuments"];
        idea.timeline = element["timeline"];
        idea.uploadVideo = element["uploadVideo"];

我得到了错误。 API的数据是这样的:

[
   {
      "industryExperienceInMonth":30,
      "estimatedPeople":200,
      "needServiceProvider":true,
      "needInvestor":true,
      "_id":5fcc681fc5b4260011810112,
      "userId":5fb6650eacc60d0011910a9b,
      "ideaType":"Implemented Idea",
      "industry":"Technalogy",
      "headline":"IDea headline",
      "idea":"This is aobut your idea",
      "timeline":{
         "timelineType":"date",
         "details":{
            "date":Dec 6,
            2020
         }
      },
      "uploadDocuments":[
         {
            "_id":5fcc6804c5b4260011810110,
            "uriPath":"https"://webfume-onionai.s3.amazonaws.com/guest/public/document/741333-beats_by_dre-wallpaper-1366x768.jpg
         }
      ],
      "uploadVideo":{
         "_id":5fcc681ac5b4260011810111,
         "uriPath":"https"://webfume-onionai.s3.amazonaws.com/guest/public/video/588700-beats_by_dre-wallpaper-1366x768.jpg
      },
      "targetAudience":"heart",
      "__v":0
   }
]

我正在使用 Dio 包。 模型中的文档是一个列表,而来自表单 API 的 uploadDocuments 也是一个列表。但是为什么我得到这个错误。

【问题讨论】:

  • 也许将SetupIdeaModel idea = new SetupIdeaModel(); 保留在forEach 循环之外?
  • 我怀疑来自 API 的这个值 element["uploadDocuments"]String 而不是 List
  • 不要手动创建app.quicktype.io,而是转到此链接并粘贴 json 响应,选择语言作为 dart。 Model 类将为您创建它
  • 我仍然有这个问题,因为 Prasanna Kumar 说来自 API 的 element["uploadDocuments"] 是字符串而不是列表。我使用 json.encode 将字符串更改为列表,但出现另一个错误 unexpected character at index 3. [{_id: "id", uriPath"fdsfadf"}]

标签: json api flutter dart dio


【解决方案1】:

您的 JSON 数据存在一些语法错误,这就是它无法正常工作的原因。所有的 UID 和 URL 都应该是字符串格式,你应该在模型类中序列化 JSON。见also

我已经修复了您的代码中的一些错误并做了一些改进:

Future getIdeaList(String token) async {
  List<SetupIdeaModel> setupIdeaModel = List();
  try {
    Response response = await APIRequest().get(
      myUrl: "$baseUrl/innovator/idea/list",
      token: token,
    );
    if (response.statusCode == 200) {
      List<SetupIdeaModel> apiData = (json.decode(utf8.decode(response.data)) as List)
        .map((data) => new SetupIdeaModel.fromJson(data))
        .toList();
      setupIdeaModel.addAll(apiData);
    }
  } catch (e) {
    print("Error: $e");
  }
}

这是模型类:

class SetupIdeaModel {
  int industryExperienceInMonth;
  int estimatedPeople;
  bool needServiceProvider;
  bool needInvestor;
  String sId;
  String userId;
  String ideaType;
  String industry;
  String headline;
  String idea;
  Timeline timeline;
  List<UploadDocuments> uploadDocuments;
  UploadDocuments uploadVideo;
  String targetAudience;
  int iV;

  SetupIdeaModel(
      {this.industryExperienceInMonth,
      this.estimatedPeople,
      this.needServiceProvider,
      this.needInvestor,
      this.sId,
      this.userId,
      this.ideaType,
      this.industry,
      this.headline,
      this.idea,
      this.timeline,
      this.uploadDocuments,
      this.uploadVideo,
      this.targetAudience,
      this.iV});

  SetupIdeaModel.fromJson(Map<String, dynamic> json) {
    industryExperienceInMonth = json['industryExperienceInMonth'];
    estimatedPeople = json['estimatedPeople'];
    needServiceProvider = json['needServiceProvider'];
    needInvestor = json['needInvestor'];
    sId = json['_id'];
    userId = json['userId'];
    ideaType = json['ideaType'];
    industry = json['industry'];
    headline = json['headline'];
    idea = json['idea'];
    timeline = json['timeline'] != null
        ? new Timeline.fromJson(json['timeline'])
        : null;
    if (json['uploadDocuments'] != null) {
      uploadDocuments = new List<UploadDocuments>();
      json['uploadDocuments'].forEach((v) {
        uploadDocuments.add(new UploadDocuments.fromJson(v));
      });
    }
    uploadVideo = json['uploadVideo'] != null
        ? new UploadDocuments.fromJson(json['uploadVideo'])
        : null;
    targetAudience = json['targetAudience'];
    iV = json['__v'];
  }

  Map<String, dynamic> toJson() {
    final Map<String, dynamic> data = new Map<String, dynamic>();
    data['industryExperienceInMonth'] = this.industryExperienceInMonth;
    data['estimatedPeople'] = this.estimatedPeople;
    data['needServiceProvider'] = this.needServiceProvider;
    data['needInvestor'] = this.needInvestor;
    data['_id'] = this.sId;
    data['userId'] = this.userId;
    data['ideaType'] = this.ideaType;
    data['industry'] = this.industry;
    data['headline'] = this.headline;
    data['idea'] = this.idea;
    if (this.timeline != null) {
      data['timeline'] = this.timeline.toJson();
    }
    if (this.uploadDocuments != null) {
      data['uploadDocuments'] =
          this.uploadDocuments.map((v) => v.toJson()).toList();
    }
    if (this.uploadVideo != null) {
      data['uploadVideo'] = this.uploadVideo.toJson();
    }
    data['targetAudience'] = this.targetAudience;
    data['__v'] = this.iV;
    return data;
  }
}

class Timeline {
  String timelineType;
  Details details;

  Timeline({this.timelineType, this.details});

  Timeline.fromJson(Map<String, dynamic> json) {
    timelineType = json['timelineType'];
    details =
        json['details'] != null ? new Details.fromJson(json['details']) : null;
  }

  Map<String, dynamic> toJson() {
    final Map<String, dynamic> data = new Map<String, dynamic>();
    data['timelineType'] = this.timelineType;
    if (this.details != null) {
      data['details'] = this.details.toJson();
    }
    return data;
  }
}

class Details {
  String date;

  Details({this.date});

  Details.fromJson(Map<String, dynamic> json) {
    date = json['date'];
  }

  Map<String, dynamic> toJson() {
    final Map<String, dynamic> data = new Map<String, dynamic>();
    data['date'] = this.date;
    return data;
  }
}

class UploadDocuments {
  String sId;
  String uriPath;

  UploadDocuments({this.sId, this.uriPath});

  UploadDocuments.fromJson(Map<String, dynamic> json) {
    sId = json['_id'];
    uriPath = json['uriPath'];
  }

  Map<String, dynamic> toJson() {
    final Map<String, dynamic> data = new Map<String, dynamic>();
    data['_id'] = this.sId;
    data['uriPath'] = this.uriPath;
    return data;
  }
}

【讨论】:

  • 没有为类型 'Response' 定义 getter 'bodyBytes'。尝试导入定义“bodyBytes”的库,将名称更正为现有 getter 的名称,或定义名为“bodyBytes”的 getter 或字段
  • 哦,因为我使用了http包。我没看到你用的是 Dio 包。
  • Insted of response.bodyBytes 你可以使用response.data 我想。试试吧。我会更新代码。
猜你喜欢
  • 2021-04-07
  • 2021-04-13
  • 2022-12-02
  • 2019-06-26
  • 2019-01-22
  • 2021-07-01
  • 1970-01-01
  • 2022-07-22
  • 2021-12-29
相关资源
最近更新 更多