zoukankan      html  css  js  c++  java
  • vc++2008 采用GSoap访问 WebService

    前一阶段写gSOAP 的文章没保存好,后来想写的,越学越没有写的勇气了,感觉自己很菜,但是现在感觉还是写点就算给入门者一点提示吧。另外虽说这篇文章是自己写的,但是却感觉是东拼西凑的,有很多别人的东西了。
       看了我转载的关于soap 的文章,大家想必对soap有所了解了吧,那么gSOAP是什么那?
    gSOAP 是一个开源的项目,用它可以方便的使用c/c++地进行SOAP客户端和服务器端编程,而不必了解xml和SOAP协议的细节。这样使用者就可以专注于自 己的web service 客户端或服务器端的编写,而不用纠缠与其它细节。我第一次接触这些东西,我对SOAP的理解是这样的:以http协议为基本的通信协议,以xml文件形式 请求远程服务,再以xml文件的形式返回执行结果,我理解的就这么简单了,有啥不妥处,还请指教阿。
    实践一下才有理性认识,下面是我自己在windows下,具体说来就是用vc 6.0下编写的一个很简单的客户端程序调用远程的服务,来发送电子邮件,感觉很爽吧。
    首先我们到 http://sourceforge.net/project/showfiles.php?group_id=52781 下载gSOAP下载工具集吧,不同的系统下用的gSOAP是不一样的,根据需要下载了windows下的和linux下的。
    gSOAP工具集不需要安装,直接解压就可以了。在/bin目录下我们可以看到两个可执行文件:
    soapcpp2.exe: gSOAP编译器,编译头文件生成服务器和客户端都需要的 c/c++文件。 
    wsdl2h.exe: 编译wsdl文件生成c/c++头文件。
    工具就算准备好了。
    其次,我们到 http://www.abysal.com/soap/AbysalEmail.wsdl 下载
    wsdl文件,假设保存文件名为:AbysalEmail.wsdl。所谓的wsdl文件翻译成中
    文就是网络服务描述文件了。我们用wsdl2h.exe工具来根据wsdl文件生成
    c/c++头文件,可以用-c选项是生成纯c的头文件,另外用-s选项是说明我们在
    程序中不使用stl,注意了默认我们是适用stl的。
    用如下命令:
    wsdl2h  -o AbysalEmail.h AbysalEmail.wsdl
    既可以生成我们需要的AbysalEmail.h头文件了。这里文件名可以随便起了。
    将下载的gsoap的import里的stlvector.h中文件拷贝到当前的文件夹下,因为默认是使用stl的,所以需要它。
    然后执行soapcpp2 命令来生成存根程序,用如下命令:
    soapcpp2  -C AbysalEmail.h
    -C  选项是只生成客户端的,默认是生成客户端和服务器端的,如果你在程序中使用了vector还要加上 –limport选项。
    即可以生存客户端存根程序和框架了。
    soapClient.cpp:编译客户端的需要的存根例程。
    soapC.cpp,soapH.h:用来序列化和反序列化c/c++不同数据类型。
    soapServer.cpp: 编译服务器端的需要的存根例程。
    soapXXXProxy.h: 生成的代理类的头文件,使用代理类时需要此文件。
    本程序为soapSendEmailBindingProxy.h。

    第三步,就是在vc中建个工程,设置如下:
    在vc6中建立工程,其源文件为:sendMailClient.cpp soapC.cpp 
                                        soapClient.cpp   stdsoap2.cpp
    头文件为:      AbysalEmail.h soapH.h soapStub.h stdsoap2.h      
    其他依赖文件为:basetsd.h  sendemailbinding.nsmp
    stdsoap2.cpp stdsoap2.h是下载的gSOAP中包含的。
    另外在所需要的库中把wsock32.lib加上,gSOAP也是采用socket方式连接的。(添加方法:项目->属性->连接器->输入->附加依赖项 添加wsock32.lib)
    其中sendMailClient.cpp为我写的客户端程序,程序如下:

    #include "soapH.h"                          // 得到存根程序
    #include "SendEmailBinding.nsmap"            //得到名称空间映射表
    #include <iostream>
    #include  <string>
    #include "soapSendEmailBindingProxy.h"

    using namespace std;

    int main(int argc, char **argv) 
    {
            struct soap email_soap;
            int result = -1;
       SendEmailBinding  EmailBind;              //生成代理类对象
        _ns1__SendEmail  sendEmail;              //web服务发送电子邮件对象
       _ns1__SendEmailResponse  Email_Response;  //web 服务返回发送结果对象
       string from = "mseaspring";
       string to   = "David";
       string sub = "Hello test!";
       sendEmail.From = &from;
       sendEmail.FromAddress = " mseaspring@hotmail.com ";
       sendEmail.MsgBody = "I want to test a web service!";
       sendEmail.To = &to;
       sendEmail.ToAddress = " mseaspring@gmail.com ";
       sendEmail.Subject = ⊂

            result = EmailBind.__ns1__SendEmail(&sendEmail,  &Email_Response);
            if (result != 0)
            {
                    printf("soap error ,errcode = %d ", result);
            }
            else
            {
                cout<<"The result is :"<<Email_Response.ReturnCode<<endl;
                    cout<<"恭喜你,邮件发送成功!"<<endl;
            }
            return 0;
    }我程序中是采用代理类的方式编写的程序,不用代理类的代码如下:
    #include "soapH.h"                          //  得到存根程序
    #include "SendEmailBinding.nsmap"            // 得到名称空间映射表
    #include <iostream>
    #include  <string>
    using namespace std;

    int main(int argc, char **argv) 
    {
            struct soap email_soap;
            //初始化gSoap运行时环境变量,只需初始化一次
            soap_init(&email_soap);
            int result = -1;
            //远程web服务的endpoint URL .不要带WSDL
       const char* server="http://www.abysal.com/soap/soapmail.wdtp";
       string from = "mseaspring";
       string to   = "David";
       string sub = "Hello test!";
       sendEmail.From = &from;
       sendEmail.FromAddress = " mseaspring@hotmail.com ";
       sendEmail.MsgBody = "I want to test a web service!";
       sendEmail.To = &to;
       sendEmail.ToAddress = " mseaspring@gmail.com ";
       sendEmail.Subject = ⊂
        //调用根据远程服务产生函数的接口
    result = soap_call___ns1__SendEmail(&email_soap, server, "", &sendEmail,  &Email_Response);
            if(email_soap.error)
            {
                    //在stderr流中打印soap的错误信息
                    soap_print_fault(&email_soap,stderr);
                    result = email_soap.error;
            }
        soap_destroy(&email_soap);// 删除反序列化类的实例,仅用于c++
            soap_end(&email_soap);    // 清空已经并行化的数据
            soap_done(&email_soap);   // 与gSOAP 环境相分离,关闭连接
            if (result != 0)
            {
                    printf("soap error ,errcode = %d ", result);
            }
            else
            {
                cout<<"The result is :"<<Email_Response.ReturnCode<<endl;
                    cout<<"恭喜你,邮件发送成功!"<<endl;
            }
            return 0;
    }
    你可能会问我怎么知道远程服务的接口阿? 到soapStub.h中去找就可以了,至于代理类的使用,到代理类头文件中一看便知。
    好了,终于要写完了,当然我们不仅可以编写客户端也可以编写服务器端程序,至于服务器端,有兴趣的可以自己看看gSOAP里面的文档,也很简单的,不过也要花点时间学习的了,呵呵。
    如果对于上面程序,有谁没调试成功联系我,邮箱都写在程序里那。呵呵。

    soap_set_mode(&soap, SOAP_C_UTFSTRING); 

    采用UTF-8的形式编码发送和接收到的文字,可防止中文乱码。

  • 相关阅读:
    hdu 3666 差分约束系统
    hdu 1198农田灌溉
    常微分方程(阿諾爾德) Page 45 相空間,相流,運動,相曲線 註記
    高等微積分(高木貞治) 1.4節 例2
    常微分方程(阿諾爾德) Page 45 相空間,相流,運動,相曲線 註記
    解析函數論 Page 29 命題(2) 函數模的有界性
    高等微積分(高木貞治) 1.4節 例2
    解析函數論 Page 29 命題(1) 有界閉集上的一致連續性
    解析函數論 Page 29 命題(3) 模的下界的可達性
    解析函數論 Page 29 命題(2) 函數模的有界性
  • 原文地址:https://www.cnblogs.com/xumaojun/p/8543199.html
Copyright © 2011-2022 走看看