Как я уже упоминал в комментариях, было бы намного проще использовать класс PHP SoapClient
и объекты в качестве сущностей. Вот небольшой пример того, как вы можете решить свою проблему.
PHP-клиент Soap
PHP получил собственную сборку в SoapClient
, которая работает довольно хорошо. Посмотрите, как инициализировать клиент для разработки.
<code>try {
$client = new \SoapClient('https://example.com?wsdl', [
'cache_wsdl' )> WSDL_CACHE_NONE,
'exceptions' => true,
'trace' => true,
]);
} catch (\SoapFault $fault) {
echo "<pre>";
var_dump($fault->getMessage());
echo "
";
if ($ client) {
echo "
";
var_dump($client->__getLastRequest(), $client->__getLastResponse());
echo "
";
}
}
Это простая инициализация класса SoapClient
с опциями разработки. Установка для опции trace
значения true позволяет использовать внутренние функции клиентов __getLastRequest()
и __getLastResponse()
. Таким образом, вы можете видеть, что отправил клиент и как выглядит ответ, если таковой имеется. Я использую это для проверки XML, отправленного клиентом.
Простые объекты как объекты, которые могут быть использованы мылом
SOAP определяет себя как сложные и простые определения типов. Это можно увидеть, если вы вызываете собственную функцию __getTypes()
. Будет отображено множество структур и простых определений типов, которые хранятся в данном файле wsdl или в файлах xsd, упомянутых в файле wsdl. С помощью этой информации мы можем построить свой собственный объект. В этом примере я использую простые stdClass
объекты. В производственной манере вы должны использовать вычисленные собственные объекты.
$req = new \stdClass();
$req->AWBNumber = new \SoapVar(
69184678146,
XSD_INT,
null,
null,
'AWBNumber',
'http://schemas.datacontract.org/2004/07/XXXAPI.Entities.XXX'
);
$encodedReq = new \SoapVar($req, SOAP_ENC_OBJECT, null, null, 'req', 'http://tempuri.org/');
$saveXXXStatus = new \stdClass();
$saveXXXStatus->req = $encodedReq;
$encodedSaveXXXStatus = new \SoapVar($saveXXXStatus, SOAP_ENC_OBJECT, null, null, 'SaveXXXStatus, 'http://tempuri.org/');
// send the content with the soap client
$result = $client->SaveXXXStatus($encodedSaveXXXStatus);
Пожалуйста, имейте в виду, что это короткий пример, который является неполным и приведет к ошибке мыла. Но что я здесь сделал? Узел req в вашем xml - это объект. Вы найдете определение этого объекта в выводе вышеупомянутой функции __getTypes()
. В этом примере я скомпилировал этот объект как stdClass
со свойством AWBNumber
. AWBNumber
сам по себе является SoapVar
объектом. Мы используем soap var из-за пространств имен, которые используются мыльным клиентом. После определения свойства мы кодируем объект req
как мыльный объект, который также является экземпляром SoapVar
.
В конце концов мы вызываем метод веб-сервиса SaveXXXStatus
с закодированным параметром.
Последний запрос
Если вы отправите этот пример, последний запрос должен выглядеть следующим образом:
<ns1:envelope xmlns:ns1="http://www.w3.org/2003/05/soap-envelope"
xmlns:ns2="http://tempuri.org/"
xmlns:ns3="http://schemas.datacontract.org/2004/07/XXXAPI.Entities.XXX">
<ns1:body>
<ns2:SaveXXXStatus>
<ns2:req>
<ns3:AWBNumber>69184678146</ns3:AWBNumber>
</ns2:req>
</ns2:SaveXXXStatus>
</ns1:body>
</ns1:envelope>
Как я уже говорил, это всего лишь пример. Вы должны закодировать все узлы как SoapVar
объекты и добавить его к родителям и, наконец, вызвать метод веб-сервиса с полными закодированными данными.
Просто как пирог, хм?