IT博客汇
  • 首页
  • 精华
  • 技术
  • 设计
  • 资讯
  • 扯淡
  • 权利声明
  • 登录 注册

    [原]VS2010使用c++、gSOAP创建的WebService 图文教程

    testcs_dn发表于 2016-05-23 10:59:34
    love 0

    VS2010使用c++、gSOAP创建的WebService 图文教程

    环境

    操作系统:Windows 7
    gsoap版本:2.8.32
    C++编译器/开发环境:Visual Studio 2010

    gSOAP是什么

    gSOAP编译工具提供了一个SOAP/XML 关于C/C++ 语言的实现,从而让C/C++语言开发web服务或客户端程序的工作变得轻松了很多。绝大多数的C++web服务工具包提供一组API函数类库来处理特定的SOAP数据结构,这样就使得用户必须改变程序结构来适应相关的类库。与之相反,gSOAP利用编译器技术提供了一组透明化的SOAP API,并将与开发无关的SOAP实现细节相关的内容对用户隐藏起来。

    下载gSOAP工具包

    http://120.52.73.49/jaist.dl.sourceforge.net/project/gsoap2/gSOAP/gsoap_2.8.32.zip

    gSOAP Toolkit
    解压后把下面两个文件复制到“C:\Windows”目录下,或者添加环境变量,这 样就可以在任何位置执行命令:

    soapcpp2.exe

    wsdl2h.exe

    一、编写一个头文件

    文件名:itoa.h

    //gsoap ns service name: itoa
    //gsoap ns service namespace: http://localhost/itoa.wsdl
    //gsoap ns service location: http://localhost
    //gsoap ns service executable: itoa.cgi
    //gsoap ns service encoding: encoded
    //gsoap ns schema namespace: urn:itoa
    
    int ns__itoa(int i, char **a);

    二、生成wsdl和服务端代码

    打开CMD命令行,切换目录到“itoa.h”文件所在目录,执行命令:

    soapcpp2 -S -I C:\gSOAP\gsoap-2.8\gsoap\import itoa.h

    执行完成后,会在文件夹下面生成以下文件:


    三、创建项目

    1、打开VS2010,文件》新建》项目


    2、左侧模板中选择Visual c++,右侧选择 Win32 控制台应用程序,输入项目名称,选择保存位置,勾选“为解决方案创建目录”,确定


    3、下一步


    4、取消“预编译头”的选中状态,完成


    四、配置编译

    1、打开项目文件目录


    2、将第二步生成的代码复制到项目目录下

    3、添加文件到项目


    4、选择要添加到项目的文件

    这里没有列全,有几个文件(stdsoap2.h,stdsoap2.cpp)是需要从gSOAP的源码目录复制过来的

    注意:并不是要把所有文件都添加到项目里!


    5、替换“itoaServer.cpp”文件的内容,使用以下代码:

    // itoaServer.cpp : 定义控制台应用程序的入口点。
    //
    #include "soapH.h"
    #include <windows.h>
    #include "itoa.nsmap"
    
    #define BACKLOG (100)    /* Max. request backlog */
    DWORD WINAPI process_request(LPVOID*);
    int http_get(struct soap * soap);
    
    int main(int argc, char **argv) {
    	struct soap soap;
    	struct soap *tsoap;
    	const char* fmt = "accepts socket %d connection from IP %d.%d.%d.%d\n";
    
    	soap_init(&soap);
    
    	if ( argc < 2 ) {
    		soap_serve(&soap);
    		soap_destroy(&soap);
    		soap_end(&soap);
    	}
    	else {
    		soap.send_timeout = 60;
    		soap.recv_timeout = 60;
    		soap.accept_timeout = 3600;
    		soap.max_keep_alive = 100;
    
    		soap.fget = http_get;
    
    		DWORD tid;
    		HANDLE hThread;
    
    		int port = atoi(argv[1]); // first command-line arg is port
    		SOAP_SOCKET m, s;
    
    		m = soap_bind(&soap, NULL, port, BACKLOG);
    		if ( !soap_valid_socket(m) ) exit(1);
    
    		printf("Socket connection successful %d\n", m);
    		for ( ; ; ) {
    			s = soap_accept(&soap);
    			if ( !soap_valid_socket(s) ) {
    				if ( soap.errnum ) {
    					soap_print_fault(&soap, stderr);
    					exit(1);
    				}
    
    				printf("server timed out\n");
    				break;
    			}
    
    			printf(fmt, s, (soap.ip>>24)&0xFF, (soap.ip>>16)&0xFF, (soap.ip>>8)&0xFF, soap.ip&0xFF);
    
    			tsoap = soap_copy(&soap); // make a safe copy
    			if ( !tsoap ) break;
    
    			hThread = CreateThread(NULL, 0, (LPTHREAD_START_ROUTINE)process_request, tsoap, 0, &tid);
    			if ( hThread == NULL ) {
    				printf("can not create a thread for SOAP request processing.\n");
    				exit(-1);
    			}
    		}
    	}
    
    	soap_done(&soap);
    	return 0;
    }
    
    DWORD WINAPI process_request(LPVOID* soap) {
    	soap_serve((struct soap*)soap);
    	soap_destroy((struct soap*)soap);
    	soap_end((struct soap*)soap);
    	soap_done((struct soap*)soap);
    	free(soap);
    	return 0;
    }
    
    // 服务消息的实现代码
    int ns__itoa(struct soap *soap, int i, char **a) 
    { 
    	*a = (char*)soap_malloc(soap, 11); 
    	sprintf(*a, "%d", i); 
    	return SOAP_OK; 
    }
    
    int http_get(struct soap * soap) {
    	FILE *fd = NULL;
    
    	printf("call http_get.\n");
    	char *s = strchr(soap->path, '?');
    	if ( !s || strcmp(s, "?wsdl") ) return SOAP_GET_METHOD;
    
    	fd = fopen("itoa.wsdl", "rb");
    	if ( !fd ) return 404;
    
    	soap->http_content = "text/xml";
    	soap_response(soap, SOAP_FILE);
    
    	for ( ; ; ) {
    		size_t r = fread(soap->tmpbuf, 1, sizeof(soap->tmpbuf), fd);
    		if ( !r ) break;
    		if ( soap_send_raw(soap, soap->tmpbuf, r) ) break;
    	}
    
    	fclose(fd);
    	soap_end_send(soap);
    
    	return SOAP_OK;
    }
    
    6、编译生成,在项目名称上单击鼠标右键,选择重新生成

    选择重新生成的好处是避免之前的生成错误影响本次生成的结果

    7、生成成功后,从项目目录下将“itoa.wsdl”文件复制到输出目录


    五、启动WebService并测试

    1、打开CMD命令提示符

    2、切换目录到生成输入目录

    3、执行命令:itoaServer.exe 8087

    后面的端口是可以自己定义的,你想用什么就输入什么,只要是未占用的,不是其它协议/服务常用的;


    4、允许访问


    5、打开浏览器,输入你的IP:端口号/itoa?wsdl 访问看看吧,正常的话应该显示“itoa.wsdl”文件的内容


    结束语

    别人如果想访问你的WebService,必须能够拿到你的 wsdl 文件(本例中为:itoa.wsdl)才行,还有就是你的WebService运行的服务器IP及使用的端口。

    这里只讲了如何用c++,gSOAP开发一个WebService供别人调用,以后再讲讲如何调用的吧。


    参考:

    http://www.genivia.com/products.html

    http://www.genivia.com/doc/soapdoc2.html

    http://www.cppblog.com/qiujian5628/archive/2008/06/19/54019.html

    http://www.cppblog.com/qiujian5628/archive/2008/09/16/61945.html





沪ICP备19023445号-2号
友情链接