使用ASPNET构造一个简单的XML Web服务是相对容易的然而XML Web服务的真正的强大的功能只有等你研究了基础结构以后才能领悟XML Web服务是建立在NET框架和公共语言运行时间基础上的一个XML Web服务可以利用这些技术例如ASPNET支持的性能状态管理和验证全都可被用来构造XML Web服务
XML Web服务的基础结构是构建来符合象SOAPXML和WSDL这样的行业标准并且它允许其他的平台的客户端与XML Web服务互操作只要一个客户端可以发送符合标准的SOAP消息依据格式化的服务描述那么这个客户端可以调用一个使用ASPNET创建的XML Web服务(不管客户端存在于何种平台)
当你使用ASPNET构造一个XML Web服务时它自动支持客户端使用SOAPHTTPGET和HTTPPOST协议通讯即使HTTPGET和HTTPPOST支持使用URL编码的变量名/变量值对来传送消息支持这两个协议的数据类型也没有支持SOAP协议的数据类型丰富在SOAP中使用XML把数据传送到XML Web服务或从XML Web服务取回消息你可以使用支持丰富的数据类型集的XSD模式定义复杂的数据类型使用ASPNET构造一个XML Web服务的开发者不必明确地定义复杂的数据类型他们可以只构造一个管理类ASPNET处理定义到一个XSD模式的映射类和到XML数据的映射对象实例以便通过网络传输
重要的是要注意XML Web服务并不能取代DCOM我们应该说XML Web服务是跨越使用行业标准的平台通信的一种消息传递基础结构
因为ASPNET提供了为XML Web服务内部工作的基础结构开发者可以集中精力来实现他们的特定的XML Web服务的功能使用ASPNET开发一个XML Web服务从下面三步开始
创建一个带有asmx扩展名的文件
在这个文件里面使用一条指令声明XML Web服务
定义组成XML Web服务功能的XML Web服务方法
XML Web服务是一个强大的技术用于提供可通过因特网变成访问的服务下面的建议将帮助你创建高效的XML Web服务
XML Web服务既支持同步的又支持异步的客户端和存放XML Web服务的服务器之间的通信在同步通信情况下客户端发送一个对服务的请求到服务主机服务器上等待响应这防止客户端在等待结果的时候执行其它的操作然而异步通信导致客户端在等待相应的时候继续处理其它的任务客户端在可用的时候响应服务请求的结果
当你使用Web服务描述语言工具(Wsdlexe)来创建你的代理类的时候它产生类中的方法的标准的同步版本和异步版本异步版本由两个方法组成称为Begin和EndBegin方法用于初始化XML Web服务而End方法取得结果
使用异步通信能够改善系统使用率和避免客户端在它等待XML Web服务结果的时候的延迟
下面的代码示例显示如何从一个客户应用程序产生一个到XML Web服务的异步调用
[C#]
<%@ Page Language=C# %>
<%@ Import Namespace=SystemNet %>
<html>
<script language=C# runat=server>
void EnterBtn_Click(Object Src EventArgs E)
{
MyMathMath math = new MyMathMath();
// Call to Add XML Web service method asynchronously
// and then wait for it to complete
IAsyncResult result =
mathBeginAdd(ConvertToInt(NumText)
ConvertToInt(NumText)
null
null);
// Wait for asynchronous call to complete
resultAsyncWaitHandleWaitOne();
// Complete the asynchronous call to Add XML Web service method
float total = mathEndAdd(result);
// Display results in a Label control
TotalText = Total: + totalToString();
}
</script>
<body>
<form action=MathClientaspx runat=server>
<font face=Verdana>
Enter the two numbers you want to add and then press
the Total button
<p>
Number :
<asp:textbox id=Num
runat=server/>
+
Number :
<asp:textbox id=Num
runat=server/>
=
<asp:button id=Total_Button
text=Total
OnClick=EnterBtn_Click
runat=server/>
<p>
<asp:label id=Total runat=server/>
</font>
</form>
</body>
</html>
[Visual Basic]
<%@ Page Language=VB %>
<%@ Import Namespace=SystemNet %>
<html>
<script language=VB runat=server>
Sub EnterBtn_Click(Src As Object E As EventArgs)
Dim math As New MyMathMath()
Call to Add XML Web service method asynchronously
and then wait for it to complete
Dim result As IAsyncResult = _
mathBeginAdd(ConvertToInt(NumText) _
ConvertToInt(NumText) _
Nothing _
Nothing)
Wait for asynchronous call to complete
resultAsyncWaitHandleWaitOne()
Complete the asynchronous call to Add XML Web service method
Dim addtotal As Single = mathEndAdd(result)
Display results in a Label control
TotalText = Total: & addtotalToString()
End Sub
</script>
<body>
<form action=MathClientaspx runat=server>
<font face=Verdana>
Enter the two numbers you want to add and then press
the Total button
<p>
Number :
<asp:textbox id=Num
runat=server/>
+
Number :
<asp:textbox id=Num
runat=server/>
=
<asp:button id=Total_Button
text=Total
OnClick=EnterBtn_Click
runat=server/>
<p>
<asp:label id=Total runat=server/>
</font>
</form>
</body>
</html>
想获得更多关于异步通信的信息请参阅后面的和XML Web服务异步地通讯
通过因特网产生许多服务请求可能影响客户应用程序的性能当设计你的XML Web服务时通过创建把有关信息集中在一起的方法可以有效利用服务请求例如假定你有一个XML Web服务用来检索一本书的信息我们可以创建一个在一条服务请求中返回所有的信息的方法来代替单独的检索书名作者和出版社的方法一次传送大块的信息比多次传送小块的信息更有效率
下面的代码示例解释如何把有关信息组织到单个XML Web服务方法中
[C#]
<%@ WebService Language=C# Class=DataService %>
using System;
using SystemData;
using SystemDataSqlClient;
using SystemWebServices;
public class DataService {
[WebMethod]
public DataSet GetTitleAuthors() {
SqlConnection myConnection = new SqlConnection(Persist Security Info=False;Integrated Security=SSPI;server=localhost;database=pubs);
SqlDataAdapter myCommand = new SqlDataAdapter (select * from Authors myConnection);
SqlDataAdapter myCommand = new SqlDataAdapter(select * from Titles myConnection);
DataSet ds = new DataSet();
myCommandFill(ds Authors);
myCommandFill(ds Titles);
return ds;
}
}
[Visual Basic]
<%@ WebService Language=VB Class=DataService %>
Imports System
Imports SystemData
Imports SystemDataSqlClient
Imports SystemWebServices
Public Class DataService
<WebMethod> _
Public Function GetTitleAuthors() As DataSet
Dim myConnection As New SqlConnection(Persist Security Info=False;Integrated Security=SSPI;server=localhost;database=pubs)
Dim myCommand As New SqlDataAdapter(select * from Authors myConnection)
Dim myCommand As New SqlDataAdapter(select * from Titles myConnection)
Dim ds As New DataSet()
myCommandFill(ds Authors)
myCommandFill(ds Titles)
Return ds
End Function
End Class
当设计你的XML Web服务时请确保使用标准的面向对象编程操作使用封装来隐藏实现细节对于更复杂的XML Web服务你可以使用继承和多态性来再次使用代码并简化你的设计
下面的代码示例显示如何使用继承来创建一个执行数学计算的XML Web服务
[C#]
<%@ WebService Language=C# Class=Add %>
using System;
using SystemWebServices;
abstract public class MathService : WebService
{
[WebMethod]
abstract public float CalculateTotal(float a float b);
}
public class Add : MathService
{
[WebMethod]
override public float CalculateTotal(float a float b)
{
return a + b;
}
}
public class Subtract : MathService
{
[WebMethod]
override public float CalculateTotal(float a float b)
{
return a b;
}
}
public class Multiply : MathService
{
[WebMethod]
override public float CalculateTotal(float a float b)
{
return a * b;
}
}
public class Divide : MathService
{
[WebMethod]
override public float CalculateTotal(float a float b)
{
if (b==)
return ;
else
return a / b;
}
}
[Visual Basic]
<%@ WebService Language=VB Class=Add %>
Imports System
Imports SystemWebServices
MustInherit Public Class MathService : Inherits WebService
<WebMethod> _
Public MustOverride Function CalculateTotal(a As Single _
b As Single) As Single
End Class
Public Class Add : Inherits MathService
<WebMethod> Public Overrides Function CalculateTotal(a As Single b As Single) As Single
Return a + b
End Function
End Class
Public Class Subtract : Inherits MathService
<WebMethod> Public Overrides Function CalculateTotal(a As Single b As Single) As Single
Return a b
End Function
End Class
Public Class Multiply : Inherits MathService
<WebMethod> Public Overrides Function CalculateTotal(a As Single b As Single) As Single
Return a * b
End Function
End Class
Public Class Divide : Inherits MathService
<WebMethod> Public Overrides Function CalculateTotal(a As Single b As Single) As Single
If b = Then
Return
Else
Return a / b
End If
End Function
End Class
使用输出缓沖来改善你的XML Web服务的性能当输出缓沖开启时服务请求的结果被保存在输出缓沖中一段指定的时间如果一个类似的XML Web服务请求被产生结果可以从缓沖中取得而不用重新计算这样就通过减少XML Web服务服务器所需的处理来改善了XML Web服务的反馈时间高速缓存可在客户端和服务器两者上执行Duration属性允许你指定高速缓沖保存XML Web服务输出的时间
在客户端上使用输出高速缓沖的指令是
<%@ OutputCache Duration= %>
下面的代码示例显示如何在客户应用程序上使用Duration属性来指定输出高速缓沖为秒
[C#]
<%@ Page Language=C# %>
<%@ Import Namespace=SystemNet %>
<%@ OutputCache Duration= VaryByParam=none %>
<html>
<script language=C# runat=server>
void EnterBtn_Click(Object Src EventArgs e)
{
MyMathMath math = new MyMathMath();
// Call the XML Web service
float total = mathAdd(ConvertToInt(NumText)ConvertToInt(NumText));
// Display the results in a Label control
TotalText = Total: + totalToString();
}
</script>
<body>
<form action=MathClientaspx runat=server>
<font face=Verdana>
Enter the two numbers you want to add and press
the Total button
<p>
Number :
<asp:textbox id=Num runat=server/>
+ Number :
<asp:textbox id=Num runat=server/>
= <asp:button id=Total_Button text=Total OnClick=EnterBtn_Click runat=server/>
<p>
<asp:label id=Total runat=server/>
</font>
</form>
</body>
</html>
[Visual Basic]
<%@ Page Language=VB %>
<%@ Import Namespace=SystemNet %>
<%@ OutputCache Duration= VaryByParam=none %>
<html>
<script language=VB runat=server>
Sub EnterBtn_Click(Src As Object e As EventArgs)
Dim math As New MyMathMath()
Call the XML Web service
Dim addtotal As Single = mathAdd(ConvertToInt(NumText) ConvertToInt(NumText))
Display the results in a Label control
TotalText = Total: & addtotalToString()
End Sub
</script>
<body>
<form action=MathClientaspx runat=server>
<font face=Verdana>
Enter the two numbers you want to add and press
the Total button
<p>
Number :
<asp:textbox id=Num runat=server/>
+
Number :
<asp:textbox id=Num runat=server/>
= <asp:button id=Total_Button text=Total OnClick=EnterBtn_Click runat=server/>
<p>
<asp:label id=Total runat=server/>
</font>
</form>
</body>
</html>
你还可以使用WebMethod属性类的CacheDuration属性来在服务器上允许高速缓沖下面的代码示例显示如何在XML Web服务方法上使用CacheDuration属性来指定输出高速缓沖为秒
[C#]
<%@ WebService Language=C# Class=MathService %>
using System;
using SystemWebServices;
public class MathService : WebService {
[WebMethod(CacheDuration=)]
public float Add(float a float b)
{
return a + b;
}
[WebMethod(CacheDuration=)]
public float Subtract(float a float b)
{
return a b;
}
[WebMethod(CacheDuration=)]
public float Multiply(float a float b)
{
return a * b;
}
[WebMethod(CacheDuration=)]
public float Divide(float a float b)
{
if (b==) return ;
return a / b;
}
}
[Visual Basic]
<%@ WebService Language=VB Class=MathService %>
Imports System
Imports SystemWebServices
Public Class MathService
Inherits WebService
<WebMethod(CacheDuration := )> _
Public Function Add(a As Single b As Single) As Single
Return a + b
End Function
<WebMethod(CacheDuration := )> _
Public Function Subtract(a As Single b As Single) As Single
Return a b
End Function
<WebMethod(CacheDuration := )> _
Public Function Multiply(a As Single b As Single) As Single
Return a * b
End Function
<WebMethod(CacheDuration := )> _
Public Function Divide(a As Single b As Single) As Single
If b = Then
Return
End If
Return a / b
End Function
End Class
当设计你的XML Web服务时努力遵循如何格式化模式的结构
XML Web服务使用SOAP作为主要的传送和序列化协议
一个SOAP消息由一个可选择的头体和消息体组成头部分包含可以被Web服务器体系结构处理的信息SOAP没有定义任何头消息体部分包含由应用程序处理的信息例如用于XML Web服务的参数或返回值
提供用于你的XML Web服务的文档如一个静态HTML文件描述你的服务的操作和数据结构还包括如何使用这个XML Web服务的示例不要依靠服务描述或服务帮助页面作为你唯一的文档