Выполнение запроса SOAP через HTTPS с использованием PHP и NuSOAP

#php #web-services #soap #https #nusoap

#php #веб-сервисы #soap #https #nusoap

Вопрос:

Я застрял с этим в течение нескольких дней, и, похоже, нигде не могу найти ответ, хотя я думаю, что это довольно распространенная задача. Кто-нибудь может помочь?

Я пытаюсь использовать PHP и NuSOAP для подключения к веб-сервису. Веб-сервис требует от меня как использования ssl-сертификата, так и передачи параметров аутентификации в запросе soap. По словам администраторов веб-сервиса, запрос должен выглядеть следующим образом:

 <?xml version="1.0"?>
<s:Envelope xmlns:s="http://schemas.xmlsoap.org/soap/envelope/">
    <s:Header>
        <o:Security xmlns:o="http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-secext-1.0.xsd">
            <o:UsernameToken>
                <o:Username>username</o:Username>
                <o:Password>password</o:Password>
            </o:UsernameToken>
        </o:Security>
    </s:Header>
    <s:Body>
        <PriceQuote xmlns="a_url">
            <PartnerProfileId>a_unique_partner_id_we_have</PartnerProfileId>
            <Reservation xmlns:d4p1="another_url" xmlns:i="http://www.w3.org/2001/XMLSchema-instance">

                * a bunch of stuff

            </Reservation>
        </PriceQuote>
    </s:Body>
</s:Envelope>
  

Я пытался выяснить, как это сделать с помощью NuSOAP. Прямо сейчас, это то, что у меня есть (я не знаю, как передать параметры аутентификации или использовать файлы сертификатов, которые у меня есть):

 $client = new nusoap_client("https://endpoint_url");
$client->soap_defencoding = 'UTF-8'; 

$result = $client->call("PriceQuote", "");

// For debugging
echo '<h2>Request</h2>';
echo '<pre>' . htmlspecialchars($client->request, ENT_QUOTES) . '</pre>';
echo '<h2>Response</h2>';
echo '<pre>' . htmlspecialchars($client->response, ENT_QUOTES) . '</pre>';
echo '<h2>Debug</h2>';
echo '<pre>' . htmlspecialchars($client->debug_str, ENT_QUOTES) . '</pre>';
  

Используя приведенный выше отладочный код, я вижу, что это ответ, который я получаю от веб-службы:

 HTTP/1.1 500 Internal Server Error
Date: Mon, 02 May 2011 13:42:14 GMT
Server: Microsoft-IIS/6.0
X-Powered-By: ASP.NET
X-AspNet-Version: 2.0.50727
Cache-Control: private
Content-Type: text/xml; charset=utf-8
Content-Length: 347

<s:Envelope xmlns:s="http://schemas.xmlsoap.org/soap/envelope/">
    <s:Body>
        <s:Fault>
            <faultcode xmlns:a="http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-secext-1.0.xsd">
                a:InvalidSecurity
            </faultcode>
            <faultstring xml:lang="sv-SE">
                An error occurred when verifying security for the message.
            </faultstring>
        </s:Fault>
    </s:Body>
</s:Envelope>
  

Этот ответ, конечно, неудивителен, поскольку я не передаю никаких параметров аутентификации в запросе.

Кто-нибудь знает, как я могу передать имя пользователя и пароль в заголовке запроса SOAP, а также как я использую имеющиеся у меня файлы ssl-сертификатов? Как вы, вероятно, можете сказать, я довольно новичок в веб-сервисах и NuSOAP. Если что-то в моем вопросе не имеет смысла, пожалуйста, дайте мне знать.

Ответ №1:

если вам не нужен nu_soap, вы можете решить проблему с помощью приведенного ниже скрипта

 <?PHP
$client = new SoapClient("http://Your Wsdl Location", array("trace" => 0));
$HeaderSecurity = array("UsernameToken"=>array("Username"=>"YourUserName",
                                          "Password"=>"YourPassword",
                                )

);

$header[] = new SoapHeader("http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-secext-1.0.xsd","Security",$HeaderSecurity);

$client->__setSoapHeaders($header);
//$client->__setLocation("https://YourTargetLocation/"); if you have wsdl file you don't need to use this line 
$REsponse = $client->YourRequest();
?>
  

Комментарии:

1. Спасибо за быстрый ответ, Мустафа. Используя это (слегка измененное, поскольку я работаю без файла wsdl) Я по-прежнему получаю сообщение об ошибке: Неустранимая ошибка: неперехваченное исключение SoapFault: [a: InvalidSecurity] Произошла ошибка при проверке безопасности сообщения. Может ли это быть связано с тем, что я все еще не использую файлы ssl-сертификата? Если да, знаете ли вы, как я могу их включить?

2. может быть, вы можете попробовать передать прямую строку xml (это для nu_soap): $client->call('MethodName',$RequestXml,NULL,"MethodName",NULL,NULL,"document"); передайте xml в $RequestXml и введите имена ваших методов в example.

3. Спасибо! Я изменил ваше предложение, чтобы также включить заголовок xml: $result = $client->call("PriceQuote",$RequestBody,NULL,"PriceQuote",$RequestHeader,NULL,"document"); . Это выдало мне новую ошибку: … Несоответствие ContractFilter в EndpointDispatcher. Это может быть либо из-за несоответствия контракта (несовпадающих действий между отправителем и получателем), либо из-за несоответствия привязки / безопасности между отправителем и получателем. Убедитесь, что отправитель и получатель имеют одинаковый контракт и одинаковую привязку (включая требования безопасности, например, сообщение, транспорт, Нет). Может ли это быть из-за отсутствия сертификатов SSL?

4. К сожалению, нет : ( Но это не что-то известное или для чего вы не найдете документацию в Интернете.

5. Оказывается, окончательные ошибки были вызваны тем, как был отформатирован запрос soap (веб-службе не понравилось форматирование, и она ответила внутренней ошибкой сервера). Предложение Мустафы в комментариях действительно помогло! В конце я использовал его метод.