我设置超时时间时未处理的套接字异常,没有互联网连接

时间:2019-07-24 12:27:12

标签: flutter dart unhandled-exception socketexception timeoutexception

我使用简单的方法从互联网“ http get request”中获取一些数据:

     `Future<UserModel> getUser(int userId) async {
       UserModel user;
       try {
            final response = await http.get(
             "$_baseUrl/users/$userId",
           )
             .timeout(Duration(seconds: 5))

            ;
         user = userModelFromJson(response.body);
       return user;
      } on TimeoutException catch (e) {
       print('$e in authentication service');
     throw e;
      } on SocketException catch (e) {
     print('$e in authentication service');
     throw e;
     } catch (e) {
     print('$e in authentication service');
    throw e;
      }
      }` 

但是当我没有互联网连接时,它会向我显示该错误:

 `Exception has occurred.
    SocketException (SocketException: Failed host lookup: 
    'jsonplaceholder.typicode.com' (OS Error: No address associated with 
    hostname, errno = 7))`

每当我删除.timeout(Duration(seconds:5))时,代码都会正常运行, 但是在很长时间(15-20)秒后捕获了套接字异常,以表明没有互联网连接,这就是我使用超时的原因,我尝试使用多个程序包(http middleware,http helper,retry),我尝试使用http .client并在“ finally”块中将其关闭,并且发生了相同的错误,并且应用程序崩溃了

the image shows the error when the socket exception is thrown and unhandled

它按预期捕获了超时异常,但是又过了10-15秒,它抛出了一个已处理的套接字异常,为什么会抛出该套接字异常,我该怎么做才能避免这种情况?

2 个答案:

答案 0 :(得分:0)

您应该考虑使用HTTP软件包https://pub.dev/packages/http 因为它有助于清理代码并有助于错误处理。

下面是使用GET请求的示例:

await http.get(url).then((response) async {
 // DO SOMETHING HERE
});

response.body是您的数据。 response.statusCode是您的http状态代码(200、404、500等)

https://en.wikipedia.org/wiki/List_of_HTTP_status_codes

这是带有数据的帖子请求:

var data = {
      "dataset1": {
        "key1": "value",
        "key2": "value",
      },
    };
await http.post(url,
  body: jsonEncode(data),
  headers: {'content-type': 'application/json'}).then((response) async {
    // DO SOMETHING HERE
});

答案 1 :(得分:0)

如果要使用http包实现超时,请按以下步骤操作:

import 'dart:io';

import 'package:http/http.dart' as http;
import 'package:http/io_client.dart' as http;

Future<void> login(String email, String password) async {
    final ioClient = HttpClient();
    client.connectionTimeout = const Duration(seconds: 5);
    final body = { 'email': email, 'password': password };
    final client = http.IOClient(ioClient);
    http.Response res;
    try {
      res = await client
        .post(
          '$url/login',
          headers: {'Content-Type': 'application/json'},
          body: jsonEncode(body));
    } on SocketException catch (e) {
      // Display an alert, no internet
    } catch (err) {
      print(err);
      return null;
    }

    // Do something with the response...
}