Php SoapClient: SoapFault Exception: Could not connect to host - php

I make soap requests using this Code :
try {
$S = new \SoapClient($this->wsdl);
$method = 'method';
$params = array('ID' => $Id, 'Code'=> $Code);
return $S->__call($method, $params);
}catch (\Exception $e) {
return $e->getMessage();
}
But an Exception is raised :
SoapFault exception: [HTTP] Could not connect to host
I tried to return all functions described in the WSDL for the Web service
$S = new \SoapClient($this->wsdl);
return $S->__getFunctions();
And I have all functions including my 'method' used above.
What could be the problem?

Related

PHP - SOAP "Parsing WSDL: Couldn't load from ..." Error

This is my code:
$this->options = [
"login" => $username,
"password" => $password
];
try {
$this->request = new SoapClient('https://servis.turkiye.gov.tr/services/g2g/kdgm/test/uetdsesya?wsdl', $this->options);
} catch(Exception $e) {
throw new Exception($e->getMessage());
}
And this is the error message:
Fatal error: Uncaught Exception: SOAP-ERROR: Parsing WSDL: Couldn't load from 'https://servis.turkiye.gov.tr/services/g2g/kdgm/test/uetdsesya?wsdl' : failed to load external entity "https://servis.turkiye.gov.tr/services/g2g/kdgm/test/uetdsesya?wsdl"
Any idea how I can fix this error?
[UPDATE]
I can get functions with this code:
$wsdl = file_get_contents('https://servis.turkiye.gov.tr/services/g2g/kdgm/test/uetdsesya?wsdl');
But this code still gets error:
SoapClient('https://servis.turkiye.gov.tr/services/g2g/kdgm/test/uetdsesya?wsdl', $this->options);
try from command line:
wget https://servis.turkiye.gov.tr/services/g2g/kdgm/test/uetdsesya?wsdl
or
php -r '$a = new SoapClient("https://servis.turkiye.gov.tr/services/g2g/kdgm/test/uetdsesya?wsdl"); var_dump($a);'
Maybe resource id not available from tour host
To handle SOAP exceptions, you can give this answer a try. Following code is standalone code which is returning a SOAP response.
$params = array(
"login" => "USERNAME",
"password" => "PASSWORD"
);
try {
$client = new SoapClient('https://servis.turkiye.gov.tr/services/g2g/kdgm/test/uetdsesya?wsdl', array($params));
} catch(Exception $e) {
throw new Exception($e->getMessage());
}
To List all available SOAP functions:
echo " List of available SOAP functions <br/><pre>"; var_dump($client->__getFunctions()); echo "</pre>";
To List all available SOAP types:
echo "List of SOAP types <br/><pre>"; var_dump($client->__getTypes()); echo "</pre>";
This answer has an explanation about how to access any available SOAP function.

Catch exception from guzzle

I'm using laravel and I have setup the abstract class method to get response from the various APIs I'm calling. But if the API url is unreachable then it throws an exception. I know I'm missing something. Any help would be great for me.
$offers = [];
try {
$appUrl = parse_url($this->apiUrl);
// Call Api using Guzzle
$client = new Client('' . $appUrl['scheme'] . '://' . $appUrl['host'] . '' . $appUrl['path']);
if ($appUrl['scheme'] == 'https') //If https then disable ssl certificate
$client->setDefaultOption('verify', false);
$request = $client->get('?' . $appUrl['query']);
$response = $request->send();
if ($response->getStatusCode() == 200) {
$offers = json_decode($response->getBody(), true);
}
} catch (ClientErrorResponseException $e) {
Log::info("Client error :" . $e->getResponse()->getBody(true));
} catch (ServerErrorResponseException $e) {
Log::info("Server error" . $e->getResponse()->getBody(true));
} catch (BadResponseException $e) {
Log::info("BadResponse error" . $e->getResponse()->getBody(true));
} catch (\Exception $e) {
Log::info("Err" . $e->getMessage());
}
return $offers;
you should set the guzzehttp client with option 'http_errors' => false,
the example code should be like this, document:guzzlehttp client http-error option explain
Set to false to disable throwing exceptions on an HTTP protocol errors (i.e., 4xx and 5xx responses). Exceptions are thrown by default when HTTP protocol errors are encountered.
$client->request('GET', '/status/500');
// Throws a GuzzleHttp\Exception\ServerException
$res = $client->request('GET', '/status/500', ['http_errors' => false]);
echo $res->getStatusCode();
// 500
$this->client = new Client([
'cookies' => true,
'headers' => $header_params,
'base_uri' => $this->base_url,
'http_errors' => false
]);
$response = $this->client->request('GET', '/');
if ($code = $response->getStatusCode() == 200) {
try {
// do danger dom things in here
}catch (/Exception $e){
//catch
}
}
These exceptions are not defined in guzzle officially.
These Exceptions are defined in AWS SDK for PHP.
For official Guzzle you may just do following.
use GuzzleHttp\Client;
use GuzzleHttp\Exception\RequestException;
use GuzzleHttp\Exception\ClientException;
....
try {
$response = $this->client->request($method, $url, [
'headers' => $headers,
'form_params' => $form_parameters,
]);
$body = (string)$response->getBody();
} catch (ClientException $e) {
// Do some thing here...
} catch (RequestException $e) {
// Do some thing here...
} catch (\Exception $e) {
// Do some thing here...
}
you could create your own exception
class CustomException extends Exception
{
}
next you throws your own exception from abstract class guzzle exception
catch(ConnectException $ConnectException)
{
throw new CustomException("Api excception ConnectException",1001);
}
and then handdle in in global exception handdler render methos
if($exception instanceof CustomException)
{
dd($exception);
}
Not sure how you declared those exceptions and which Guzzle version are you using but in official documentation those exceptions don't exist.
In your case you are probally missing GuzzleHttp\Exception\ConnectException.

How can I make Symfony2 ignore Guzzle Client bad response exception in my custom controller?

function order_confirmationAction($order,$token) {
$client = new \GuzzleHttp\Client();
$answer = $client->post("http://www.fullcommerce.com/rest/public/Qtyresponse",
array('body' => $order)
);
$answer = json_decode($answer);
if ($answer->status=="ACK") {
return $this->render('AcmeDapiBundle:Orders:ack.html.twig', array(
'message' => $answer->message,
));
} else throw new \Symfony\Component\HttpKernel\Exception\HttpException(500, $answer->message);
}
If $client->post() response status code is an "Error 500" Symfony stops the script execution and throw new exception before the json decoding.
How can I force Symfony to ignore $client->post() bad response and execute till the last if statement?
$client = new \GuzzleHttp\Client();
try {
$answer = $client->post("http://www.fullcommerce.com/rest/public/Qtyresponse",
array('body' => $serialized_order)
);
}
catch (\GuzzleHttp\Exception\ServerException $e) {
if ($e->hasResponse()) {
$m = $e->getResponse()->json();
throw new \Symfony\Component\HttpKernel\Exception\HttpException(500, $m['result']['message']);
}
}
I solved like this. In that way I can access to responses of remote server even if it returns an error 500 code.
Per Guzzle documentation:
Guzzle throws exceptions for errors that occur during a transfer.
Specifically, if the API responds with a 500 HTTP error, you shouldn't expect its content to be JSON, and you don't want to parse it, so you're better off re-throwing an exception from there already (or informing the user that something went wrong). I would suggest trying this out:
function order_confirmationAction($order, $token) {
$client = new \GuzzleHttp\Client();
try {
$answer = $client->post("http://www.fullcommerce.com/rest/public/Qtyresponse",
array('body' => $order)
);
}
catch (Exception $e) {
throw new \Symfony\Component\HttpKernel\Exception\HttpException(500, $e->getMessage());
}
$answer = json_decode($answer);
if ($answer->status=="ACK") {
return $this->render('AcmeDapiBundle:Orders:ack.html.twig', array(
'message' => $answer->message,
));
} else {
throw new \Symfony\Component\HttpKernel\Exception\HttpException(500, $answer->message);
}
}
It is probably also a good idea to check for errors when JSON-decoding the response, because there could be surprises in the content you're getting (eg. wrong format, missing or unexpected fields or values, etc.).

How do I handle multiple SOAP Faults during php Soap Client request?

I am interested in making a soap call via php’s soapClient to a web service to get the water level from a monitoring station. I want to handle two soapfaults that have occured during the execution. The first fault is as follows :
SoapFault exception: [soapenv:Server.userException] java.rmi.RemoteException: We are sorry, but no data is available from this station at this time in C:\xampp\htdocs\NOAA\LogWriter.php:214 Stack trace: #0 C:\xampp\htdocs\NOAA\LogWriter.php(214): SoapClient->__soapCall('getWaterLevelRa...', Array, Array) #1 C:\xampp\htdocs\NOAA\LogWriter.php(188): getLevel('8531680', '20120726 15:19') #2 {main}
This error is expected to occur several times during the script if the data for a certain time is not available. I need to catch this fault in order to tell the script to try again with a new time. I used a catch block to do so.
I also need to catch a second fault that occurs if the webservice is not loading the wsdl file or the server is timedout. To test for this have gave my script a faultly location to generate the same error I had received previously and it is as follows:
Fatal error: Uncaught SoapFault exception: [WSDL] SOAP-ERROR: Parsing WSDL: Couldn't load from 'http://opendap.co-ops.nos.noaa.gov/axis/services/WaterLevelRawOneMin?wsdl' : Extra content at the end of the document in C:\xampp\htdocs\NOAA\LogWriter.php:210 Stack trace: #0 C:\xampp\htdocs\NOAA\LogWriter.php(210): SoapClient->SoapClient('http://opendap....', Array) #1 C:\xampp\htdocs\NOAA\LogWriter.php(171): getLevel('8531680', '20120726 12:35') #2 {main} thrown in C:\xampp\htdocs\NOAA\LogWriter.php on line 210
The second error remains uncaught and terminates my script. However I need to catch it and display a message.
I have posted my php function that makes the soap call below.
Could anyone give me any ideas on how to do this?
function getLevel($id, $date) {
$client = new SoapClient("http://opendap.co-ops.nos.noaa.gov/axis/services/WaterLevelRawOneMin?wsdl", array('trace' => false));
$Parameters = array("stationId" => $id, "beginDate" => $date, "endDate" => $date, "datum" => "MLLW",
"unit" => 1, "timeZone" => 1);
try {
return $client->__soapCall(
"getWaterLevelRawOneMin", array('Parameters' => $Parameters),
array('location' => "http://opendap.co-ops.nos.noaa.gov/axis/services/WaterLevelRawOneMin")
);
} catch (SoapFault $e) {
if (
$e->faultcode == "soapenv:Server.userException"
and $e->faultstring == "java.rmi.RemoteException: We are sorry, but no data is available from this station at this time"
) {
return "FAULT";
} else {
echo "Could not connect to the server";
}
} // end of catch blocK
}// end of function
Exception regarding broken WSDL can occur only when you call SoapClient::constructor so
try {
$client= new SoapClient($wsdlUrl ,array('trace'=>false));
}catch(Exception $e) {
// your loging regarding this case
}
SoapFault exception can occur when you make a webservice all so:
try {
$client= new SoapClient($wsdlUrl ,array('trace'=>false));
try {
return $client->_call('....');
} catch (SoapFault $sp) {
//your logic rearding soap fault
}
}catch(Exception $e) {
// your loging regarding this case
}
return false;

PHP SoapClient to call a soap method with authentication

I am trying to access a webservice (JAX-WS) with wsdl using php (5.3.5). Following is the code I am using :
class insoapauth
{
public $Username;
public $Password;
public function __construct($username, $pass)
{
$this->Username = $username;
$this->Password = $pass;
}
}
$client = new SoapClient("http://192.168.124.11:8080/cx-subscriberdata/CXSubscriberAdmin?wsdl", array( "login" => "SOAPDW", "password" => "DW#2012"));
// Create the header
$auth = new insoapauth("SOAPDW", "DW#2012");
$header = new SoapHeader("http://192.168.124.11:8080/cx-subscriberdata/CXSubscriberAdmin", "APICredentials", $auth, false);
try {
$result = $client->__soapCall("getDataWS", array(
"CrmSearchInformation" => array(
"searchKeyValue" => "93700801021"
)
));
echo("<br/>Returning value of __soapCall() call: ".$result);
}catch(SoapFault $exception)
{
print_r("Got issue:<br/>") ;
var_dump($exception);
}
Alternatively I tried another way using the SoapHeader and supplying it while the method call. But I am always getting the SoapFault exception :
Could not connect to host
More details exception:
SoapFault exception: [HTTP] Could not connect to host in
C:\wamp\www\SOAPTest\client\insoaptest.php:103 Stack trace: #0
[internal function]: SoapClient->_doRequest('_soapCall('getDataWS',
Array) #2 {main}
However, using soapUI I can connect to the soapsever and can call the soapmethod with the same credentials.
Following is some example code to access the WS - I guess it's in Java- that comes with the manual:
INBeanService service = new INBeanService();
CXINWS wsPort = service.getCXINWSPort();
String username = "crmtestuser";
String password = "crmpassword";
BindingProvider bp = (BindingProvider) wsPort;
bp.getRequestContext().put(BindingProvider.USERNAME_PROPERTY, username);
bp.getRequestContext().put(BindingProvider.PASSWORD_PROPERTY, password);
try {
CrmSearchInformation crmSearchInfo = new CrmSearchInformation();
crmSearchInfo.setSearchKeyValue(msisdn);
CrmSearchResult result = wsPort.getDataWS(crmSearchInfo);
//handle result
System.out.println("Result state: " + result.getSearchResultState());
} catch (NxWsException e) {
// handle exceptions
}
Can anybody please show me some light how I can access a wsdl webservice from php with authentication ?
I have had this error before because of a cached WSDL ... try disabling the cache :
ini_set('soap.wsdl_cache_enabled',0);
ini_set('soap.wsdl_cache_ttl',0);
Docs on these settings here

Categories