Home > Back-end >  Laravel - Correct way to catch cURL exceception
Laravel - Correct way to catch cURL exceception

Time:10-24

I am building a simple REST API package using cURL and would like to catch an error and then return a view with the error message. I want to see if the cURL response matches a string and then throw the error to a login view with the error message.

OLD WAY

try{
    $curl = curl_init();
        curl_setopt_array($curl, array(
            CURLOPT_URL => "https://" . $this->ip_address",
            CURLOPT_CONNECTTIMEOUT => 10,
            CURLOPT_CUSTOMREQUEST => "POST",
            CURLOPT_POST => true,
            CURLOPT_POSTFIELDS => "username=" . $this->username . "&password=" . $this->password,
            CURLOPT_HTTPHEADER => array(
                "cache-control: no-cache",
                "content-type: application/x-www-form-urlencoded"
            ),
        ));
    $response = curl_exec($curl);
    $error = curl_error($curl);

    if($error == 'failed to authenticate'){
        throw new \Exception("you just got an error");
    }

} catch (\Exception $e){
         return view('auth.login', $e->getMessage);
    }
}

I am able to throw an error if I dd($e) but if I try and return a view it just continues with the code after the catch function. Shouldn't PHP kill the process and just go to the login view?

UPDATED CODE USING LARAVEL HTTP CLIENT

try{    
    $response = Http::timeout(2)->asForm()->post('https://' . $this->ip_address, [
        'username' => $this->username,
        'password' => $this->password
    ]);

} catch(\Illuminate\Http\Client\ConnectionException $e) {
    return view('auth.login');
}

If I get a cURL timeout exception I just want to go back to the login page for now. If I put in a bogus IP address obviously it will timeout after 2 seconds, which is what I am testing.

Using Laravel Http client, how can I catch that error and display the auth login view?

CodePudding user response:

Could you try this please?

try {
    $response = Http::timeout(2)->asForm()->post('https://' . $this->ip_address, [
        'username' => $this->username,
        'password' => $this->password
    ]);
} catch(\Illuminate\Http\Client\ConnectionException $e) {
    return view('auth.login')->with('errorMessage', $e->getMessage());
}

And you can show the error on the frontend, like below;

@if(!empty($errorMessage))
  <div class="alert alert-danger"> {{ $errorMessage }}</div>
@endif

CodePudding user response:

Unlike Guzzle, Laravel's HttpClient does not throw errors if the response is > 400.

You should simply use an if statement to check the response status code. See: https://laravel.com/docs/8.x/http-client#error-handling

You can call use the following checks:

// Determine if the status code is >= 200 and < 300...
$response->successful();

// Determine if the status code is >= 400...
$response->failed();

// Determine if the response has a 400 level status code...
$response->clientError();

// Determine if the response has a 500 level status code...
$response->serverError();

So in your case you can simply do something like this:

$response = Http::timeout(2)->asForm()->post('https://' . $this->ip_address, [
    'username' => $this->username,
    'password' => $this->password
]);

if ($response->failed()) {
    return view('your-view')->with([
        'message' => 'Failed.',
    ]);
}
  • Related