我们有一个包含以下内容的WSDL,并使用标准的PHP SOAP Client进行调用:
<element name="doSomething">
<complexType>
<sequence>
<element name="Payload" nillable="true" type="xsd:string"/>
<element name="Username" type="string"/>
<element name="service" type="string"/>
<element name="Password" type="string"/>
</sequence>
</complexType>
</element>
有效载荷本质上是XML数据,例如看起来像这样
<code>1</code>
现在,通过echo $client->__getLastRequest();
转储的SOAP客户端请求如下所示:
<?xml version="1.0" encoding="UTF-8"?>
<SOAP-ENV:Envelope xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/" xmlns:ns1="pa/WebshopService"><SOAP-ENV:Body><ns1:doSomething><ns1:Payload><code>
1
</code>
</ns1:pcRequest><ns1:Username>bar</ns1:Username><ns1:service>bar</ns1:service><ns1:Password>bar</ns1:Password></ns1:doSomething></SOAP-ENV:Body></SOAP-ENV:Envelope>
我认为这是有道理的,因为<
和>
应该被编码。
对方似乎期望这样:
<?xml version="1.0" encoding="UTF-8"?>
<SOAP-ENV:Envelope xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/" xmlns:ns1="pa/WebshopService"><SOAP-ENV:Body><ns1:doSomething><ns1:Payload><code>
1
</code>
</ns1:pcRequest><ns1:Username>bar</ns1:Username><ns1:service>bar</ns1:service><ns1:Password>bar</ns1:Password></ns1:doSomething></SOAP-ENV:Body></SOAP-ENV:Envelope>
答案 0 :(得分:1)
好吧,复杂类型doSomething
说,属性Payload
是字符串类型。因此,xml内容的编码字符串应该正确。如果提供方希望未编码的内容,则属性Payload
将是另一种复杂类型。因此,在这种情况下,wsdl无效(如果为true),则提供者端确实需要元素而不是编码字符串。
无论如何,有一种解决方案可以使用PHP处理。只处理Payload
而不是字符串。而是用它做成一个复杂的类型。
class DoSomething()
{
protected $Payload;
protected $Username;
protected $Service;
protected $Password;
public function getPayload() : ?\SoapVar {
return $this->Payload;
}
public function setPayload(\SoapVar $payload) : DoSomething
{
$this->Payload = $payload;
return $this;
}
...
public function encode() : \SoapVar
{
return new \SoapVar(
$this,
SOAP_ENC_OBJECT,
null,
null,
'doSomething',
'http://www.example.com/namespace'
);
}
}
上面您将复杂类型doSomething
视为一个PHP类。您还会看到示例吸气剂和塞特方法。 get方法返回null或\ SoapVar实例。 setter方法采用一个\ SoapVar实例。
出于您的目的,您将需要Payload
属性的另一个PHP类,其中包含code
属性。
class Payload
{
protected $Code;
public function getCode() : ?\SoapVar
{
return $this->Code;
}
public function setCode(\SoapVar $code) : Payload
{
$this->Code = $code;
return $this;
}
public function encode() : \SoapVar
{
return new \SoapVar
{
$this,
SOAP_ENC_OBJECT,
null,
null,
'Payload',
'http://www.example.com/namespace'
}
}
}
现在将所有东西放在一起...
$code = new \SoapVar(1, XSD_INT, null, null, 'code');
$payload = (new Payload())
->setCode($code)
->encode();
$doSomething = (new DoSomething())
->setPayload($payload)
->setUsername(...)
->setService(...)
->setPassword(...)
->encode();
$result = $client->doSomething($doSomething);
现在您的请求应该看起来像...
<ns1:doSomething>
<ns1:Payload>
<code>1</code>
</ns1:Payload>
<ns1:Username>...</ns1:Username>
<ns1:Service>...</ns1:Service>
<ns1:Password>...</ns1:Password>
</ns1:doSomething>
希望对您有帮助。