使用http包获取数据时遇类型不匹配错误:_InternalLinkedHashMap无法转为String
错误原因及解决方案
错误type '_InternalLinkedHashMap<String, dynamic>' is not a subtype of type 'String'的核心原因是:WordPress REST API返回的title和content并非直接字符串,而是包含rendered字段的嵌套对象,你的模型直接将其赋值给String类型变量导致类型不匹配。
以下是保留现有Future函数前提下的修复步骤:
1. 修正NewsModel模型类
修改fromJson构造函数,正确解析嵌套的title和content字段:
class NewsModel { late int id; late String date; late String status; late String type; late String link; late String title; late String content; NewsModel({ required this.id, required this.date, required this.status, required this.type, required this.link, required this.title, required this.content, }); NewsModel.fromJson(Map<String, dynamic> json) { id = json['id']; date = json['date']; status = json['status']; type = json['type']; link = json['link']; // 解析嵌套的title对象,取rendered字段 title = json['title']['rendered']; // 解析嵌套的content对象,取rendered字段 content = json['content']['rendered']; } Map<String, dynamic> toJson() { final Map<String, dynamic> data = <String, dynamic>{}; data['id'] = id; data['date'] = date; data['status'] = status; data['type'] = type; data['link'] = link; data['title'] = title; data['content'] = content; return data; } }
2. 修正NewsController控制器
将返回的原始JSON列表转换为List<NewsModel>,增强类型安全性:
import 'dart:convert'; import 'package:http/http.dart' as http; import 'your_model_path.dart'; // 替换为你的NewsModel文件路径 class NewsController { String url = "https://wrestlingworld.co/wp-json/wp/v2/posts?categories=22"; Future<List<NewsModel>> getNews() async { try { var response = await http.get(Uri.parse(url)); if (response.statusCode == 200) { // 将JSON数组转换为NewsModel列表 List<dynamic> jsonList = json.decode(response.body); return jsonList.map((json) => NewsModel.fromJson(json)).toList(); } else { throw Exception("请求处理错误,状态码: ${response.statusCode}"); } } catch (e) { print(e); throw Exception("控制器请求错误"); } } }
3. 修正FutureBuilder数据获取代码
使用转换后的NewsModel对象获取数据:
FutureBuilder<List<NewsModel>>( future: newsController.getNews(), builder: (context, snapShot) { if (snapShot.hasData) { return Padding( padding: const EdgeInsets.all(8.0), child: ListView.builder( scrollDirection: Axis.vertical, shrinkWrap: true, itemCount: snapShot.data?.length ?? 0, itemBuilder: (context, index) { NewsModel news = snapShot.data![index]; return NewsCard(title: news.title); }, ), ); } else if (snapShot.hasError) { return Center(child: Text("${snapShot.error}")); } else { return const Center(child: CircularProgressIndicator()); } }, )
额外说明
- WordPress REST API的文章字段中,
title、content、excerpt均为包含rendered(渲染后文本)和raw(原始文本)的对象,需根据需求取对应字段。 - 控制器中使用
throw Exception替代return Future.error,更符合Dart异步错误处理规范,同时保留了Future函数的结构。
内容的提问来源于stack exchange,提问作者sakib Ovi
相关产品推荐
相关产品推荐

