PHP SoapClient不处理WSDL中的抽象和替换组属性

PHP SoapClient不处理WSDL中的抽象和替换组属性,php,soap,wsdl,soap-client,Php,Soap,Wsdl,Soap Client,我正在使用他们提供的wsdl向加拿大邮政发送一个电话,其中包含如下部分: <!-- group-id and transmit-shipment are mutually exclusive --> <xsd:element name="groupIdOrTransmitShipment" abstract="true" /> <xsd:element name="group-id" type="tns:GroupIDType" substitutionGroup=

我正在使用他们提供的wsdl向加拿大邮政发送一个电话,其中包含如下部分:

<!-- group-id and transmit-shipment are mutually exclusive -->
<xsd:element name="groupIdOrTransmitShipment" abstract="true" />
<xsd:element name="group-id" type="tns:GroupIDType" substitutionGroup="tns:groupIdOrTransmitShipment"/>
<xsd:element name="transmit-shipment" type="xsd:boolean" fixed="true" substitutionGroup="tns:groupIdOrTransmitShipment"/>

<xsd:complexType name="ShipmentType">
    <xsd:all>
        <xsd:element ref="tns:groupIdOrTransmitShipment" />
        <xsd:element name="quickship-label-requested" type="xsd:boolean" minOccurs="0"/>
        <xsd:element name="cpc-pickup-indicator" type="xsd:boolean" fixed="true" minOccurs="0"/>
        <xsd:element name="requested-shipping-point" type="tns:PostalCodeType" minOccurs="0"/>
        <xsd:element name="shipping-point-id" type="tns:OutletIDType" minOccurs="0" />
        <xsd:element name="expected-mailing-date" type="xsd:date" minOccurs="0"/>
        <xsd:element name="delivery-spec" type="tns:DeliverySpecType"/>
        <xsd:element name="return-spec" type="tns:ReturnSpecType" minOccurs="0"/>
    </xsd:all>
</xsd:complexType>
/*
 Need to override SoapClient because the abstract element 'groupIdOrTransmitShipment' is expected to be in the request in order for validation to pass.
So, we give it what it expects, but in __doRequest we modify the request by removing the abstract element and add the correct element.

*/

class MySoapClient extends SoapClient {

    function __construct($wsdl, $options = null) {
        parent::__construct($wsdl, $options);
    }

    function __doRequest($request, $location, $action, $version, $one_way = NULL) {
        $dom = new DOMDocument('1.0');
        $dom->loadXML($request);
        //get element name and values of group-id or transmit-shipment.
        $groupIdOrTransmitShipment =  $dom->getElementsByTagName("groupIdOrTransmitShipment")->item(0);
        $element = $groupIdOrTransmitShipment->firstChild->firstChild->nodeValue;
        $value = $groupIdOrTransmitShipment->firstChild->firstChild->nextSibling->firstChild->nodeValue;

        //remove bad element
        $newDom = $groupIdOrTransmitShipment->parentNode->removeChild($groupIdOrTransmitShipment);

        //append correct element with namespace
        $body =  $dom->getElementsByTagName("shipment")->item(0);
        $newElement = $dom->createElement($element, $value);
        $body->appendChild($newElement);

        //save $dom to string
        $request = $dom->saveXML();
        //echo $request;

        //doRequest
        return parent::__doRequest($request, $location, $action, $version);
    }
}
使用他们的overidden方法可以很好地改变xml请求,但我完全搞不懂他们为什么这样做。WSDL是否存在根本性的问题?这是PHP的SoapClient中的一个bug吗?我想要一种在不重写任何核心类方法的情况下发送有效请求的方法

根据我的理解,作者想要一个
组id
传输装运
元素,但不是两者都要或没有。由于在
中不能有
元素,因此可以为此声明一个替换组,并在我的请求中只包含两个元素中的一个,但是如果我只包含
传输装运
并省略抽象元素
GroupIDorTransmitShipping
php将返回一个错误:

SOAP-ERROR:编码:对象没有“groupIdOrTransmitShipment”属性
更新:
这是非常古老的,但它是否相关

我还必须覆盖和扩展php SoapClass。它与php soapclass有关,php soapclass在请求/响应中需要某种格式,然后接收/发送什么。扩展它允许我自己处理格式化


wsdl没有问题,错误是类的一部分。无法绕过覆盖

是的,我在问题中已经明确了这一点。虽然欢迎您的反馈,但这不是答案。如果你愿意的话,你应该加上它作为评论。你的问题现在还不清楚。如果你想得到确认和解释,你就要发出声音。这就是我所给出的。“WSDL有什么根本性的错误吗?这是PHP的SoapClient中的错误吗?我想要一种在不重写任何核心类方法的情况下发送有效请求的方法。”不,WSDL没有任何问题,错误是类的一部分。你可能是对的,只是很难相信这样一个明显的错误会继续存在。您能提供任何文档、示例或任何东西来支持您的答案吗?就目前情况而言,你目前的回答只不过是重复了我在问题中提供的相同信息。