Как отловить SocketException с помощью библиотеки http?
На эту проблему уже указывали другие (как здесь). Хотя я мог понять причину, я все еще не нашел решения при использовании более высокого уровня http
библиотека. Например:
import 'package:http/http.dart';
// yes, pwd is String, it's just a test...
Future<Response> login(String user, String pwd) {
final authHeader = encodeBasicCredentials(user, pwd);
return get(
'http://192.168.0.100:8080/login',
headers: <String, String>{
HttpHeaders.AUTHORIZATION: authHeader,
},
));
}
Я не могу найти способ поймать SocketException
это бросается, например, если хост не может быть достигнут (в моем случае, неправильный ip хоста). Я пытался обернуть await
в try/catch
или используя Future.catchError
,
Это трассировка стека исключения:
[ERROR:topaz/lib/tonic/logging/dart_error.cc(16)] Unhandled exception:
E/flutter ( 4036): SocketException: OS Error: Connection refused, errno = 111, address = 192.168.0.100, port = 35588
E/flutter ( 4036): #0 IOClient.send (package:http/src/io_client.dart:30:23)
E/flutter ( 4036): <asynchronous suspension>
E/flutter ( 4036): #1 BaseClient._sendUnstreamed (package:http/src/base_client.dart:171:38)
E/flutter ( 4036): <asynchronous suspension>
E/flutter ( 4036): #2 BaseClient.get (package:http/src/base_client.dart:34:5)
E/flutter ( 4036): #3 get.<anonymous closure> (package:http/http.dart:47:34)
E/flutter ( 4036): #4 _withClient (package:http/http.dart:167:20)
E/flutter ( 4036): <asynchronous suspension>
E/flutter ( 4036): #5 get (package:http/http.dart:47:3)
4 ответа
Ты можешь измениться login
быть async
так что вы можете ждать ответа. Это позволяет вам перехватить исключение (и, например, вернуть null
вместо Response
).
Future<Response> login(String user, String pwd) async {
final String authHeader = encodeBasicCredentials(user, pwd);
try {
return await get(
'http://192.168.0.100:8080/login',
headers: {
HttpHeaders.AUTHORIZATION: authHeader,
},
);
} catch (e) {
print(e);
return null;
}
}
Вы можете проверить тип исключения и соответственно обработать его, например:
Future<Response> login(String user, String pwd) async {
final String authHeader = encodeBasicCredentials(user, pwd);
try {
return await get(
'http://192.168.0.100:8080/login',
headers: {
HttpHeaders.AUTHORIZATION: authHeader,
},
);
} catch (e) {
if(e is SocketException){
//treat SocketException
print("Socket exception: ${e.toString()}");
}
else if(e is TimeoutException){
//treat TimeoutException
print("Timeout exception: ${e.toString()}");
}
else print("Unhandled exception: ${e.toString()}");
}
}
Вероятно, лучше создать библиотеку обработчика ошибок, поэтому вы можете просто вызвать такую функцию, как
Один простой способ поймать ошибку — вызвать метод для метода get с использованием аргумента catch error, например, так. Этот метод метода get может перехватывать другие типы ошибок, а не только исключение сокета. Посмотрите на код ниже, чтобы узнать больше
import 'package:http/http.dart';
Future<Response> login(String user, String pwd) {
final authHeader = encodeBasicCredentials(user, pwd);
return get(
'http://192.168.0.100:8080/login',
headers: <String, String>{
HttpHeaders.AUTHORIZATION: authHeader,
},
).catchError(error){
//you can now do your error handling in this block
});
}
}