ホームページ  >  記事  >  バックエンド開発  >  PHPはwsdlをどのように処理しますか

PHPはwsdlをどのように処理しますか

藏色散人
藏色散人転載
2019-12-03 14:24:293166ブラウズ

0x00 はじめに

最近インターフェイスを書いているのですが、以前はインターフェイスのデータ送信はjson形式やxml形式で送信または取得していました。しかし今回、サードパーティと共同でデバッグする際に、彼らは wsdl 形式を提供してくれました。瞬時に SB に変わります...

テスト コードを Google で検索すると、テストはサードパーティのインターフェイスを呼び出してステータス 200 を返します。このまま何も起こらなければ終わるだろうと思っていたのですが、近づいてみると、インターフェースをいくら呼び出しても正しいデータが返ってこないことが分かりました。その後、ログを確認したところ、渡されたパラメータをまったく受け取っていないことが分かり、午後から夕方まで混乱して問題が解決されました。なかなか興味深い内容だったので、まずは書いてみました。

0x01 wsdl

とは何か これまでの説明に基づいて、Web サーバーの定義を記述するために使用される XML 形式のドキュメントです。つまり、Web サーバーのメソッドとパラメーターの説明です。

参照: https://www.php.cn/faq/437443.html

リクエストする場合 http://api.test.cn/xwebservices / testServer?wsdl' は、?wsdl で終わるこの URL と同様に、一連の XML 構造化データが提供されます。

はい、ただの塊です...

PHPはwsdlをどのように処理しますか

次はそれをどう理解するか、その方法が鍵です、それ以外はすべて無駄だ。

0x02 説明ドキュメントの理解

この XML ドキュメントを最初に見たときは非常に混乱しましたが、PHP 拡張機能を使用すると、より明確になりました。

<?php
$client = new SoapClient(&#39;http://api.test.cn/xwebservices/testServer?wsdl&#39;);
print "\n提供的方法\n";
print_r($client->__getFunctions());
print "相关的数据结构\n";
print_r($client->__getTypes());
print "\n\n";

PHPはwsdlをどのように処理しますか

ここでは SOAP 拡張機能を使用します。この拡張機能は、公式 PHP コピーで提供されている操作処理 WebServer サービス拡張機能です。最終的には、パラメーターの実現にも使用します。伝染 ; 感染。

上の図からわかるように、このインターフェイスには次の 3 つのメソッドが用意されています。

##関連するデータ構造は、メソッド内のパラメーター名とパラメーターのタイプを指します。たとえば、xxxxUserInfo メソッドには 3 つの文字列型パラメータが必要です。それぞれ in0、in1、in2 に対応します。

注意

ここでのパラメータ キーは in0 である必要があります。これは配列を必要としない任意のパラメータ名であり、ユーザー定義または双方の合意によって決まります。 。インターフェイス メソッドの作成を開始したとき、err_msg (エラー情報を示す)、err_code (エラー コーディングを示す)、および date (送信される最終データ) など、インターフェイス コピーに指定されているパラメーターの説明に基づいて送信を実行しました。次に、それを順序付き配列に変更し、対応するパラメータを 1 つずつ埋めていきます (このときのキーは 0 ~ 2)。しかし、試してみてもうまくいかなかったので、最終的には試してみようという気持ちで、キー名として int0 を使用し、値として対応する err_msg の内容を使用してみました。 OK~、完璧な解決策です。

コード:

<?php
/**
 * @author 0x584A
 * 获取WSDL接口数据
 */
class getwsdlTest extends PHPUnit_Framework_TestCase
{
    public $apiurl = &#39;http://api.test.cn/xwebservices/testServer?wsdl&#39;;
    private static $soapClientHandler;
    private $infoArr = [
        &#39;err_msg&#39; => &#39;false&#39;,
        &#39;err_code&#39; => &#39;0&#39;,
        &#39;date&#39; => &#39;此处是要传输的数据&#39;
    ];
    public function setUp()
    {
        $client = new SoapClient(&#39;http://api.test.cn/xwebservices/testServer?wsdl&#39;);
        print "提供的方法\n";
        print_r($client->__getFunctions());
        print "相关的数据结构\n";
        print_r($client->__getTypes());
        print "\n\n";
    }
    /**
     * xxxxUserInfo方法
     */
    public function testxxxxUserInfoData()
    {
        try {
            $ApiInfo = $this->infoArr;
            //set request param
            $parameter = array(
                &#39;in0&#39; => $ApiInfo[&#39;err_msg&#39;],
                &#39;in1&#39; => $ApiInfo[&#39;err_code&#39;],
                &#39;in2&#39; => $ApiInfo[&#39;date&#39;]
            );
            $result = $this->getSoapClientHandler()->synchUserInfo($parameter);
            //调用结果返回异常
            if (!$result instanceof stdClass) {
                throw new Exception("调用synchUserInfo结果出现异常:" . json_encode($result));
            }
            //调用接口状态码,输出对应错误详情
            if ($result->out == &#39;01&#39;) {
                throw new Exception("调用synchUserInfo=>error:" . $result->out . ",msg:接口数据异常");
            }
            $xml_parser = xml_parser_create();
            if (!xml_parse($xml_parser, $result->out, true)) {
                xml_parser_free($xml_parser);
                throw new Exception("调用synchUserInfo返回的不是一个xml结构体");
            }
            xml_parser_free($xml_parser);
            //XXE
            libxml_disable_entity_loader(true);
            $xml = simplexml_load_string($result->out, &#39;SimpleXMLElement&#39;, LIBXML_NOCDATA);
            // 输出参数
            var_dump($xml->data);
            echo " 成功".PHP_EOL;
        } catch (SoapFault $soapFault) {
            throw new Exception($soapFault->getMessage() . $this->getSoapClientHandler()->__getLastResponse());
        }
    }
    /**
     * @description getSoapClientHandler
     */
    public function getSoapClientHandler()
    {
        if (!self::$soapClientHandler) {
            self::$soapClientHandler = new SoapClient($this->getSynchApi());
        }
        return self::$soapClientHandler;
    }
    /**
     * @description getSynchApi
     */
    public function getSynchApi()
    {
        return $this->apiurl;
    }
}
?>

プロモーション:「

PHP チュートリアル

以上がPHPはwsdlをどのように処理しますかの詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

声明:
この記事はsegmentfault.comで複製されています。侵害がある場合は、admin@php.cn までご連絡ください。