您的位置:首页 > 其它

使用gSOAP开发实例(1) 股票信息客户端程序

2014-01-24 20:16 615 查看
/article/8534413.html

gSOAP 是一套开源的 C/C++ 软件工具包,使用它能够很方便地开发 SOAP 网页服务和基于 XML 的应用程序,就像 JAVA里面的 axis 。

首先,我们需要从以下地址下载最新版本的 gSOAP 2.7.17 :
https://sourceforge.net/projects/gsoap2/files/

其次, gSOAP 依赖于 Bison 和 Flex ,编译 gSOAP 的时候会用到,如果没有,从这里下载:
Bison : http://www.gnu.org/software/bison/
Flex : http://flex.sourceforge.net/

关于这两个工具包的安装步骤可以参考最新的 LFS 手册:
http://www.linuxfromscratch.org/lfs/view/6.4/chapter06/bison.html
http://www.linuxfromscratch.org/lfs/view/6.4/chapter06/flex.html

如果不是 root 用户,没有安装权限的话,可以在 configure 的时候使用 --prefix=/path/to/your/own/directory ,指定安装路径。装好之后,修改用户目录的 .profile 文件,更改PATH 和 LD_LIBRARY_PATH 环境变量,使得系统能够正确搜索到你安装后的可执行文件和库文件即可。

这两步准备工作完成后,我们就可以开始编译 gSOAP 。 Linux 下编译安装源代码包无非就是 tar zxvf xxx ,configure , make , make install ,由于我不是 root 用户,没有安装的权限,那么不执行 make install 也可以使用 gSOAP 开发程序,只不过使用的时候常常需要指定路径。

现在我们的目标是开发一个获取股票信息的客户端程序。服务端采用 webxml 开发的 WSDL ,其 URL 是:
http://webservice.webxml.com.cn/WebServices/ChinaStockWebService.asmx?wsdl

首先,在 gsoap-2.7/gsoap/wsdl/ 下创建一个 stock 目录
-bash-3.2$ mkdir -p stock

改变当前路径为 stock
-bash-3.2$ cd stock

使用 wsdl2h 生成 stock.h ,如果希望生成纯 C 代码,需要加上 -c 参数,否则,将会生成 C++ 代码
-bash-3.2$ ../wsdl2h -c -o stock.h http://webservice.webxml.com.cn/WebServices/ChinaStockWebService.asmx?wsdl
** The gSOAP WSDL/Schema processor for C and C++, wsdl2h release 1.2.17
** Copyright (C) 2000-2010 Robert van Engelen, Genivia Inc.
** All Rights Reserved. This product is provided "as is", without any warranty.
** The wsdl2h tool is released under one of the following two licenses:
** GPL or the commercial license by Genivia Inc. Use option -l for more info.

Saving stock.h

Cannot open file 'typemap.dat'
Problem reading type map file 'typemap.dat'.
Using internal type definitions for C instead.

Connecting to 'http://webservice.webxml.com.cn/WebServices/ChinaStockWebService.asmx?wsdl' to retrieve WSDL/XSD...
Connected, receiving...
Done reading 'http://webservice.webxml.com.cn/WebServices/ChinaStockWebService.asmx?wsdl'

To complete the process, compile with:
> soapcpp2 stock.h

然后,使用 soapcpp2 生成客户端存根程序和相关的头文件、资源文件,由于我们只开发客户端程序,所以可以指定 -C参数
-bash-3.2$ ../../bin/linux386/soapcpp2 -C stock.h

** The gSOAP code generator for C and C++, soapcpp2 release 2.7.17
** Copyright (C) 2000-2010, Robert van Engelen, Genivia Inc.
** All Rights Reserved. This product is provided "as is", without any warranty.
** The soapcpp2 tool is released under one of the following three licenses:
** GPL, the gSOAP public license, or the commercial license by Genivia Inc.

Saving soapStub.h annotated copy of the input declarations
Saving soapH.h interface declarations
Saving soapC.c XML serializers
Saving soapClient.c client calling stubs
Saving soapClientLib.c client stubs with serializers (use only for libs)
Using ns2 service name: ChinaStockWebServiceSoap
Using ns2 service style: document
Using ns2 service encoding: literal
Using ns2 service location: http://webservice.webxml.com.cn/WebServices/ChinaStockWebService.asmx Using ns2 schema namespace: http://WebXml.com.cn/ChinaStockWebServiceSoap Saving ChinaStockWebServiceSoap.getStockImageByCode.req.xml sample SOAP/XML request
Saving ChinaStockWebServiceSoap.getStockImageByCode.res.xml sample SOAP/XML response
Saving ChinaStockWebServiceSoap.getStockImageByteByCode.req.xml sample SOAP/XML request
Saving ChinaStockWebServiceSoap.getStockImageByteByCode.res.xml sample SOAP/XML response
Saving ChinaStockWebServiceSoap.getStockImage_kByCode.req.xml sample SOAP/XML request
Saving ChinaStockWebServiceSoap.getStockImage_kByCode.res.xml sample SOAP/XML response
Saving ChinaStockWebServiceSoap.getStockImage_kByteByCode.req.xml sample SOAP/XML request
Saving ChinaStockWebServiceSoap.getStockImage_kByteByCode.res.xml sample SOAP/XML response
Saving ChinaStockWebServiceSoap.getStockInfoByCode.req.xml sample SOAP/XML request
Saving ChinaStockWebServiceSoap.getStockInfoByCode.res.xml sample SOAP/XML response
Saving ChinaStockWebServiceSoap.nsmap namespace mapping table
Using ns3 service name: ChinaStockWebServiceSoap12
Using ns3 service style: document
Using ns3 service encoding: literal
Using ns3 service location: http://webservice.webxml.com.cn/WebServices/ChinaStockWebService.asmx Using ns3 schema namespace: http://WebXml.com.cn/ChinaStockWebServiceSoap12 Saving ChinaStockWebServiceSoap12.getStockImageByCode.req.xml sample SOAP/XML request
Saving ChinaStockWebServiceSoap12.getStockImageByCode.res.xml sample SOAP/XML response
Saving ChinaStockWebServiceSoap12.getStockImageByteByCode.req.xml sample SOAP/XML request
Saving ChinaStockWebServiceSoap12.getStockImageByteByCode.res.xml sample SOAP/XML response
Saving ChinaStockWebServiceSoap12.getStockImage_kByCode.req.xml sample SOAP/XML request
Saving ChinaStockWebServiceSoap12.getStockImage_kByCode.res.xml sample SOAP/XML response
Saving ChinaStockWebServiceSoap12.getStockImage_kByteByCode.req.xml sample SOAP/XML request
Saving ChinaStockWebServiceSoap12.getStockImage_kByteByCode.res.xml sample SOAP/XML response
Saving ChinaStockWebServiceSoap12.getStockInfoByCode.req.xml sample SOAP/XML request
Saving ChinaStockWebServiceSoap12.getStockInfoByCode.res.xml sample SOAP/XML response
Saving ChinaStockWebServiceSoap12.nsmap namespace mapping table

Compilation successful

接着,就可以利用存根程序提供的接口编写客户端程序了,过程相当简单。

[cpp] view plaincopy

#include "soapH.h"
#include "ChinaStockWebServiceSoap12.nsmap"
int main(int argc, char **argv) {
if ( argc != 2 ) {
printf("Usage: %s stock_code/n", argv[0]);
exit(-1);
}
struct soap soap;
soap_init(&soap);
struct _ns1__getStockInfoByCode request;
struct _ns1__getStockInfoByCodeResponse response;
request.theStockCode = argv[1];
if ( soap_call___ns3__getStockInfoByCode(&soap, NULL, NULL, &request, &response) == SOAP_OK ) {
int element_counter = response.getStockInfoByCodeResult->__sizestring;
int i = 0;
for ( i = 0; i < element_counter; i++ ) {
switch ( i ) {
case 0 : printf("Stock code : "); break;
case 1 : printf("Stock name : "); break;
case 2 : printf("Timestamp : "); break;
case 3 : printf("Latest price : "); break;
case 4 : printf("Closing price T-1 : "); break;
case 5 : printf("Opening price : "); break;
case 6 : printf("Ups and downs : "); break;
case 7 : printf("Mininum price : "); break;
case 8 : printf("Maxinum price : "); break;
case 9 : printf("Amount of up/down : "); break;
case 10 : printf("Trading volume : "); break;
case 11 : printf("Trading amount : "); break;
case 12 : printf("Buy price : "); break;
case 13 : printf("Sell price : "); break;
case 14 : printf("Agency trans : "); break;
case 15 : printf("Buy 1 : "); break;
case 16 : printf("Buy 2 : "); break;
case 17 : printf("Buy 3 : "); break;
case 18 : printf("Buy 4 : "); break;
case 19 : printf("Buy 5 : "); break;
case 20 : printf("Sell 1 : "); break;
case 21 : printf("Sell 2 : "); break;
case 22 : printf("Sell 3 : "); break;
case 23 : printf("Sell 4 : "); break;
case 24 : printf("Sell 5 : "); break;
default : break;
}
printf("%s/n", response.getStockInfoByCodeResult->string[i]);
}
}
else {
soap_print_fault(&soap, stderr);
}
soap_destroy(&soap);
soap_end(&soap);
soap_done(&soap);
return 0;
}

基本上都是套用差不多的格式,不清楚具体参数意义的话,可以参考 soapcpp2 生成的存根程序及其头文件。把上述代码保存为 stock.c ,编译命令是:
gcc -O2 -o stock stock.c soapC.c soapClient.c ../../stdsoap2.c -I../.. -L../.. –lgsoap

可以看到,编译时,除了 stock.c ,还需要包括存根程序 soapC.c 和 soapClient.c ,以及 gSOAP 运行时引擎stdsoap2.c ,另外还需要指定头文件搜索路径、库文件搜索路径,以及告诉编译器,链接 libgsoap

一切正常的话,就大功告成了:
-bash-3.2$ ./stock sh600000
Stock code : sh600000
Stock name : 浦发银行
Timestamp : 2010-07-08 15:02:07
Latest price : 13.79
Closing price T-1 : 13.76
Opening price : 13.88
Ups and downs : 0.03
Mininum price : 13.73
Maxinum price : 14.06
Amount of up/down : 0.22%
Trading volume : 451017.84
Trading amount : 62602.5809
Buy price : 13.78
Sell price : 13.79
Agency trans : 34.07%
Buy 1 : 13.78 / 1622.88
Buy 2 : 13.77 / 687.10
Buy 3 : 13.76 / 785.00
Buy 4 : 13.75 / 1430.00
Buy 5 : 13.74 / 264.00
Sell 1 : 13.79 / 33.70
Sell 2 : 13.80 / 64.17
Sell 3 : 13.81 / 290.80
Sell 4 : 13.82 / 1318.70
Sell 5 : 13.83 / 647.70
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: 
相关文章推荐