首页 > 代码库 > gSoap 开发 (客户端)

gSoap 开发 (客户端)

一.开发环境准备
1.从gSoap官方网站http://gsoap2.sourceforge.net下载gSoap工具包。
  本例下载的是2.8.15的版本。
2.根据说明文档(README)配置安装gSoap工具包。
     说明: 一般下载的gSoap工具包中已经包含了生成Web Service客户端需要用到的两个工具(可执行文件):wsdl2h.exe和soapcpp2.exe,一般win32版本在gsoap\bin\win32下。只是默认情况下,wsdl2h并不支持SSL,即无法访问HTTPS站点,且这两个工具的版本一般也要低于所在gSoap工具包的版本。
     所以如果想要支持SSL等更多功能,就需要自己重新配置编译该gSoap工具包,以生成新的sdl2h和soapcpp2。
反之,如果下载的gSoap工具包中自带的wsdl2h和soapcpp2已经满足了你的需求,就可以不必再配置编译gSoap工具包,而是直接使用工具包自带的wsdl2h和soapcpp2。

二.wsdl2h和soapcpp2工具工具的使用
1. 通过WSDL文件生成头文件(.h)

用法:

?
1
2
3
4
5
6
7
8
Wsdl2h  [-o 头文件名]  [WSDL文件名或URL]
wsdl2h 常用选项
-o 文件名,指定输出头文件
-n 名空间前缀 代替默认的ns
-c 产生纯C代码,否则是C++代码
-s 不要使用STL代码
-t 文件名,指定type map文件,默认为typemap.dat
-e 禁止为enum成员加上名空间前缀

  该步的目的:使用gSoap工具wsdl2h,根据WSDL生成一个C/C++语法结构的头文件。实现WSDL文件到.h文件的数据映射。
示例(其中的头文件名称和wsdl文件链接按实际情况填入):

?
1
wsdl2h -s -o mapp.h http://****/mapp.wsdl

  该语句将得到一个头文件:mapp.h
2. 通过头文件(如:mapp.h)生成所需要的c/cpp 文件

  用法:

?
1
2
3
4
5
6
7
8
9
soapcpp2    [头文件]
soapcpp2 常用选项
-C 仅生成客户端代码
-S 仅生成服务器端代码
-L 不要产生soapClientLib.c和soapServerLib.c文件
-c 产生纯C代码,否则是C++代码(与头文件有关)
-I 指定import路径(见上文)
-x 不要产生XML示例文件
-i 生成C++包装,客户端为xxxxProxy.h(.cpp),服务器端为xxxxService.h(.cpp)

  该步目的:使用gSoap的预编译器soapcpp2生成相应的底层通信代码。
示例(以下命令只生成客户端使用代码):

?
1
soapcpp2 -i -x -C -L mapp.h

  提示:执行时如果看到soapcpp2提示:Critical error: #import: Cannot open file "stlvector.h" for reading.等 那是因为我们的头文件使用了STL(wsdl2h 没用-s选项),这时要使用-I选项指定gSOAP的 import文件路径,这个路径是"$gsoap\gsoap\import":
如下(import路径按用户系统实际路径指定):

?
1
soapcpp2 -i -x -C -L mapp.h -I D:\gsoap-2.8\gsoap\import

  上述命令执行结果生成如下文件:
  soapH.h    soapStub.h      soapC.cpp
  MappBinding.nsmap
  soapMappBindingProxy.h
  soapMappBindingProxy.cpp
  上述文件具体含义见【附1】
三.在vc中使用gsoap编写soap客户端示例
1. 在vc中创建一个win32项目 (mfc项目通用)。将soapcpp2 生成的所有文件加入到工程下。
2. 将gsoap目录下的 stdsoap2.cpp、stdsoap2.h 两个文件引入工程中(编译需要)。
3. 客户端实现代码如下:

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
#include <iostream> 
#include "soapMappBindingProxy.h" 
#include "MappBinding.nsmap" 
 
int main(int argc, char** argv) 
    MappBindingProxy Proxy; 
    _ns1__doCicRequest cicReq; 
    _ns1__doCicRequestResponse cicRes; 
 
    cicReq.msg = new char[1024]; 
    memset(cicReq.msg,0,sizeof(cicReq.msg)); 
    strcpy(cicReq.msg,"<?xml version=\"1.0\" encoding=\"GBK\"?><INSUREQ>\ 
        <MSG>soap client message.</MSG></INSUREQ>"); 
    std::cout << "请求数据:" << cicReq.msg << std::endl; 
    Proxy.doCicRequest(&cicReq,&cicRes); 
    std::cout << "接收数据:" << cicRes.return_ << std::endl; 
    return 0; 
}

4. 编译注意事项:
  1). 在vc中开发,需要对引入的3个cpp文件进行设置 不使用预编译头,设置方式如下: 工程 -> 设置 -> 选择cpp文件 -> 预编译头 -> 选择不使用
  2). 在程序中如不使用默认的webService地址,调用xxxxxProxy类的指定构造函数。

?
1
MappBindingProxy Proxy(surl);

  3). 字符编码设置,详情见【附2】

附1: 文件含义解析
  1). MappBinding.nsmap
      该文件的作用:An XML-to-C/C++ namespace mapping table,即WSDL文件与生成的客户端代码框架的一个名字空间的映射表。
  2). soapStub.h
      该文件就是直接由wsdl2生成的头文件转化而来,它详细定义了WSDL所描述的各项服务和数据结构。它是soap的存根文件,定义了由wsdl2生成的头文件里对应的远程调用模型(RPC)。
  3). soapMappBindingProxy.h 和soapMappBindingProxy.cpp
      这两个文件是客户端代码的一个简单封装,它封装了底层通信,并向外提供一个很简单的界面,该界面展示了用户能够使用的所有服务(由WSDL所描述)。
  4). soapH.h和soapC.cpp
      这个两个文件是soap的序列和反序列化代码。

附2 :设置字符编码
    在利用gSoap编写Web Service客户端和服务器端的程序时,需要设置其编码方式。接口为:soapsetmode,其实它是就是一个宏:

?
1
#define soap_set_mode(soap, n) ((soap)->imode |= (n), (soap)->omode |= (n))

    如果要设置为UTF-8 ,可以如下调用:

?
1
soap_set_mode(&soap, SOAP_C_UTFSTRING);

    详细信息可参考该宏所在文件:stdsoap2.h