加入收藏 | 设为首页 | 会员中心 | 我要投稿 李大同 (https://www.lidatong.com.cn/)- 科技、建站、经验、云计算、5G、大数据,站长网!
当前位置: 首页 > 综合聚焦 > 服务器 > 安全 > 正文

MFC客户端WebService(gSOAP)天气预报

发布时间:2020-12-16 23:15:45 所属栏目:安全 来源:网络整理
导读:本例以 天气预报 为例 一、新建MFC工程(本例使用VS2013) ????略 二、下载gSOAP ??下载地址: gSOAP Toolkit 三、工具介绍 ??? 1、解压gSOAP(本例下载gSOAP版本为2.8.18 ),得到gsoap-2.8文件夹(存放路径在H:WorkSpaceC++gSOAP 目录下)。 ??? 2、gSOAP工具

本例以天气预报为例


一、新建MFC工程(本例使用VS2013)

????略


二、下载gSOAP

??下载地址: gSOAP Toolkit


三、工具介绍

??? 1、解压gSOAP(本例下载gSOAP版本为2.8.18),得到gsoap-2.8文件夹(存放路径在H:WorkSpaceC++gSOAP目录下)。

??? 2、gSOAP工具介绍(gsoap-2.8gsoapbinwin32)

??????????在该目录下存在2个工具: wsdl2h.exe及soapcpp2.exe

????????? (1) wsdl2h.exe: 根据WSDL生成C/C++风格的头文件

?????????????? 使用方法:?wsdl2h.exe -o XXX.h WSDL文件名或URL(末尾加:?wsdl)

?????????????? 参数说明:
???????????????????????????? -o: 文件名,指定输出头文件
?????????????????????????????-n: 名空间前缀 代替默认的ns
?????????????????????????????-c: 产生纯C代码,否则是C++代码
?????????????????????????????-s: 不要使用STL代码
?????????????????????????????-t: 文件名,指定type map文件,默认为typemap.dat,建立一个字符转换规则文件wsmap.dat,文件内容为xsd__string = | std::wstring | wchar_t*
?????????????????????????????-e 禁止为enum成员加上名空间前缀

??????? ? (2) soapcpp2.exe: 根据头文件自动生成调用远程 SOAP服务的客户端代码(称为存根:Stub)和提供SOAP服务的框架代码(称为框架:Skeleton),另外它也能从头文件生成WSDL文件。

????????????? 使用方法:?soapcpp2 -x -C WeatherWeb.h

?????????????参数说明:
???????????????????????????? -C: 仅生成客户端代码
???????????????????????????? -S: 仅生成服务器端代码
???????????????????????????? -L: 不要产生soapClientLib.c和soapServerLib.c文件
???????????????????????????? -c: 产生纯C代码,否则是C++代码(与头文件有关)
???????????????????????????? -I: 指定import路径(此项是必要的,如果前面为指定-s)
???????????????????????????? -x: 不要产生XML示例文件
???????????????????????????? -i: 代表使用Proxy(代理),生成C++包装,客户端为xxxxProxy.h(.cpp),服务器端为xxxxService.h(.cpp)。

四、生成文件

??? 1、启动cmd.exe

??? 2、进入工具目录: cd H:WorkSpaceC++gSOAPgsoap-2.8gsoapbinwin32

??? 3、根据URL(http://www.webxml.com.cn/WebServices/WeatherWebService.asmx)生成WeatherWeb.h文件

??????????执行: wsdl2h -oWeatherWeb.h -s -n Weather -t ....typemap.dat?http://www.webxml.com.cn/WebServices/WeatherWebService.asmx?wsdl

????????? 其中:gSOAP默认生成的名称以soap_call___ns开头,用Weather代替ns(-n Weather)

??? 4、解析生成的头文件(如本例WeatherWeb.h)

????????? 两种方式生成C++文件方式(2选1): 非代理方式(生成:XXXProxy.cpp)代理方式(生成XXXClient.cpp)

????????? (1)?非代理方式:

????????????? 执行: soapcpp2 -x -C WeatherWeb.h -I H:WorkSpaceC++gSOAPgsoap-2.8gsoapimport

?????????????????????? 其中: import路径需要根据实际的结对路径

????????????? 生成的文件: soapC.cpp,soapH.h,soapStub.h,soapClient.cpp,soapClientLib.cpp,WeatherWebServiceSoap.nsmap

?????????????????????? 注:?拷贝文件到工程中时不能拷贝soapClientLib.cpp文件。

???????? (2) 代理方式

???????????? 执行: soapcpp2 -i -x -C WeatherWeb.h -I H:WorkSpaceC++gSOAPgsoap-2.8gsoapimport

?????????????????????? 其中: import路径需要根据实际的结对路径

???????????? 生成的文件: soapC.cpp,soapWeatherWebServiceSoapProxy.h,soapWeatherWebServiceSoapProxy.cpp,WeatherWebServiceSoap.nsmap

五、添加生成文件到MFC工程中

??? 1、把所有生成文件拷贝到MFC工程中,对于代理方式需要拷贝soapClientLib.cpp文件否则报错,另外拷贝gsoap-2.8gsoap目录下的stdsoap2.h和stdsoap2.cpp文件到MFC工程目录中。

??? 2、在所有的.cpp文件中添加: #include "stdafx.h"

??? 3、在stdsoap2.cpp文件中添加: #include"WeatherWebServiceSoap.nsmap"

??? 4、窗口头文件(XXXDlg.h)添加: #include "soapH.h"


六、测试

??? 1、非代理方式:

??????????

void CgSOAPWeatherDlg::OnBnClickedButton1()
{
	int cnt = 0;
	struct soap soap;
	soap_init(&soap);
	soap_set_mode(&soap,SOAP_C_UTFSTRING);
	soap.mode |= SOAP_C_UTFSTRING;

	_ns1__getWeatherbyCityName weatherbyCityName;
	_ns1__getWeatherbyCityNameResponse weatherbyCityNameResponse;

	weatherbyCityName.theCityName = "北京";

	CStringList list;
	if (SOAP_OK == soap_call___ns1__getWeatherbyCityName(&soap,NULL,&weatherbyCityName,weatherbyCityNameResponse))
	{
#if 0
		char **weather = weatherbyCityNameResponse.getWeatherbyCityNameResult->string;

		while (*weather)
		{
			CString cs;

			MultiByte2WideChar(*weather++,cs);
			list.AddTail(cs);
		}
#else
		cnt = weatherbyCityNameResponse.getWeatherbyCityNameResult->__sizestring;
		for (int i = 0; i < cnt; i++)
		{
			CString cs;

			MultiByte2WideChar(weatherbyCityNameResponse.getWeatherbyCityNameResult->string[i],cs);
			list.AddTail(cs);
		}
#endif
	}
	soap_destroy(&soap);
	soap_end(&soap);
	soap_done(&soap);
}

void MultiByte2WideChar(char* src,const wchar_t* dst)
{
	if (NULL == src || NULL == dst)
	{
		return;
	}
	int srcSize = strlen(src);
	int iLen = MultiByteToWideChar(CP_UTF8,src,srcSize,0);
	if (0 == iLen)
	{
		return;
	}

	MultiByteToWideChar(CP_UTF8,strlen(src),(LPWSTR)dst,iLen * 2);
}

??? 2、代理方式:

void WideChar2MultiByte(const wchar_t* src,char* dst);
void MultiByte2WideChar(char* src,const wchar_t* dst);

void CWeatherWebServiceDlg::OnBnClickedWeatherwebservicesoap()
{
	// TODO:  在此添加控件通知处理程序代码
	int result = 0;
	int cnt = 0;
	int i = 0;
	CString cs;

	WeatherWebServiceSoapProxy wwssp(SOAP_C_UTFSTRING);
	//wwssp.reset();
	//wwssp.WeatherWebServiceSoapProxy_init(SOAP_C_UTFSTRING,SOAP_IO_DEFAULT);

	_Weather1__getSupportCity cityName;
	_Weather1__getSupportCityResponse  citySupportCityResponse;
#if 0
	cityName.byProvinceName = "北京";
#else
	cs = "北京";
	cnt = (2 * cs.GetLength()) + 1 ;
	cityName.byProvinceName = new char[cnt];
	memset(cityName.byProvinceName,cnt);
	WideChar2MultiByte(cs,cityName.byProvinceName);
	cs.Empty();
#endif
	result = wwssp.getSupportCity(&cityName,citySupportCityResponse);
	if (SOAP_OK == result)
	{
		cnt = citySupportCityResponse.getSupportCityResult->__sizestring;
		for (i = 0; i < cnt; i++)
		{
			MultiByte2WideChar(citySupportCityResponse.getSupportCityResult->string[i],cs);
		}
	}

	_Weather1__getWeatherbyCityName weatherbyCityName;
	_Weather1__getWeatherbyCityNameResponse  weatherbyCityNameResponse;

#if 1
	weatherbyCityName.theCityName = "北京";
#else
	weatherbyCityName.theCityName = new char[cnt];
	memset(weatherbyCityName.theCityName,weatherbyCityName.theCityName);
#endif
	result = wwssp.getWeatherbyCityName(&weatherbyCityName,weatherbyCityNameResponse);

	CStringList list;
	if (SOAP_OK == result)
	{
		cnt = weatherbyCityNameResponse.getWeatherbyCityNameResult->__sizestring;
		for (i = 0; i < cnt; i++)
		{
			cs.Empty();
			MultiByte2WideChar(weatherbyCityNameResponse.getWeatherbyCityNameResult->string[i],cs);
			list.AddTail(cs);
		}
	}

	wwssp.destroy();
}

void MultiByte2WideChar(char* src,const wchar_t* dst)
{
	int iLen = MultiByteToWideChar(CP_UTF8,iLen * 2);
}

void WideChar2MultiByte(const wchar_t* src,char* dst)
{
	int iLen = WideCharToMultiByte(CP_UTF8,-1,NULL);
	if (0 == iLen)
	{
		return;
	}

	WideCharToMultiByte(CP_UTF8,dst,iLen,NULL);
}

(编辑:李大同)

【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容!

    推荐文章
      热点阅读