介紹
WCF(Windows Communication Foundation) - 可靠性消息(ReliableMessaging):
·通過重試的方法來保證消息的可靠傳遞,默認為8次
·當配置了“有序傳遞”的時候,客戶端和服務端會開辟緩沖區,服務端緩沖區在接到所有客戶端發來的消息後,按照客戶端調用的順序排序各個消息,然後有序地調用服務端
示例
1、服務
IReliable.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.ServiceModel;
namespace WCF.ServiceLib.Message
{
/**//// <summary>
/// 演示可靠性消息的接口
/// </summary>
/// <remarks>
/// DeliveryRequirements - 指定綁定必須提供給服務或客戶端實現的功能要求
/// RequireOrderedDelivery - 如果指示 WCF 確認綁定必須支持排序消息,則為 true;否則為 false。默認值為 false。如果設置為了 true,那麼也需要在配置的時候將order設置為 true
/// </remarks>
[ServiceContract]
[DeliveryRequirements(RequireOrderedDelivery = true)]
public interface IReliable
{
/**//// <summary>
/// 將字符串寫入文本文件
/// </summary>
/// <param name="str">需要寫入文本文件的字符串</param>
[OperationContract(IsOneWay = true)]
void Write(string str);
}
}
Reliable.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.ServiceModel;
namespace WCF.ServiceLib.Message
{
/**//// <summary>
/// 演示可靠性消息的類
/// </summary>
public class Reliable : IReliable
{
/**//// <summary>
/// 將字符串寫入文本文件
/// </summary>
/// <param name="str">需要寫入文本文件的字符串</param>
public void Write(string str)
{
System.IO.StreamWriter sw = new System.IO.StreamWriter(@"C:\WCF_Log_Reliable.txt", true);
sw.Write(str);
sw.WriteLine();
sw.Close();
}
}
}
2、宿主
Reliable.svc
<%@ ServiceHost Language="C#" Debug="true" Service="WCF.ServiceLib.Message.Reliable" %>
Web.config
<?xml version="1.0"?> <configuration> <system.serviceModel> <services> <!--name - 提供服務的類名--> <!--behaviorConfiguration - 指定相關的行為配置--> <service name="WCF.ServiceLib.Message.Reliable" behaviorConfiguration="MessageBehavior"> <!--address - 服務地址(監聽地址);listenUri - 服務監聽地址(實際地址)。監聽可以在host中設置(本例),也可以在client中設置(參看MTOM的例子)--> <!--binding - 通信方式--> <!--contract - 服務契約--> <!--bindingConfiguration - 指定相關的綁定配置--> <endpoint address="http://localhost:8888/ServiceHost/Message/Reliable.svc" listenUri="http://localhost:3502/ServiceHost/Message/Reliable.svc" binding="wsHttpBinding" contract="WCF.ServiceLib.Message.IReliable" bindingConfiguration="ReliableBindingConfiguration" /> </service> </services> <behaviors> <serviceBehaviors> <behavior name="MessageBehavior"> <!--httpGetEnabled - 指示是否發布服務元數據以便使用 HTTP/GET 請求進行檢索,如果發布 WSDL,則為 true,否則為 false,默認值為 false--> <serviceMetadata httpGetEnabled="true" /> <serviceDebug includeExceptionDetailInFaults="true"/> </behavior> </serviceBehaviors> </behaviors> <bindings> <wsHttpBinding> <binding name="ReliableBindingConfiguration"> <!--reliableSession - 對可靠會話綁定元素屬性的設置--> <!--enabled - 指示是否在通道終結點之間建立 WS-RM (WS-ReliableMessaging) 可靠會話。默認值為 false--> <!--ordered - 該值指示消息傳遞是否必須保持與消息發送一致的順序(如果設置為true,那麼也需要在相應的接口或類上聲明DeliveryRequirements)--> <!--inactivityTimeout - 服務在關閉之前保持非活動狀態的時間間隔--> <reliableSession enabled="true" ordered="true" inactivityTimeout="00:10:00" /> <!--security - 與此綁定一起使用的安全設置--> <!--mode="None" - 禁用安全性--> <security mode="None" /> </binding> </wsHttpBinding> </bindings> </system.serviceModel> </configuration>
3、客戶端
Reliable.aspx
<%@ Page Language="C#" MasterPageFile="~/Site.master" AutoEventWireup="true" CodeFile="Reliable.aspx.cs"
Inherits="Message_Reliable" Title="可靠性消息(ReliableMessaging)" %>
<asp:Content ID="Content1" ContentPlaceHolderID="head" runat="Server">
</asp:Content>
<asp:Content ID="Content2" ContentPlaceHolderID="ContentPlaceHolder1" runat="Server">
<asp:Button ID="btnReliable" runat="server" Text="可靠性消息測試" OnClick="btnReliable_Click" />
<p>
測試方法:
<br />
1、用TcpTrace監聽8888端口,目標端口3502
<br />
2、程序調用proxy.Hello("1")後馬上停止Trace,過一會再打開Trace,發現程序還會調用proxy.Hello("2");
</p>
<p>
備注:
<br />
1、通過重試的方法來保證消息的可靠傳遞,默認為8次
<br />
2、當配置了“有序傳遞”的時候,客戶端和服務端會開辟緩沖區,服務端緩沖區在接到所有客戶端發來的消息後,按照客戶端調用的順序排序各個消息,然後有序地調用服務端
</p>
</asp:Content>
Reliable.aspx.cs
using System;
using System.Collections;
using System.Configuration;
using System.Data;
using System.Linq;
using System.Web;
using System.Web.Security;
using System.Web.UI;
using System.Web.UI.HtmlControls;
using System.Web.UI.WebControls;
using System.Web.UI.WebControls.WebParts;
using System.Xml.Linq;
using System.ServiceModel.Channels;
using System.IO;
public partial class Message_Reliable : System.Web.UI.Page
{
protected void Page_Load(object sender, EventArgs e)
{
}
protected void btnReliable_Click(object sender, EventArgs e)
{
using (var proxy = new MessageSvc.Reliable.ReliableClient())
{
proxy.Write("1");
System.Threading.Thread.Sleep(3000);
proxy.Write("2");
}
}
}
Web.config
<?xml version="1.0"?> <configuration> <system.serviceModel> <client> <!--address - 服務地址--> <!--binding - 通信方式--> <!--contract - 服務契約--> <!--bindingConfiguration - 指定相關的綁定配置--> <endpoint address="http://localhost:8888/ServiceHost/Message/Reliable.svc" binding="wsHttpBinding" contract="MessageSvc.Reliable.IReliable" bindingConfiguration="ReliableBindingConfiguration" /> </client> <bindings> <wsHttpBinding> <binding name="ReliableBindingConfiguration"> <!--reliableSession - 對可靠會話綁定元素屬性的設置--> <!--enabled - 指示是否在通道終結點之間建立 WS-RM (WS-ReliableMessaging) 可靠會話。默認值為 false--> <!--ordered - 該值指示消息傳遞是否必須保持與消息發送一致的順序(如果設置為true,那麼也需要在相應的接口或類上聲明DeliveryRequirements)--> <!--inactivityTimeout - 服務在關閉之前保持非活動狀態的時間間隔--> <reliableSession enabled="true" ordered="true" inactivityTimeout="00:10:00" /> <!--security - 與此綁定一起使用的安全設置--> <!--mode="None" - 禁用安全性--> <security mode="None" /> </binding> </wsHttpBinding> </bindings> </system.serviceModel> </configuration>
運行結果:
1、用TcpTrace監聽8888端口,目標端口3502
2、程序調用proxy.Hello("1")後馬上停止Trace,過一會再打開Trace,發現程序還會調用proxy.Hello("2");
OK