一、Flutter JSON 字符串和 Map 类型的转换
import 'dart:convert'
var mapData={"name":"张三","age":"20"};
var strData='{"name":"张三","age":"20"}';
print(json.encode(mapData)); //Map 转换成 Json 字符串
print(json.decode(strData)); //Json 字符串转化成 Map 类型
二、使用 官方http 库进行网络请求
请参考官方文档:https://pub.dev/packages/http
三、Flutter Dio 库
dio 是一个强大的 Dart Http 请求库,支持 Restful API、FormData、拦截器、请
求取消、Cookie 管理、文件上传/下载、超时、自定义适配器等...
https://pub.dev/packages/dio
https://github.com/flutterchina/dio/blob/master/README-ZH.md
官方http 案例代码-----------下面有dio http 代码案例
import 'package:flutter/material.dart';
import 'package:http/http.dart' as http;
import 'dart:convert';
class HttpPage extends StatefulWidget {
HttpPage({Key key}) : super(key: key);
_HttpDemoState createState() => _HttpDemoState();
}
class _HttpDemoState extends State {
List _list=[];
@override
initState() {
// TODO: implement initState
super.initState();
this._getData();
}
_getData() async{
var apiUrl="http://a.itying.com/api/productlist";
var result=await http.get(apiUrl);
if(result.statusCode==200){
print(result.body);
setState(() {
this._list=json.decode(result.body)["result"];
});
}else{
print("失败${result.statusCode}");
}
}
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text("请求数据Demo"),
),
body: this._list.length>0?ListView(
children: this._list.map((value){
return ListTile(
title: Text(value["title"]),
);
}).toList(),
):Text("加载中...")
);
}
}
dio http 代码案例
dio: ^3.0.9
import 'dart:convert';
import 'package:flutter/material.dart';
import 'package:dio/dio.dart';
class UpDown extends StatefulWidget{
UpDown({Key key});
_UpDown createState() => _UpDown();
}
class _UpDown extends State<UpDown> {
@override
var list = [];
var page = 1;
var pageFlag = true;
var _scrollController = ScrollController();
initState() {
super.initState();
_getData();
_scrollController.addListener(() { // 上拉加载
var _scrollTop = _scrollController.position.pixels; //获取滚动条下拉的距离
var _scrollHeight = _scrollController.position.maxScrollExtent; //获取整个页面的高度
if(_scrollTop >= _scrollHeight - 20) {
_getData();
}
});
}
// 获取数据
_getData() async{
if(pageFlag == false) return;
var response = await Dio().get('http://www.phonegap100.com/appapi.php?a=getPortalList&catid=20&page=${page}');
var res = json.decode(response.data)['result'];
setState(() {
list.addAll(res);
page++;
});
if(res.length < 20) {
setState(() {
pageFlag = false;
});
}
}
// 下拉刷新
Future<void> _onRefresh() async {
await Future.delayed(
Duration(
milliseconds: 2000), () {
list = [];
page = 1;
_getData();
});
}
Widget build(BuildContext context) {
// TODO: implement build
return Scaffold(
appBar: AppBar(title: Text('上拉加载-下拉刷新'),),
body: list.length > 0 ? RefreshIndicator(
onRefresh: _onRefresh,
child: ListView.builder(
controller: _scrollController,
itemCount: list.length,
itemBuilder: (context, index) {
return Column(
children: <Widget>[
Container(
padding: EdgeInsets.only(top: 5, bottom: 5, left: 5),
alignment: Alignment.centerLeft,
child: Text('${list[index]['title']}', maxLines: 1, overflow: TextOverflow.ellipsis),
),
Divider(),
index == list.length - 1 ? getMoreTips(flag: this.pageFlag) : SizedBox()
],
);
},
),
) : getMoreTips(flag: this.pageFlag)
);
}
}
class getMoreTips extends StatelessWidget{ // 底部的转圈和文字
var flag = true;
getMoreTips({Key key, this.flag}) : super(key: key);
@override
Widget build(BuildContext context) {
// TODO: implement build
return Center(
child: flag ? Row(
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[
Text('正在加载...'),
SizedBox(width: 10),
CircularProgressIndicator(strokeWidth: 2)
],
) : Column(
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[
Text('没有更多数据了'),
SizedBox(height: 10),
],
),
);
}
}
Dio封装 带拦截器
import 'dart:convert';
import 'package:dio/dio.dart';
import 'utils.dart';
var dio = Dio();
interceptors () async{
// dio.options.contentType = 'application/json;charset=UTF-8';
// dio.options.headers = {'testHeader':'aaaa'};
var tokens = await Storage.getString('token');
dio.options.baseUrl = '';
dio.options.connectTimeout = 15000;
dio.options.receiveTimeout = 15000;
dio.interceptors.add(
InterceptorsWrapper(
onRequest: (options) async {
// print("method = ${options.method.toString()}");
// print("url = ${options.uri.toString()}");
// print("headers = ${options.headers}");
// print("params = ${options.queryParameters}");
// 此处可网络请求之前做相关配置,比如会所有请求添加token
// options.queryParameters['token'] = 'testtoken123443423';
// options.headers["token"] = "testtoken123443423";
// if (tokens == null) {
// dio.lock();
// return dio.get('/token').then((e) {
//
// options.queryParameters['token'] = e.data['data']['token'];
// Storage.setString('token', {token: e.data['data']['token']});
//
// return options;
// }).whenComplete(() => dio.unlock());
// } else {
// options.queryParameters['token'] = 'testtoken123443423';
// return options;
// }
return options;
},
onResponse: (response) {
//此处拦截工作在数据返回之后,可在此对dio请求的数据做二次封装或者转实体类等相关操作
return response;
},
onError: (error) {
//处理错误请求
return error;
}),
);
}
class DioHttp {
static const downloadUrl = 'https://dev1.mifengff.com/obhcx4';
// DioHttp.get(
// 'http://www.phonegap100.com/appapi.php?a=getPortalList',
// queryParameters: {
// 'catid': 20, 'page': page
// },
// success: (e) {
// setState(() {list.addAll(e);page++;});
// if(e.length < 20) {setState(() {pageFlag = false;});}
// });
static get (url, {queryParameters, success = '', error = '', headers = '', requests = '', statusCodes = ''}) async{
interceptors();
try{
var response = await dio.get(dio.options.baseUrl + url, queryParameters: queryParameters ?? {});
if(headers != '') {headers(response.headers);}
if(requests != '') {requests(response.request);}
if(statusCodes != '') {statusCodes(response.statusCode);}
if(response.statusCode == 200) {
var res = json.decode(response.data)['result'];
if(success != '') {success(res);}
} else {
if(error != '') {error(response);}
throw Exception('erroor: $response');
}
} catch (e) {
formatError(e);
throw Exception('erroor: $e');
}
}
static post (url, {data, success = '', error = '', headers = '', requests = '', statusCodes = '', onSendProgress}) async{
interceptors();
try{
var response = await dio.post(dio.options.baseUrl + url, data: data ?? {}, onSendProgress: onSendProgress ?? () {});
if(headers != '') {headers(response.headers);}
if(requests != '') {requests(response.request);}
if(statusCodes != '') {statusCodes(response.statusCode);}
if(response.statusCode == 200) {
var res = json.decode(response.data)['result'];
if(success != '') {success(res);}
} else {
if(error != '') {error(response);}
throw Exception('erroor: $response');
}
} catch (e) {
formatError(e);
throw Exception('erroor: $e');
}
}
static download (url, saveUrl, {success, error, onReceiveProgress}) async{
interceptors();
try{
var response = await dio.download(dio.options.baseUrl + url, saveUrl, onReceiveProgress: onReceiveProgress ?? () {});
if(response.statusCode == 200) {
var res = json.decode(response.data)['result'];
if(success != '') {success(res);}
} else {
if(error != '') {error(response);}
throw Exception('erroor: $response');
}
} catch (e) {
formatError(e);
throw Exception('erroor: $e');
}
}
static formData (url, data, {success, error}) async{
interceptors();
// var formData = FormData.fromMap({
// 'name': 'wendux',
// 'age': 25,
// });
try{
var response = await dio.post(dio.options.baseUrl + url, data: data ?? {});
if(response.statusCode == 200) {
var res = json.decode(response.data)['result'];
if(success != '') {success(res);}
} else {
if(error != '') {error(response);}
throw Exception('erroor: $response');
}
} catch (e) {
formatError(e);
throw Exception('erroor: $e');
}
}
}
// error统一处理
void formatError(DioError e) {
if (e.type == DioErrorType.CONNECT_TIMEOUT) {
print("连接超时");
} else if (e.type == DioErrorType.SEND_TIMEOUT) {
print("请求超时");
} else if (e.type == DioErrorType.RECEIVE_TIMEOUT) {
print("响应超时");
} else if (e.type == DioErrorType.RESPONSE) {
print("出现异常404 503");
} else if (e.type == DioErrorType.CANCEL) {
print("请求取消");
} else {
print("未知错误");
}
}