使用 Dio 请求数据,json_serializable 解析 json 数据
可以创建 flutter 项目,也可以创建 dart 项目。因为只是数据解析,不需要用到 flutter 视图组件。
添加 Dio 依赖 https://pub.flutter-io.cn/packages/dio
name: dartlearn # 项目名字version: 0.0.1description: A sample command-line application for dartdependencies:dio: ^3.0.9 # dio 依赖#flutter packages pub run build_runner buildjson_annotation: ^3.0.1 # json 解析依赖dev_dependencies:build_runner: ^1.0.0 # json 解析依赖json_serializable: ^3.2.5 # json 解析依赖
创建 simple_demo.dart
GET 请求 https://api.apiopen.top/getJoke?page=1&count=2&type=video 接口

import 'package:dio/dio.dart';main(List<String> args) async {try {const url = "https://api.apiopen.top/getJoke?page=1&count=2&type=video";Dio dio = Dio();Response response = await dio.get(url);print(response);} catch (e) {print(e);}}
运行 dart 文件 输出

POST 请求 localhost:7000/api/v1/account/login
main(List<String> args) async {try {// const url = "https://api.apiopen.top/getJoke?page=1&count=2&type=video";// const url = 'https://api.apiopen.top/videoCategory';Dio dio = Dio();final String loginUrl = "http://localhost:7000/api/v1/account/login";Map<String, dynamic> params = Map();params["accountName"] = "李白";params["password"] = "123456";params["loginType"] = "password";Response response = await dio.post(loginUrl, queryParameters: params);print(response);} catch (e) {print(e);}}

携带 access token 获取用户信息
main(List<String> args) async {try {// const url = "https://api.apiopen.top/getJoke?page=1&count=2&type=video";// const url = 'https://api.apiopen.top/videoCategory';Dio dio = Dio();// Response response = await dio.get(url);// VideoResult videoResult = VideoResult.fromJson(response.data);// for (var item in videoResult.result.itemList) {// print(item.data.description);// }// final String loginUrl = "http://localhost:7000/api/v1/account/login";// Map<String, dynamic> params = Map();// params["accountName"] = "李白";// params["password"] = "123456";// params["loginType"] = "password";// Response response = await dio.post(loginUrl, queryParameters: params);// print(response);final String info_url = "http://localhost:7000/api/v1/user/info";dio.post(info_url, queryParameters: {"access_token": 'ade59299-5833-496b-b5ab-42a8e3a84af1'}).then((response) {AccountInfo accountInfo = AccountInfo.fromJson(response.data);print(accountInfo.data.toJson());});} catch (e) {print(e);}}

返回数据格式,可以封装一个最外层数据模型, BaseResponse, 再根据 result 返回的具体结果进行模型解析
{code: 200,message: "成功!",result: {}}
BaseResponse.dart
import 'package:json_annotation/json_annotation.dart';part 'base_response.g.dart';@JsonSerializable()class BaseResponse {// 后台返回的错误码int code;// 返回的信息String message;BaseResponse(this.code, this.message);factory BaseResponse.fromJson(Map<String, dynamic> json) =>_$BaseResponseFromJson(json);Map<String, dynamic> toJson() => _$BaseResponseToJson(this);}
数据返回数组,创建与之对应模型
JokeItemModel.dart
import 'package:json_annotation/json_annotation.dart';part 'joke_item_model.g.dart';@JsonSerializable()class JokeItemModel {/*** sid: "31577089",* text: "孩子厉害👍",* type: "video",* thumbnail: "http://wimg.spriteapp.cn/picture/2020/1026/5f967bc4e7de2_wpd.jpg",* video: "http://uvideo.spriteapp.cn/video/2020/1026/5f967bc4e7de2_wpd.mp4",* images: null,* up: "114",* down: "3",* forward: "0",* comment: "6",* uid: "23005857",* name: "无情无义",* header: "http://wimg.spriteapp.cn/profile/large/2020/02/09/5e3fc8f551f9a_mini.jpg",* top_comments_content: "厉害不厉害不知道。反正比我强",* top_comments_voiceuri: "",* top_comments_uid: "11981984",* top_comments_name: "不得姐用户",* top_comments_header: "http://qzapp.qlogo.cn/qzapp/100336987/D2C67A061C37841FD39E2D6232DE9833/100",* passtime: "2020-12-24 18:30:05"*/String sid;String text;String type;String thumbnail;String video;String images;String up;String down;String forward;String comment;String uid;String name;String header;String top_comments_content;String top_comments_voiceuri;String top_comments_uid;String top_comments_name;String top_comments_header;String passtime;JokeItemModel(this.sid,this.text,this.type,this.thumbnail,this.video,this.images,this.up,this.down,this.forward,this.comment,this.uid,this.name,this.header,this.top_comments_content,this.top_comments_voiceuri,this.top_comments_uid,this.top_comments_name,this.top_comments_header,);factory JokeItemModel.fromJson(Map<String, dynamic> json) =>_$JokeItemModelFromJson(json);Map<String, dynamic> toJson() => _$JokeItemModelToJson(this);}
解析返回 result 字段,可以创建最外层模型 JokeModel 继承 BaseResponse
JokeModel.dart
import 'package:json_annotation/json_annotation.dart';import 'base_response.dart';import 'joke_item_model.dart';part 'joke_model.g.dart';@JsonSerializable()class JokeModel extends BaseResponse {List<JokeItemModel> result;JokeModel(int code, String message) : super(code, message) {this.result = result;}factory JokeModel.fromJson(Map<String, dynamic> json) =>_$JokeModelFromJson(json);Map<String, dynamic> toJson() => _$JokeModelToJson(this);}
定义完所有模式之后,可以使用 build_runner 命令生成 json 解析模型
flutter packages pub run build_runner build


解析数据
Response response = await dio.get(url);JokeModel jokeModel = JokeModel.fromJson(response.data);for (var item in jokeModel.result) {print(item.text);}

解析复杂一些数据
https://api.apiopen.top/videoCategory

定义模型
VideoResult.dart
import 'package:json_annotation/json_annotation.dart';import 'base_response.dart';import 'video_category.dart';part 'video_result.g.dart';@JsonSerializable()class VideoResult extends BaseResponse {VideoCategory result;VideoResult(int code, String message, this.result) : super(code, message);factory VideoResult.fromJson(Map<String, dynamic> json) =>_$VideoResultFromJson(json);Map<String, dynamic> toJson() => _$VideoResultToJson(this);}
返回的 result 为一个对象模型 需要注意
VideoCategory.dart
import 'package:dartlearn/src/json_demo/video_category_item.dart';import 'package:json_annotation/json_annotation.dart';part 'video_category.g.dart';@JsonSerializable()class VideoCategory {bool adExist;int total;String nextPageUrl;int count;List<VideoCategoryItem> itemList;VideoCategory(this.adExist, this.count, this.nextPageUrl, this.total, this.itemList);factory VideoCategory.fromJson(Map<String, dynamic> json) =>_$VideoCategoryFromJson(json);Map<String, dynamic> toJson() => _$VideoCategoryToJson(this);}
itemList 字段返回集合类型,定义对象模型
VideoCategoryItem.dart
import 'package:dartlearn/src/json_demo/category_item.dart';import 'package:json_annotation/json_annotation.dart';part 'video_category_item.g.dart';@JsonSerializable()class VideoCategoryItem {int adIndex;dynamic tag;int id;String type;CategoryItem data;VideoCategoryItem(this.adIndex, this.tag, this.id, this.type);factory VideoCategoryItem.fromJson(Map<String, dynamic> json) =>_$VideoCategoryItemFromJson(json);Map<String, dynamic> toJson() => _$VideoCategoryItemToJson(this);}
VideoCategoryItem data 为对象类型
CategoryItem.dart
import 'package:json_annotation/json_annotation.dart';import 'package:dartlearn/src/json_demo/follow_item.dart';part 'category_item.g.dart';@JsonSerializable()class CategoryItem {bool ifShowNotificationIcon;bool expert;String dataType;String icon;String actionUrl;String description;String title;int uid;String subTitle;String iconType;bool ifPgc;int id;String adTrack;FollowItem follow;CategoryItem(this.actionUrl,this.adTrack,this.dataType,this.description,this.expert,this.icon,this.iconType,this.id,this.ifPgc,this.ifShowNotificationIcon,this.subTitle,this.title,this.uid,this.follow);factory CategoryItem.fromJson(Map<String, dynamic> json) =>_$CategoryItemFromJson(json);Map<String, dynamic> toJson() => _$CategoryItemToJson(this);}
follow 字段为一个对象
FollowItem.dart
import 'package:json_annotation/json_annotation.dart';part 'follow_item.g.dart';@JsonSerializable()class FollowItem {int itemId;String itemType;bool followed;FollowItem(this.followed, this.itemId, this.itemType);factory FollowItem.fromJson(Map<String, dynamic> json) =>_$FollowItemFromJson(json);Map<String, dynamic> toJson() => _$FollowItemToJson(this);}
执行 flutter packages pub run build_runner build,生成 *.g.dart 文件。
XXXXFromJson 为 JsonSerializableGenerator 生成器生成的方法
使用
main(List<String> args) async {try {// const url = "https://api.apiopen.top/getJoke?page=1&count=2&type=video";const url = 'https://api.apiopen.top/videoCategory';Dio dio = Dio();Response response = await dio.get(url);VideoResult videoResult = VideoResult.fromJson(response.data);for (var item in videoResult.result.itemList) {print(item.data.description);}} catch (e) {print(e);}}

