Domanda

Sto scrivendo un'app Web che consentirà all'utente di specificare un URL per un SoapClient. Volevo confermare che php può connettersi al client quando l'utente invia un modulo. Potrei farlo tramite try catch o set_error_handler (o una combinazione dei due). Tuttavia sembra che questo non sia possibile per errori fatali. C'è un modo per convincere SoapClent a testare un URL che non genererà un errore irreversibile?

Fatal error: SOAP-ERROR: Parsing WSDL: Couldn't load from 'http://example.com/wibble'

Voglio che contrassegni un errore poiché l'URL non esiste, ma vorrei essere in grado di rilevarlo.

Altrimenti suppongo di poter provare a scaricare e convalidare l'URL da solo, ma avrei pensato che sarebbe stato possibile farlo da SoapClient.

Questo dovrebbe essere un errore fatale?

Modifica

Dopo aver letto la risposta di rogeriopvl, ribadisco che avrei dovuto dire che avevo provato l'opzione "eccezioni" al costruttore soapclient e (nella disperazione) la funzione use-soap-error-handler.

È stato utile?

Soluzione

Stai usando xdebug? Secondo questa segnalazione e discussione sui bug di PHP , il problema è stato risolto almeno da PHP 5.1, ma questo bug xdebug fa un errore con "errore fatale nelle conversioni di eccezione" in un modo in cui l'eccezione non viene generata e l'errore fatale "perde".

Posso riprodurlo localmente, con xdebug abilitato:

try {
  $soapClient = new SoapClient('http://www.example.com');
}
catch(Exception $e) {
  $exceptionMessage = t($e->getMessage());
  print_r($exceptionMessage);
}

Questo mi dà l'errore fatale che hai descritto, senza nemmeno inserire la clausola catch:

Fatal error: SOAP-ERROR: Parsing WSDL: Couldn't load from 'http://www.example.com'

Funziona se disabilito xdebug subito prima della chiamata:

xdebug_disable();
try {
  $soapClient = new SoapClient('http://www.example.com');
}
catch(Exception $e) {
  $exceptionMessage = t($e->getMessage());
  print_r($exceptionMessage);
}

Questo innesca l'eccezione come previsto e ottengo un oggetto SoapFault corretto nella clausola catch con un messaggio di:

SOAP-ERROR: Parsing WSDL: Couldn't load from 'http://www.example.com'

Quindi, in sostanza, le eccezioni funzionano come pubblicizzato. Se non funzionano nel tuo caso, potresti riscontrare il bug xdebug o un problema simile con un altro componente di terze parti.

Altri suggerimenti

Citando Documentazione SoapClient :

  

L'opzione eccezioni è un valore booleano che definisce se gli errori soap generano eccezioni di tipo SoapFault.

Quindi dovresti provare qualcosa del tipo:

$client = new SoapClient("some.wsdl", array('exceptions' => TRUE));

In questo modo verranno generate SoapFault consentendoti di catturarli .

Vedi: http://bugs.xdebug.org/view.php?id= 249

Possibile soluzione:

Index: trunk/www/sites/all/libraries/classes/defaqtoSoapClient.class.php
===================================================================
--- classes/defaqtoSoapClient.class.php
+++ classes/defaqtoSoapClient.class.php
@@ -31,10 +31,23 @@

     try {
+        // xdebug and soap exception handling interfere with each other here 
+        // so disable xdebug if it is on - just for this call
+        if (function_exists('xdebug_disable')) {
+            xdebug_disable();
+        }
       //Create the SoapClient instance
       parent::__construct($wsdl, $options);
     }
     catch(Exception $parent_class_construct_exception) {
+        if (function_exists('xdebug_enable')) {
+            xdebug_enable();
+        }
       // Throw an exception an say that the SOAP client initialisation is failed
       throw $parent_class_construct_exception;
+    } 
+    if (function_exists('xdebug_enable')) {
+        xdebug_enable();
     }
   }

potresti provare a fare una richiesta curl o fsockopen per verificare che l'URL sia valido.

Per tua informazione, sto usando SoapClient con PHPUnit per testare i servizi Web remoti e ho riscontrato lo stesso problema!

  • quando si utilizza una vecchia versione di PHPUnit (3.3.x) come terza parte, crash di phpunit
  • quando si utilizza la versione corrente di PHPUnit (3.4.6) come terza parte, phpunit visualizza " RuntimeException " ;.

Ecco il mio primo metodo di prova:

public function testUnavailableURL() {
    $client = new SoapClient("http://wrong.URI");
}

Ecco il primo risultato di PHPUnit:

There was 1 error:

1) MyTestCase::testUnavailableURL
RuntimeException: 


FAILURES!

Ecco il mio secondo metodo di prova:

public function testUnavailableURL() {
        try {
          $client = @new SoapClient("http://wrong.URI");
        } catch (SoapFault $fault) {
          print "SOAP Fault: (faultcode: {$fault->faultcode}, faultstring: {$fault->faultstring})";
        }
}

Ecco il secondo risultato del test PHPUnit:

PHPUnit 3.4.6 by Sebastian Bergmann.

.SOAP Fault: (faultcode: WSDL, faultstring: SOAP-ERROR: Parsing WSDL: Couldn't load from 'http://wrong.URI' : failed to load external entity "http://wrong.URI"
)...

Time: 3 seconds, Memory: 4.25Mb

OK

NB: ho trovato un biglietto phpunit su questo argomento: ticket 417

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top