2

これが php のバグ (不適切な実装) なのか、それとも私のバグなのか (SOAP プロトコルの理解が不十分/SoapServer を使用するのはこれが初めてであるため) なのかはわかりません。

同じ操作が 2 つ以上あるwsdl:part場合 (wsdl:message操作と soapAction が異なっていても)、SoapServer常に最初の関数が呼び出されることに気付きました。この例では、2 つの関数がmultiply2あり、multiply4どちらもnum(int) を入力パラメーターとして持っています。今日、部品名 (service1.wsdl) を変更すると、関数は正しくマップされます。

ただし、バグのように見える別の名前を使用してもかまいません。何か不足していますか、それともバグを開く必要がありますか?

これは私が作成した簡単な例です:

非常に単純な php クラス

<?php
class Multi
{
    function multiply2($num) { return ($num * 2 ); }
    function multiply4($num){ return ($num * 4 );  }
}
?>

SoapServer を少し変更しました (ロギングを追加 -この投稿から適応) が、プレーンな SoapServer も使用している場合に問題が発生します。

$server = new overloadedSoapServer("service.wsdl", array('soap_version' => SOAP_1_2,'encoding' => SOAP_ENCODED));
$server->setClass("multi");

if ($_SERVER["REQUEST_METHOD"] == "POST") {
    $server->handle();
} 

これはクライアント コードです。

ini_set("soap.wsdl_cache_enabled", "0");
$client = new SoapClient('service.wsdl');
$client1 = new SoapClient('service1.wsdl');
echo "<pre>\nFrom service.wsdl:";
echo  "\n".$client->multiply2(10);
echo  "\n".$client->multiply4(10);
echo "</pre>";
echo "<pre>\nFrom service1.wsdl:";
echo  "\n".$client1->multiply2(10);
echo  "\n".$client1->multiply4(10);
echo "</pre>";

service.wsdlservice1.wsdlは基本的に同じファイルですが、次の 2 つの例外があります。

  1. それらのエンドポイントは異なります(各エンドポイントservice.wsdlへのポイントhttp://tests.simsimy.info/web/service.phpと各エンドポイントservice1.phphttp://tests.simsimy.info/web/service1.phpのポイントは、適切な wsdl を使用して をロードしますSoapServer
  2. inservice.wsdl multiply2Requestmultiply4Requestas part name -numを持ちますが、 inservice1.wsdlの名前は異なります (num2num4)

これは、service.wsdl の完全な wsdl です。

<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<wsdl:definitions xmlns:soap="http://schemas.xmlsoap.org/wsdl/soap/"
    xmlns:tns="http://tests.simsimy.info/web/" xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/"
    xmlns:xsd="http://www.w3.org/2001/XMLSchema" name="service"
    targetNamespace="http://tests.simsimy.info/web/">
    <wsdl:message name="multiply2Request">
        <wsdl:part name="num" type="xsd:int"></wsdl:part>
    </wsdl:message>
    <wsdl:message name="multiply2Response">
        <wsdl:part name="res" type="xsd:int"></wsdl:part>
    </wsdl:message>

    <wsdl:message name="multiply4Request">
        <wsdl:part name="num" type="xsd:int"></wsdl:part>
    </wsdl:message>
    <wsdl:message name="multiply4Response">
        <wsdl:part name="res" type="xsd:int"></wsdl:part>
    </wsdl:message>
    <wsdl:portType name="dd">
        <wsdl:operation name="multiply2">
            <wsdl:input message="tns:multiply2Request"></wsdl:input>
            <wsdl:output message="tns:multiply2Response"></wsdl:output>
        </wsdl:operation>
        <wsdl:operation name="multiply4">
            <wsdl:input message="tns:multiply4Request"></wsdl:input>
            <wsdl:output message="tns:multiply4Response"></wsdl:output>
        </wsdl:operation>
    </wsdl:portType>
    <wsdl:binding name="serviceSOAP" type="tns:dd">
        <soap:binding style="document"
            transport="http://schemas.xmlsoap.org/soap/http" />
        <wsdl:operation name="multiply2">
            <soap:operation soapAction="http://tests.simsimy.info/web/multiply2" />
            <wsdl:input>
                <soap:body use="literal" />
            </wsdl:input>
            <wsdl:output>
                <soap:body use="literal" />
            </wsdl:output>
        </wsdl:operation>
        <wsdl:operation name="multiply4">
            <soap:operation soapAction="http://tests.simsimy.info/web/multiply4" />
            <wsdl:input>
                <soap:body use="literal" />
            </wsdl:input>
            <wsdl:output>
                <soap:body use="literal" />
            </wsdl:output>
        </wsdl:operation>
    </wsdl:binding>
    <wsdl:service name="multiply_service">
        <wsdl:port binding="tns:serviceSOAP" name="serviceSOAP">
            <soap:address location="http://tests.simsimy.info/web/service.php" />
        </wsdl:port>
    </wsdl:service>
</wsdl:definitions>

の変更部分service1.wsdl:

<wsdl:message name="multiply2Request">
        <wsdl:part name="num2" type="xsd:int"></wsdl:part>
    </wsdl:message>
    <wsdl:message name="multiply2Response">
        <wsdl:part name="res" type="xsd:int"></wsdl:part>
    </wsdl:message>

    <wsdl:message name="multiply4Request">
        <wsdl:part name="num4" type="xsd:int"></wsdl:part>
    </wsdl:message>
    <wsdl:message name="multiply4Response">
        <wsdl:part name="res" type="xsd:int"></wsdl:part>
    </wsdl:message>

クライアント コードを実行すると、次の出力が得られます。

From service.wsdl:
20
20

From service1.wsdl:
20
40
4

1 に答える 1

2

wsdl のバインディング スタイルを「document」から「rpc」に変更できます。

上記の投稿されたサーバーコードにはキャッシュを無効にする ini_set() が含まれていないため、最初にキャッシュの問題だと思いました。しかし、キャッシュの問題ではありません。

http トラフィックを追跡しました。クライアントは適切に動作しているようです。これは SoapServer の問題です。(あなたが言ったように)..さらに調査中...

バグ レポートは既に提出されていますが、現時点ではバグかどうかは不明です。

バグレポートにも回避策が記載されています。これが問題ない場合は、バインド スタイルを rpc に変更できます。

変化する

<soap:binding style="document"

<soap:binding style="rpc"

この回避策は私にとってはうまくいきます。バインディング スタイルがどのように機能するかについての非常に興味深い記事がここにあります。これは、rpc バインディング スタイルが適切かどうかを判断するのに役立ちます。

于 2012-12-19T18:21:15.563 に答える