Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

PHP SOAP error catching

Tags:

php

soap

I'm getting desperate, all I want is simple error handling when the PHP SOAP Web Service is down to echo an error message login service down. Please help me!

At the moment it's still displaying the error (along with warnings...):

Fatal error: SOAP-ERROR: Parsing WSDL

Here is the script:

<?php session_start();  $login="0000000000000nhfidsj"; //It is like this for testing, It will be changed to a GET  $username = substr($login,0,13); //as password is always 13 char long                                   //(the validation is done int he javascript) $password = substr($login,13); try  {     ini_set('default_socket_timeout', 5); //So time out is 5 seconds     $client = new SoapClient("http://192.168.0.142:8080/services/Logon?wsdl"); //locally hosted      $array = $client->login(array('username'=>$username,                                    'password'=>$password));      $result = $array->return;  }catch(SoapFault $client){     $result = "0"; }  if($result == "true")//as this would be what the ws returns if login success  {     $_SESSION['user'] = $login;     echo "00"; } else {     echo "01 error: login failed"; } ?> 
like image 994
David Avatar asked Aug 05 '11 07:08

David


People also ask

How to catch Soap fault exception in PHP?

It is possible to use PHP exception mechanism to throw SOAP Fault. $server = new SoapServer(null, array('uri' => "http://test-uri/")); $server->addFunction("test"); $server->handle();

What is SoapClient PHP?

Description ¶ This is a low level API function that is used to make a SOAP call. Usually, in WSDL mode, SOAP functions can be called as methods of the SoapClient object. This method is useful in non-WSDL mode when soapaction is unknown, uri differs from the default or when sending and/or receiving SOAP Headers.

What is SOAPFault exception?

Class SOAPFaultException The SOAPFaultException exception represents a SOAP 1.1 or 1.2 fault. A SOAPFaultException wraps a SAAJ SOAPFault that manages the SOAP-specific representation of faults. The createFault method of javax. xml. soap.


2 Answers

UPDATE July 2018

If you don't care about getting the SoapFault details and just want to catch any errors coming from the SoapClient you can catch "Throwable" in PHP 7+. The original problem was that SoapClient can "Fatal Error" before it throws a SoapFault so by catching both errors and exceptions with Throwable you will have very simple error handling e.g.

try{     soap connection... }catch(Throwable $e){     echo 'sorry... our service is down'; } 

If you need to catch the SoapFault specifically, try the original answer which should allow you to suppress the fatal error that prevents the SoapFault being thrown

Original answer relevant for older PHP versions

SOAP can fatal error calling the native php functions internally which prevents the SoapFaults being thrown so we need to log and suppress those native errors.

First you need to turn on exceptions handling:

try {     $client = new SoapClient("http://192.168.0.142:8080/services/Logon?wsdl",array(        'exceptions' => true,     )); } catch ( SoapFault $e ) { // Do NOT try and catch "Exception" here     echo 'sorry... our service is down'; } 

AND THEN you also need to silently suppress any "PHP errors" that originate from SOAP using a custom error handler:

set_error_handler('handlePhpErrors'); function handlePhpErrors($errno, $errmsg, $filename, $linenum, $vars) {     if (stristr($errmsg, "SoapClient::SoapClient")) {          error_log($errmsg); // silently log error          return; // skip error handling     } } 

You will then find it now instead trips a SoapFault exception with the correct message "Soap error: SOAP-ERROR: Parsing WSDL: Couldn't load from '...'" and so you end up back in your catch statement able to handle the error more effectively.

like image 134
MeatPopsicle Avatar answered Oct 08 '22 16:10

MeatPopsicle


Fatal error: SOAP-ERROR: Parsing WSDL Means the WSDL is wrong and maybe missing? so it's not related to soap. And you cannot handle FATAL ERROR with a try catch. See this link : http://ru2.php.net/set_error_handler#35622

What do you get when you try to access http://192.168.0.142:8080/services/Logon?wsdl in your browser?

You can check if the WSDL is present like this

$handle = curl_init($url); curl_setopt($handle,  CURLOPT_RETURNTRANSFER, TRUE);  $response = curl_exec($handle); $httpCode = curl_getinfo($handle, CURLINFO_HTTP_CODE); if($httpCode == 404) {     /* You don't have a WSDL Service is down. exit the function */ }  curl_close($handle);  /* Do your stuff with SOAP here. */ 
like image 39
yokoloko Avatar answered Oct 08 '22 16:10

yokoloko