dio的简单使用
dio
一个适合Dart的强大的Http Client,它支持拦截器,全局配置,FormData,请求取消,文件下载,超时等。
Sample Use
pubspec.yaml 导入
dependencies:
dio: ^3.0.10
import 'package:dio/dio.dart';
void getHttp() async {
try {
Response response = await Dio().get("http://www.google.com");
print(response);
} catch (e) {
print(e);
}
}
下面是简单用法,来自dio 官方使用:
Get
Response response;
Dio dio = new Dio();
response = await dio.get("/test?id=12&name=wendu");
print(response.data.toString());
// Optionally the request above could also be done as
response = await dio.get("/test", queryParameters: {"id": 12, "name": "wendu"});
print(response.data.toString());
Post
response = await dio.post("/test", data: {"id": 12, "name": "wendu"});
Multiple Concurrent Requests
执行多个并发请求
response = await Future.wait([dio.post("/info"), dio.get("/token")]);
下载文件:
response = await dio.download("https://www.google.com/", "./xx.html");
Get response stream:
Response<ResponseBody> rs = await Dio().get<ResponseBody>(url,
options: Options(responseType: ResponseType.stream), // set responseType to `stream`
);
print(rs.data.stream); //response stream
Get response with bytes:
Response<List<int>> rs = await Dio().get<List<int>>(url,
options: Options(responseType: ResponseType.bytes), // // set responseType to `bytes`
);
print(rs.data); // List<int>
Sending FormData:
FormData formData = new FormData.fromMap({
"name": "wendux",
"age": 25,
});
response = await dio.post("/info", data: formData);
Uploading multiple files to server by FormData:
FormData.fromMap({
"name": "wendux",
"age": 25,
"file": await MultipartFile.fromFile("./text.txt",filename: "upload.txt"),
"files": [
await MultipartFile.fromFile("./text1.txt", filename: "text1.txt"),
await MultipartFile.fromFile("./text2.txt", filename: "text2.txt"),
]
});
response = await dio.post("/info", data: formData);
Listening the uploading progress:
response = await dio.post(
"http://www.dtworkroom.com/doris/1/2.0.0/test",
data: {"aa": "bb" * 22},
onSendProgress: (int sent, int total) {
print("$sent $total");
},
);
Post binary data by Stream:
// Binary data
List<int> postData = <int>[...];
await dio.post(
url,
data: Stream.fromIterable(postData.map((e) => [e])), //create a Stream<List<int>>
options: Options(
headers: {
Headers.contentLengthHeader: postData.length, // set content-length
},
),
);
还有Dio APIs,Request Options ,Response Schema,Interceptors #,Cookie Manager
我比较懒,就不CV了,
简单封装:
class HttpHelper {
static final HttpHelper _instance = HttpHelper._internal();
static HttpHelper get instance => _instance;
// Use the factory keyword when implementing a constructor that doesn’t always create a new instance of its class.
// For example, a factory constructor might return an instance from a cache, or it might return an instance of a subtype.
factory HttpHelper() {
return _instance;
}
HttpHelper._internal() {
if (dio == null) {
var options = BaseOptions(
connectTimeout: 15000,
receiveTimeout: 15000,
responseType: ResponseType.plain,
/* validateStatus: (status) {
// 不使用http状态码判断状态,使用AdapterInterceptor来处理(适用于标准REST风格)
return true;
},*/
baseUrl: host,
);
dio = Dio(options);
}
} //private constructor
Dio dio;
Dio baseDio() {
return dio;
}
static const String host = "https://xxxx";
Future getHttp(String url) async {
try {
Response response = await dio.get(url);
if (response.statusCode == HttpStatus.ok) {
print(response.data);
print("success:$response");
return jsonDecode(response.data);
}
} on DioError catch (e) {
if (e.response != null) {
print(e.response.data);
print(e.response.headers);
print(e.response.request);
} else {
// Something happened in setting up or sending the request that triggered an Error
print(e.request);
print(e.message);
}
}
}
Future postHttp(String url, Map<String, dynamic> map) async {
try {
Response response = await dio.post(url, queryParameters: map);
print(response);
} catch (e) {
print(e);
}
}
Future<Response> postForm(String url, Map<String, dynamic> map) async {
FormData formData = new FormData.fromMap(map);
Response response = await dio.post(url, data: formData);
return response;
}
Future<T> request<T>(String url,
{String method = "get",
Map<String, dynamic> map,
Options options,
Function(String error) onError}) async {
var option = options;
if (option != null) {
option.method = method;
} else {
option = Options(method: method);
}
try {
Response response =
await dio.request(url, queryParameters: map, options: option);
return jsonDecode(response.data.toString());
// return jsonDecode(response.data.toString());
} on DioError catch (e) {
String msg = HandleError.getFinalException(e);
onError(msg);
//Future.error(e) 无返回
// return Future.error(e);
return null;
}
}
}
class HandleError {
static String getFinalException(DioError dioError) {
print("HandleError DioError: $dioError");
switch (dioError.type) {
case DioErrorType.CANCEL:
return "Request Cancel";
case DioErrorType.CONNECT_TIMEOUT:
return "CONNECT TIMEOUT";
case DioErrorType.SEND_TIMEOUT:
return 'Send Time Out';
case DioErrorType.RESPONSE:
return "Server Incorrect Status";
case DioErrorType.RECEIVE_TIMEOUT:
return "Receive Time Out";
case DioErrorType.DEFAULT:
String msg = 'UnKnown';
Log.v("Handle Error DEFAULT", dioError.error);
if (dioError.error != null) {
if (dioError.error is SocketException) {
msg = "网络连接异常";
} else {
msg = dioError.message;
}
}
return msg;
}
return "UnKnown";
}
}
使用:
Future<dynamic> getLoginInfo(String url,String account, String password,
{Function onError}) async {
Map map = {};
map["user_name"] = account;
map["pass"] = password;
print(map);
var loginData = await HttpHelper.instance
.request(url, method: "post", map: map, onError: onError);
// print(loginData);
print(TAG + "$loginData");
return loginData;
}