【问题标题】:How to build a correct SOAP request with PHP如何使用 PHP 构建正确的 SOAP 请求
【发布时间】:2013-09-14 10:00:09
【问题描述】:

我需要为此 SOAP“服务”格式化/构建一个请求: http://api.notificationmessaging.com/NMSOAP/NotificationService?wsdl

理想情况下,我想使用原生 PHP SOAP 类,但我开始怀疑这个类是否不是我的问题的原因。

手册提供了这个例子:

    <soapenv:Body>
        <api:sendObject>
            <arg0>
                <content>
                    <entry>
                        <key>1</key>
                        <value>
                        <![CDATA[
                        <table width="600">
                        <tr>
                        <td>
                        <font size="2" face="Arial">Our powerful algorithms already
                        found a matching profile that matches your criteria:
                        <br>Celina72&nbsp;</font>
                        <img src="http://mypath/to/my/image.gif" width="50"
                        height="50" border="0" />
                        </td>]]></value>
                    </entry>
                </content>
                <dyn>
                    <entry>
                        <key>FIRSTNAME</key>
                        <value>john</value>
                    </entry>
                </dyn>
                <email>johnblum@flowerpower.com</email>
                <encrypt>BdX7CqkmjSivyBgIcZoN4sPVLkx7FaXGiwsO</encrypt>
                <notificationId>6464</notificationId>
                <random>985A8B992601985A</random>
                <senddate>2008-12-12T00:00:00</senddate>
                <synchrotype>NOTHING</synchrotype>
                <uidkey>EMAIL</uidkey>
            </arg0>
        </api:sendObject>
    </soapenv:Body>
</soapenv:Envelope>

这是我的 PHP 请求产生的垃圾(来自 __getLastRequest())

<?xml version="1.0" encoding="UTF-8"?>
    <SOAP-ENV:Envelope xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/" xmlns:ns1="http://api.service.nsapi.emailvision.com/" xmlns:ns2="http://xml.apache.org/xml-soap">
        <SOAP-ENV:Body>
            <ns1:sendObject/>
            <param1>AAAAAAAAAAAAAAAAAAAAAAAAAAA</param1>
            <param2>123456789</param2>
            <param3>BBBBBBBBBBBB</param3>
            <param4>2013-09-09T00:00:00</param4>
            <param5>NOTHING</param5>
            <param6>EMAIL</param6>
            <param7>
                <ns2:Map>
                    <item>
                        <key>2</key>
                        <value>TEST</value>
                    </item>
                </ns2:Map>
            </param7>
            <param8>
                <ns2:Map>
                <item>
                    <key>FIRSTNAME</key>
                    <value>John</value>
                </item>
            </ns2:Map>
            <ns2:Map>
                <item>
                    <key>LASTNAME</key>
                    <value>Smith</value>
                </item>
            </ns2:Map>
        </param8>
    </SOAP-ENV:Body>
</SOAP-ENV:Envelope>

我的电话:

$client = new SoapClient('http://api.notificationmessaging.com/NMSOAP/NotificationService?wsdl', array( 'trace' => 1, 'exceptions' => 0 ) );

参数看起来像这样(用虚拟数据修改):

$email = 'john.smith@example.com';
$encrypt = 'AAAAAAAAAAAAAAAAAAAAAAAAAAA';
$notification_id = 123456789;
$random = 'BBBBBBBBBBBB';
$senddate = '2013-09-09T00:00:00';
$synchrotype = 'NOTHING';
$uidkey = 'EMAIL';

$content = array();
$content[] = array(
    2 => 'TEST'
);

$dyn = array();
$dyn[] = array(
    'FIRSTNAME' => 'John'
);
$dyn[] = array(
    'LASTNAME' => 'Smith'
);

$params = array(
    'email' => $email,
    'encrypt' => $encrypt,
    'notificationId' => $notification_id,
    'random' => $random,
    'senddate' => $senddate,
    'synchrotype' => $synchrotype,
    'uidkey' => $uidkey,
    'content' => $content,
    'dyn' => $dyn
);

然后我像这样执行请求:

$res = $client->__soapCall( 'sendObject', array( $email, $encrypt, $notification_id, $random, $senddate, $synchrotype, $uidkey, $content, $dyn ) );

为什么 PHP 无法正确格式化我的请求?有没有一种更直接的方法,我可以“手动”编写 XML,然后使用 cURL 发布它?

【问题讨论】:

    标签: php web-services soap wsdl


    【解决方案1】:

    “有没有更直接的方法可以让我编写 XML?”

    通过使用SoapVar 并将构造函数的encode 参数设置为XSD_ANYXML,您可以编写原始XML。

    应该有一种方法可以让 WSDL 帮助构建 XML。

    你可以试试这样的:

    $wsdl   = "http://api.notificationmessaging.com/NMSOAP/NotificationService?wsdl"; 
    $client = new SoapClient($wsdl, array(  'soap_version' => SOAP_1_1,
                                            'trace' => true,
                                          )); 
    try {
    
        $xml = '<arg0>
                <content>
                    <entry>
                        <key>1</key>
                        <value>
                        <![CDATA[
                        <table width="600">
                        <tr>
                        <td>
                        <font size="2" face="Arial">Our powerful algorithms already
                        found a matching profile that matches your criteria:
                        <br>Celina72&nbsp;</font>
                        <img src="http://mypath/to/my/image.gif" width="50"
                        height="50" border="0" />
                        </td>]]></value>
                    </entry>
                </content>
                <dyn>
                    <entry>
                        <key>FIRSTNAME</key>
                        <value>john</value>
                    </entry>
                </dyn>
                <email>johnblum@flowerpower.com</email>
                <encrypt>BdX7CqkmjSivyBgIcZoN4sPVLkx7FaXGiwsO</encrypt>
                <notificationId>6464</notificationId>
                <random>985A8B992601985A</random>
                <senddate>2008-12-12T00:00:00</senddate>
                <synchrotype>NOTHING</synchrotype>
                <uidkey>EMAIL</uidkey>
            </arg0>';
    
        $args = array(new SoapVar($xml, XSD_ANYXML));    
        $res  = $client->__soapCall('sendObject', $args);
        return $res;
    } catch (SoapFault $e) {
        echo "Error: {$e}";
    }
    
    echo "<hr>Last Request";
    echo "<pre>", htmlspecialchars($client->__getLastRequest()), "</pre>";
    

    【讨论】:

    • 谢谢@quaspas,我更喜欢这种方法。我试过这个,我终于得到了服务的回应。但是它仍然不起作用:我收到消息“无法识别消息部分 arg0。(它是否存在于服务 WSDL 中?)”。我尝试删除部分,但消息是“无法识别消息部分内容。(它是否存在于服务 WSDL 中?)”。多亏了你,我可能离解决方案不远了:)
    • 知道了!缺少的只是一个封闭的 。现在另一个问题是文档使用 API 的命名空间“api”,但 PHP 将其返回为“ns1”。为什么? “忘了它,杰克。它是肥皂。”再次感谢@quaspas 的大力帮助!
    • 如果有人对前面评论中未回答的问题感到好奇,前缀ns1api 本身并不意味着什么;重要的部分是它绑定到的 URI,使用文档顶部的 xmlns:ns1="http://api.service.nsapi.emailvision.com/" 属性。您可以通过更改该属性来给它任何前缀,或者在文档中的任何位置添加您自己的前缀。
    • 该死的地狱。这正是我所需要的。非常感谢
    • 非常感谢这个代码对我有用,我从 30 多天开始就一直在寻找这个
    【解决方案2】:

    我知道这个话题大约有 1 年的历史, 但是我在其中找到了一些很好的信息,这给了我很好的帮助,并且我最终成功地使它与 php 方法 sendObject() 一起工作 所以我希望我的贡献也能帮助其他人......

    起初 sendObject() 的调用是这样的:$client->__soapCall 似乎根本不起作用 你必须直接调用它:$client->sendObject

    在这个主题中,我认为它是使用 emailvision 的 API (smartfocus, now...) 此方法 sendObject 不需要 openApiConnection()

    生成的令牌

    oki,现在,是让它工作的代码

    <?php
    
    
        $email = 'johann.******@gmail.com';
        $encrypt = '******************************';
        $notification_id = '**************';
        $random = '********************';
        $senddate = '2013-09-09T00:00:00';
        $synchrotype = 'NOTHING';
        $uidkey = 'EMAIL';
    
    
        $params = array(
            'arg0' => array(
                'content' => array( 1 => 'mon_test'),
                'dyn' => array( 'FIRSTNAME' => 'yoyo'),
                'email' => $email,
                'encrypt' => $encrypt,
                'notificationId' => $notification_id,
                'random' => $random,
                'senddate' => $senddate,
                'synchrotype' => $synchrotype,
                'uidkey' => $uidkey
            )
        );
    
    
        $client = new       SoapClient('http://api.notificationmessaging.com/NMSOAP/NotificationService?wsdl', array(  'trace' => 1, 'exceptions' => 0  ) );
    
        $res = $client->sendObject( $params );
    
    echo "<br /><br /><br />";
    echo "REQUEST 1 :" . htmlspecialchars($client->__getLastRequest()) . "<br />";
    echo "RESPONSE 1 :" . htmlspecialchars($client->__getLastResponse()) . "<br /><br /><br />";
    

    ?>

    你要知道 $encrypt ,$notification_id , $random 是通过创建一个transactionnal消息产生的,你可以在campagn指挥官的界面中得到这些信息

    注意输入xml的架构,有一个节点arg0,那么你必须在你的数组参数中创建一个级别arg0

    使其直接与 xml 一起工作:

    <?php
    $wsdl   = "http://api.notificationmessaging.com/NMSOAP/NotificationService?wsdl"; 
    $client = new SoapClient($wsdl, array(  'soap_version' => SOAP_1_1, 'trace' => true,  )); 
    try {
    
        $xml = '
    
                <ns1:sendObject>
                    <arg0>
    
                        <content>
                            <entry>
                                <key>1</key>
                                <value>
                                    <![CDATA[
                                    <table width="600">
                                    <tr>
                                    <td>
                                    <font size="2" face="Arial">Our powerful algorithms already found a matching profile that matches your criteria:
                                    <br>Celina72&nbsp;</font>
                                    <img src="http://mypath/to/my/image.gif" width="50" height="50" border="0" />
                                    </td>]]>
                                </value>
                            </entry>
                        </content>
    
                        <dyn>
                            <entry>
                                <key>FIRSTNAME</key>
                                <value>john</value>
                            </entry>
                        </dyn>
    
                        <email>johann*******@gmail.com</email>
                        <encrypt>*********************</encrypt>
                        <notificationId>**************</notificationId>
                        <random>**********************</random>
                        <senddate>2008-12-12T00:00:00</senddate>
                        <synchrotype>NOTHING</synchrotype>
                        <uidkey>EMAIL</uidkey>
    
                    </arg0>
                </ns1:sendObject>
    
    
    
            ';
    
        $args = array(new SoapVar($xml, XSD_ANYXML));    
        $res  = $client->__soapCall('sendObject', $args);
        //return $res;
    } 
    catch (SoapFault $e) {
        echo "Error: {$e}";
    }
    
    echo "<hr>Last Request";
    echo "<pre>", htmlspecialchars($client->__getLastRequest()), "</pre>";
    
    echo "<hr>Last Response";
    echo "<pre>", htmlspecialchars($client->__getLastResponse()), "</pre>";
    
    ?>
    

    这样写第一个节点很重要:&lt;ns1:sendObject&gt;

    &lt;api:sendObject&gt; 不起作用

    【讨论】:

      猜你喜欢
      • 2012-07-30
      • 1970-01-01
      • 2012-05-05
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多