How to show error if server is unreachable flutter

Viewed 1302

Am still pretty new to flutter. I have a network call to be executed. But before doing that I need to check whether the device have internet connectivity and that the server is api server is reachable. I have managed to check if the internet connectivity is available, but cant show an when server is not reachable

This is what i have done so far:

 login(username, password) async {
  final String url = "http://10.0.2.2:8080/api/auth/signin"; // iOS
  var responseJson;
  try {
    final response= await http.post(
      url,
      headers: <String, String>{
        'Content-Type': 'application/json; charset=UTF-8',
      },
      body: jsonEncode(<String, String>{
        'username': username,
        'password': password,
      }),
    );
    responseJson = _response(response);
  } on SocketException {
    throw FetchDataException('No Internet connection');
  }
  print(responseJson);
  SharedPreferences prefs = await SharedPreferences.getInstance();
  var parse = jsonDecode(responseJson.body);

  await prefs.setString('username', parse["username"]);
  await prefs.setString('message', parse["message"]);
  await prefs.setString('accessToken', parse["accessToken"]);

  return responseJson;
}
  dynamic _response(http.Response response) {
    switch (response.statusCode) {
      case 200:
        var responseJson = json.decode(response.body.toString());
        print(responseJson);
        return responseJson;
      case 400:
        throw BadRequestException(response.body.toString());
      case 401:

      case 403:
        throw UnauthorisedException(response.body.toString());
      case 500:
        throw FetchDataException(
            'Error occured while Communication with Server with StatusCode : ${response
                .statusCode}');
      default:
        throw FetchDataException(
            'Error occured while Communication with Server with StatusCode : ${response
                .statusCode}');
    }
  }

My login button function

 RoundedButton(
                    text: "LOGIN",
                    press: () async {
                      if (_formKey.currentState.validate()) {
                        progressDialog.show();
                        await login(
                          username,
                          password,
                        );
                        SharedPreferences prefs =
                            await SharedPreferences.getInstance();
                        String token = prefs.getString("accessToken");
                        print(token);

                        if (token == null) {
                          progressDialog.hide();
                          showAlertsDialog(context);
                        } else {
                          showAlertzDialog(context);
                        }
                      }
                    },
                  )

Whenever I switch of the server and click on login, the app is stuck a progress bar showing signing in. How can I display an alert that there is no connection to the server?

2 Answers

This is how you can manage your API call.

Future<dynamic> requestGET({String url}) async {
try {
  final response = await http.get(Uri.parse(url));
  switch (response.statusCode) {
    case 200:
    case 201:
      final result = jsonDecode(response.body);
      final jsonResponse = {'success': true, 'response': result};
      return jsonResponse;
    case 400:
      final result = jsonDecode(response.body);
      final jsonResponse = {'success': false, 'response': result};
      return jsonResponse;
    case 401:
      final jsonResponse = {
        'success': false,
        'response': ConstantUtil.UNAUTHORIZED
      };
      return jsonResponse;
    case 500:
    case 501:
    case 502:
      final jsonResponse = {
        'success': false,
        'response': ConstantUtil.SOMETHING_WRONG
      };
      return jsonResponse;
    default:
      final jsonResponse = {
        'success': false,
        'response': ConstantUtil.SOMETHING_WRONG
      };
      return jsonResponse;
  }
} on SocketException {
  final jsonResponse = {
    'success': false,
    'response': ConstantUtil.NO_INTERNET
  };
  return jsonResponse;
} on FormatException {
  final jsonResponse = {
    'success': false,
    'response': ConstantUtil.BAD_RESPONSE
  };
  return jsonResponse;
} on HttpException {
  final jsonResponse = {
    'success': false,
    'response': ConstantUtil.SOMETHING_WRONG  //Server not responding
  };
  return jsonResponse;
 }
}

Call this function and use response I'm calling it in init method of statefulWidget.

    @override
    void initState() {
    // TODO: implement initState
    super.initState();

    final result = await requestGET('google.com');
    if (result['success'] == false) {
      // show the dialog
      showDialog(
        context: context,
        builder: (BuildContext context) {
          return AlertDialog(
            title: Text("Error"),
            content: Text(result['response']),
            actions: [
              FlatButton(
                child: Text("OK"),
                onPressed: () {
                  Navigator.pop(context);
                },
              ),
            ],
          );
          ;
        },
      );
    }
  }

I think you can check the response code from the api call using http code request from this link http status code

as you can check the response from json like this:

Future<String> checkServerResponse() await 
{
 http.Response response =
    await http.get('server_link'):
print(response.statusCode);

}

now as you can see the response code of the server based on http status code.

Related