C#下的webservcie 实现代码和 在vc和python下的调用实现

发表于:2007-06-30来源:作者:点击数: 标签:
C#下的webservcie 实现代码,很简单一看就清楚了是完成什么样的功能了 using System; using System.Collections; using System.ComponentModel; using System.Data; using System.Diagnostics; using System.Web; using System.Web.Services; namespace WebHel
C#下的webservcie 实现代码,很简单一看就清楚了是完成什么样的功能了

using System;
using System.Collections;
using System.ComponentModel;
using System.Data;
using System.Diagnostics;
using System.Web;
using System.Web.Services;

namespace WebHelloZ5
{
/// <summary>
/// Service1 的摘要说明。
/// </summary>
public class Service1 : System.Web.Services.WebService
{
public Service1()
{
//CODEGEN:该调用是 ASP.NET Web 服务设计器所必需的
InitializeComponent();
}

#region Component Designer generated code

//Web 服务设计器所必需的
private IContainer components = null;

/// <summary>
/// 设计器支持所需的方法 - 不要使用代码编辑器修改
/// 此方法的内容。
/// </summary>
private void InitializeComponent()
{
}

/// <summary>
/// 清理所有正在使用的资源。
/// </summary>
protected override void Dispose( bool disposing )
{
if(disposing && components != null)
{
components.Dispose();
}
base.Dispose(disposing);
}

#endregion

// WEB 服务示例
// HelloWorld() 示例服务返回字符串 Hello World
// 若要生成,请取消注释下列行,然后保存并生成项目
// 若要测试此 Web 服务,请按 F5 键

//[WebMethod]
//public string HelloWorld1()
//{
// return "Hello World";
//}

[WebMethod]
public string HelloWorld(int nArg, string strArg)
{
return strArg+ nArg.ToString();
}


}
}


下面就是调用webservice时,网络上大家发送的数据包了

Client请求数据:

POST /WebHelloZ5/Service1.asmx HTTP/1.1
Host: localhost
Content-Type: text/xml
Content-Length: length
SOAPAction: "http://tempuri.org/HelloWorld"

<?xml version="1.0" encoding="utf-8"?>
<soap:Envelope xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
<soap:Body>
<HelloWorld xmlns="http://tempuri.org/">
<nArg>int</nArg>
<strArg>string</strArg>
</HelloWorld>
</soap:Body>
</soap:Envelope>

Server回应数据:

HTTP/1.1 200 OK
Content-Type: text/xml; charset=utf-8
Content-Length: length

<?xml version="1.0" encoding="utf-8"?>
<soap:Envelope xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
<soap:Body>
<HelloWorldResponse xmlns="http://tempuri.org/">
<HelloWorldResult>string</HelloWorldResult>
</HelloWorldResponse>
</soap:Body>
</soap:Envelope>



VC7下的自动生成的代理类,如下所示:

template <typename TClient>
inline HRESULT CService1T<TClient>::HelloWorld(
int nArg,
BSTR strArg,
BSTR* HelloWorldResult
)
{
HRESULT __atlsoap_hr = InitializeSOAP(NULL);
if (FAILED(__atlsoap_hr))
{
SetClientError(SOAPCLIENT_INITIALIZE_ERROR);
return __atlsoap_hr;
}

CleanupClient();

CComPtr<IStream> __atlsoap_spReadStream;
__CService1_HelloWorld_struct __params;
memset(&__params, 0x00, sizeof(__params));
__params.nArg = nArg;
__params.strArg = strArg;

__atlsoap_hr = SetClientStruct(&__params, 0);
if (FAILED(__atlsoap_hr))
{
SetClientError(SOAPCLIENT_OUTOFMEMORY);
goto __skip_cleanup;
}

__atlsoap_hr = GenerateResponse(GetWriteStream());
if (FAILED(__atlsoap_hr))
{
SetClientError(SOAPCLIENT_GENERATE_ERROR);
goto __skip_cleanup;
}

__atlsoap_hr = SendRequest(_T("SOAPAction: \"http://tempuri.org/HelloWorld\"\r\n"));
if (FAILED(__atlsoap_hr))
{
goto __skip_cleanup;
}
__atlsoap_hr = GetReadStream(&__atlsoap_spReadStream);
if (FAILED(__atlsoap_hr))
{
SetClientError(SOAPCLIENT_READ_ERROR);
goto __skip_cleanup;
}

// cleanup any in/out-params and out-headers from previous calls
Cleanup();
__atlsoap_hr = BeginParse(__atlsoap_spReadStream);
if (FAILED(__atlsoap_hr))
{
SetClientError(SOAPCLIENT_PARSE_ERROR);
goto __cleanup;
}

*HelloWorldResult = __params.HelloWorldResult;
goto __skip_cleanup;

__cleanup:
Cleanup();
__skip_cleanup:
ResetClientState(true);
memset(&__params, 0x00, sizeof(__params));
return __atlsoap_hr;
}

流程为:

1 初始化参数列表( SetClientStruct(&__params, 0);)
|
V

2.生成发送数据请求(GenerateResponse(GetWriteStream());SendRequest(_T("SOAPAction: \"http://tempuri.org/HelloWorld\"\r\n"));)
|
V
3.接收和解析回应数据(BeginParse(__atlsoap_spReadStream);)
|
V
4.清理工作


Python代码:

#author:zfive5(zhaozidong)
#email: zfive5@yahoo.com.cn

import httplib
import xml.parsers.expat
import urlparse

class ZFive5Web:

def __init__(self, url,xmlns):
self.url=url
self.xmlns=xmlns
self.ret=""
self.data=""

def gen_request(self,strfunc,strxmlns,dictarg):
ret="<soap:Envelope xmlns:soap=\"http://schemas.xmlsoap.org/soap/envelope/\" xmlns:xsi=\"http://www.w3.org/2001/XMLSchema-instance\" xmlns:xsd=\"http://www.w3.org/2001/XMLSchema\" xmlns:soapenc=\"http://schemas.xmlsoap.org/soap/encoding/\">"
ret+="<soap:Body>"
ret+="<%s xmlns=\"%s/\">"%(strfunc,strxmlns)
for (k,v) in dictarg.items():
if k is int:
ret+="<%s>%s</%s>"%(k,str(v),k)
else:
ret+="<%s>%s</%s>"%(k,v,k)
ret+="</%s>"%(strfunc)
ret+="</soap:Body>"
ret+="</soap:Envelope>"
return ret

def hello_world(self,argl):
func="HelloWorld"
addr=urlparse.urlparse(self.url)
argd={}
argd["nArg"]=argl[0]
argd["strArg"]=argl[1]

try:
header={}
header[@#Host@#]=@#localhost@#
header[@#Content-Type@#]=@#text/xml@#
header[@#SOAPAction@#]=@#\"%s/%s\"@#%(self.xmlns,func)
conn=httplib.HTTPConnection(addr[1])
print self.gen_request(func,self.xmlns,argd)
conn.request(@#POST@#,@#/WebHelloZ5/Service1.asmx@#,self.gen_request(func,self.xmlns,argd),header)
resp=conn.getresponse()
dataxml=resp.read()
def start_element(name, attrs):
pass

def end_element(name):
if name==@#HelloWorldResult@#:
self.ret=self.data
#elif name==@#OurPutArg@#:
# argl[0]=self.temp

def char_data(data):
self.data=data

pxml=xml.parsers.expat.ParserCreate()
pxml.StartElementHandler = start_element
pxml.EndElementHandler = end_element
pxml.CharacterDataHandler = char_data
pxml.Parse(dataxml, 1)
except:
return None
return self.ret

def test():
A=ZFive5Web("http://127.0.0.1/WebHelloZ5/Service1.asmx","http://tempuri.org")
l=[1,@#121@#]
ret=A.hello_world([1,@#121@#])

if __name__ == @#__main__@#:
assert test()

流程与上差不多如果实现分析.asmx?WDSL文件就完全可以vs中的添加web引用的功能,这里
剩下的主要是特殊符号的处理和类型转化工作。


原文转自:http://www.ltesting.net