[索引页]
[源码下载]
作者: webabcd
介绍
WCF(Windows Communication Foundation) - 消息处理:通过操作契约的IsOneWay参数实现异步调用,基于Http, TCP, Named Pipe, MSMQ的双向通讯。
示例(异步调用OneWay)
1、服务
IOneWay.cs
OneWay.cs
2、宿主
OneWay.cs
App.config
3、客户端
App.config
运行结果:
单击" btnWithOneWay"按钮,没有弹出提示框。(异步操作)
单击" btnWithoutOneWay"按钮,弹出错误提示框。(同步操作)
示例( 双向通讯Duplex)
1、服务
IDuplex.cs
Duplex.cs
2、 宿主
Duplex.cs
App.config
3、客户端
Duplex.cs
CallbackType.cs
App.config
运行结果:
单击" btnDuplex"按钮后弹出提示框, 显示"Hello: webabcd"
OK
[源码下载]
[源码下载]
化零为整WCF(6) - 消息处理(异步调用OneWay, 双向通讯Duplex)
作者: webabcd
介绍
WCF(Windows Communication Foundation) - 消息处理:通过操作契约的IsOneWay参数实现异步调用,基于Http, TCP, Named Pipe, MSMQ的双向通讯。
示例(异步调用OneWay)
1、服务
IOneWay.cs
using
System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.ServiceModel;
namespace WCF.ServiceLib.Message
{
/// <summary>
/// IOneWay接口
/// </summary>
[ServiceContract]
public interface IOneWay
{
/// <summary>
/// 不使用OneWay(同步调用)
/// </summary>
[OperationContract]
void WithoutOneWay();
/// <summary>
/// 使用OneWay(异步调用)
/// </summary>
[OperationContract(IsOneWay=true)]
void WithOneWay();
}
}
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.ServiceModel;
namespace WCF.ServiceLib.Message
{
/// <summary>
/// IOneWay接口
/// </summary>
[ServiceContract]
public interface IOneWay
{
/// <summary>
/// 不使用OneWay(同步调用)
/// </summary>
[OperationContract]
void WithoutOneWay();
/// <summary>
/// 使用OneWay(异步调用)
/// </summary>
[OperationContract(IsOneWay=true)]
void WithOneWay();
}
}
OneWay.cs
using
System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.ServiceModel;
namespace WCF.ServiceLib.Message
{
/// <summary>
/// OneWay类
/// </summary>
public class OneWay : IOneWay
{
/// <summary>
/// 不使用OneWay(同步调用)
/// 抛出Exception异常
/// </summary>
public void WithoutOneWay()
{
throw new System.Exception("抛出Exception异常");
}
/// <summary>
/// 使用OneWay(异步调用)
/// 抛出Exception异常
/// </summary>
public void WithOneWay()
{
throw new System.Exception("抛出Exception异常");
}
}
}
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.ServiceModel;
namespace WCF.ServiceLib.Message
{
/// <summary>
/// OneWay类
/// </summary>
public class OneWay : IOneWay
{
/// <summary>
/// 不使用OneWay(同步调用)
/// 抛出Exception异常
/// </summary>
public void WithoutOneWay()
{
throw new System.Exception("抛出Exception异常");
}
/// <summary>
/// 使用OneWay(异步调用)
/// 抛出Exception异常
/// </summary>
public void WithOneWay()
{
throw new System.Exception("抛出Exception异常");
}
}
}
2、宿主
OneWay.cs
using
(ServiceHost host
=
new
ServiceHost(
typeof
(WCF.ServiceLib.Message.OneWay)))
{
host.Open();
Console.WriteLine("服务已启动(WCF.ServiceLib.Message.OneWay)");
Console.WriteLine("按<ENTER>停止服务");
Console.ReadLine();
}
{
host.Open();
Console.WriteLine("服务已启动(WCF.ServiceLib.Message.OneWay)");
Console.WriteLine("按<ENTER>停止服务");
Console.ReadLine();
}
App.config
<?
xml version="1.0" encoding="utf-8"
?>
< configuration >
< system.serviceModel >
< services >
<!-- name - 提供服务的类名 -->
<!-- behaviorConfiguration - 指定相关的行为配置 -->
< service name ="WCF.ServiceLib.Message.OneWay" behaviorConfiguration ="MessageBehavior" >
<!-- address - 服务地址 -->
<!-- binding - 通信方式 -->
<!-- contract - 服务契约 -->
< endpoint address ="" binding ="basicHttpBinding" contract ="WCF.ServiceLib.Message.IOneWay" />
< endpoint address ="mex" binding ="mexHttpBinding" contract ="IMetadataExchange" />
< host >
< baseAddresses >
< add baseAddress ="http://localhost:12345/Message/OneWay/" />
</ baseAddresses >
</ host >
</ service >
</ services >
< behaviors >
< serviceBehaviors >
< behavior name ="MessageBehavior" >
<!-- httpGetEnabled - 使用get方式提供服务 -->
< serviceMetadata httpGetEnabled ="true" />
< serviceDebug includeExceptionDetailInFaults ="true" />
</ behavior >
</ serviceBehaviors >
</ behaviors >
</ system.serviceModel >
</ configuration >
< configuration >
< system.serviceModel >
< services >
<!-- name - 提供服务的类名 -->
<!-- behaviorConfiguration - 指定相关的行为配置 -->
< service name ="WCF.ServiceLib.Message.OneWay" behaviorConfiguration ="MessageBehavior" >
<!-- address - 服务地址 -->
<!-- binding - 通信方式 -->
<!-- contract - 服务契约 -->
< endpoint address ="" binding ="basicHttpBinding" contract ="WCF.ServiceLib.Message.IOneWay" />
< endpoint address ="mex" binding ="mexHttpBinding" contract ="IMetadataExchange" />
< host >
< baseAddresses >
< add baseAddress ="http://localhost:12345/Message/OneWay/" />
</ baseAddresses >
</ host >
</ service >
</ services >
< behaviors >
< serviceBehaviors >
< behavior name ="MessageBehavior" >
<!-- httpGetEnabled - 使用get方式提供服务 -->
< serviceMetadata httpGetEnabled ="true" />
< serviceDebug includeExceptionDetailInFaults ="true" />
</ behavior >
</ serviceBehaviors >
</ behaviors >
</ system.serviceModel >
</ configuration >
3、客户端
using
System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using System.ServiceModel;
namespace Client2.Message
{
/// <summary>
/// 演示Message.OneWay的类
/// </summary>
public class OneWay
{
/// <summary>
/// 调用IsOneWay=true的操作契约(异步操作)
/// </summary>
public void HelloWithOneWay()
{
try
{
var proxy = new MessageSvc.OneWay.OneWayClient();
proxy.WithOneWay();
proxy.Close();
}
catch (Exception ex)
{
MessageBox.Show(ex.ToString());
}
}
/// <summary>
/// 调用IsOneWay=false的操作契约(同步操作)
/// </summary>
public void HelloWithoutOneWay()
{
try
{
var proxy = new MessageSvc.OneWay.OneWayClient();
proxy.WithoutOneWay();
proxy.Close();
}
catch (Exception ex)
{
MessageBox.Show(ex.ToString());
}
}
}
}
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using System.ServiceModel;
namespace Client2.Message
{
/// <summary>
/// 演示Message.OneWay的类
/// </summary>
public class OneWay
{
/// <summary>
/// 调用IsOneWay=true的操作契约(异步操作)
/// </summary>
public void HelloWithOneWay()
{
try
{
var proxy = new MessageSvc.OneWay.OneWayClient();
proxy.WithOneWay();
proxy.Close();
}
catch (Exception ex)
{
MessageBox.Show(ex.ToString());
}
}
/// <summary>
/// 调用IsOneWay=false的操作契约(同步操作)
/// </summary>
public void HelloWithoutOneWay()
{
try
{
var proxy = new MessageSvc.OneWay.OneWayClient();
proxy.WithoutOneWay();
proxy.Close();
}
catch (Exception ex)
{
MessageBox.Show(ex.ToString());
}
}
}
}
App.config
<?
xml version="1.0" encoding="utf-8"
?>
< configuration >
< system.serviceModel >
< client >
<!-- address - 服务地址 -->
<!-- binding - 通信方式 -->
<!-- contract - 服务契约 -->
< endpoint address ="http://localhost:12345/Message/OneWay/" binding ="basicHttpBinding" contract ="MessageSvc.OneWay.IOneWay" />
</ client >
</ system.serviceModel >
</ configuration >
< configuration >
< system.serviceModel >
< client >
<!-- address - 服务地址 -->
<!-- binding - 通信方式 -->
<!-- contract - 服务契约 -->
< endpoint address ="http://localhost:12345/Message/OneWay/" binding ="basicHttpBinding" contract ="MessageSvc.OneWay.IOneWay" />
</ client >
</ system.serviceModel >
</ configuration >
运行结果:
单击" btnWithOneWay"按钮,没有弹出提示框。(异步操作)
单击" btnWithoutOneWay"按钮,弹出错误提示框。(同步操作)
示例( 双向通讯Duplex)
1、服务
IDuplex.cs
using
System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.ServiceModel;
namespace WCF.ServiceLib.Message
{
/// <summary>
/// IDuplex接口
/// </summary>
/// <remarks>
/// CallbackContract - 回调接口
/// </remarks>
[ServiceContract(CallbackContract = typeof(IDuplexCallback))]
public interface IDuplex
{
/// <summary>
/// Hello
/// </summary>
/// <param name="name">名字</param>
[OperationContract(IsOneWay = true)]
void HelloDuplex(string name);
}
/// <summary>
/// IDuplex回调接口
/// </summary>
public interface IDuplexCallback
{
/// <summary>
/// Hello
/// </summary>
/// <param name="name"></param>
[OperationContract(IsOneWay = true)]
void HelloDuplexCallback(string name);
}
}
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.ServiceModel;
namespace WCF.ServiceLib.Message
{
/// <summary>
/// IDuplex接口
/// </summary>
/// <remarks>
/// CallbackContract - 回调接口
/// </remarks>
[ServiceContract(CallbackContract = typeof(IDuplexCallback))]
public interface IDuplex
{
/// <summary>
/// Hello
/// </summary>
/// <param name="name">名字</param>
[OperationContract(IsOneWay = true)]
void HelloDuplex(string name);
}
/// <summary>
/// IDuplex回调接口
/// </summary>
public interface IDuplexCallback
{
/// <summary>
/// Hello
/// </summary>
/// <param name="name"></param>
[OperationContract(IsOneWay = true)]
void HelloDuplexCallback(string name);
}
}
Duplex.cs
using
System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.ServiceModel;
namespace WCF.ServiceLib.Message
{
/// <summary>
/// Duplex类
/// </summary>
public class Duplex : IDuplex
{
/// <summary>
/// Hello
/// </summary>
/// <param name="name">名字</param>
public void HelloDuplex(string name)
{
// 声明回调接口
IDuplexCallback callback = OperationContext.Current.GetCallbackChannel<IDuplexCallback>();
// 调用回调接口中的方法
callback.HelloDuplexCallback(name);
}
}
}
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.ServiceModel;
namespace WCF.ServiceLib.Message
{
/// <summary>
/// Duplex类
/// </summary>
public class Duplex : IDuplex
{
/// <summary>
/// Hello
/// </summary>
/// <param name="name">名字</param>
public void HelloDuplex(string name)
{
// 声明回调接口
IDuplexCallback callback = OperationContext.Current.GetCallbackChannel<IDuplexCallback>();
// 调用回调接口中的方法
callback.HelloDuplexCallback(name);
}
}
}
2、 宿主
Duplex.cs
using
(ServiceHost host
=
new
ServiceHost(
typeof
(WCF.ServiceLib.Message.Duplex)))
{
host.Open();
Console.WriteLine("服务已启动(WCF.ServiceLib.Message.Duplex)");
Console.WriteLine("按<ENTER>停止服务");
Console.ReadLine();
}
{
host.Open();
Console.WriteLine("服务已启动(WCF.ServiceLib.Message.Duplex)");
Console.WriteLine("按<ENTER>停止服务");
Console.ReadLine();
}
App.config
<?
xml version="1.0" encoding="utf-8"
?>
< configuration >
< system.serviceModel >
< services >
<!-- name - 提供服务的类名 -->
<!-- behaviorConfiguration - 指定相关的行为配置 -->
< service name ="WCF.ServiceLib.Message.Duplex" behaviorConfiguration ="MessageBehavior" >
<!-- address - 服务地址 -->
<!-- binding - 通信方式 -->
<!-- contract - 服务契约 -->
<!-- 双向通讯可以基于Http, TCP, Named Pipe, MSMQ;其中基于Http的双向通讯会创建两个信道(Channel),即需要创建两个http连接 -->
<!-- endpoint address="Message/Duplex" binding="wsDualHttpBinding" contract="WCF.ServiceLib.Message.IDuplex" / -->
< endpoint address ="Message/Duplex" binding ="netTcpBinding" contract ="WCF.ServiceLib.Message.IDuplex" />
< endpoint address ="mex" binding ="mexHttpBinding" contract ="IMetadataExchange" />
< host >
< baseAddresses >
< add baseAddress ="http://localhost:12345/Message/Duplex" />
< add baseAddress ="net.tcp://localhost:54321/" />
</ baseAddresses >
</ host >
</ service >
</ services >
< behaviors >
< serviceBehaviors >
< behavior name ="MessageBehavior" >
<!-- httpGetEnabled - 使用get方式提供服务 -->
< serviceMetadata httpGetEnabled ="true" />
< serviceDebug includeExceptionDetailInFaults ="true" />
</ behavior >
</ serviceBehaviors >
</ behaviors >
</ system.serviceModel >
</ configuration >
< configuration >
< system.serviceModel >
< services >
<!-- name - 提供服务的类名 -->
<!-- behaviorConfiguration - 指定相关的行为配置 -->
< service name ="WCF.ServiceLib.Message.Duplex" behaviorConfiguration ="MessageBehavior" >
<!-- address - 服务地址 -->
<!-- binding - 通信方式 -->
<!-- contract - 服务契约 -->
<!-- 双向通讯可以基于Http, TCP, Named Pipe, MSMQ;其中基于Http的双向通讯会创建两个信道(Channel),即需要创建两个http连接 -->
<!-- endpoint address="Message/Duplex" binding="wsDualHttpBinding" contract="WCF.ServiceLib.Message.IDuplex" / -->
< endpoint address ="Message/Duplex" binding ="netTcpBinding" contract ="WCF.ServiceLib.Message.IDuplex" />
< endpoint address ="mex" binding ="mexHttpBinding" contract ="IMetadataExchange" />
< host >
< baseAddresses >
< add baseAddress ="http://localhost:12345/Message/Duplex" />
< add baseAddress ="net.tcp://localhost:54321/" />
</ baseAddresses >
</ host >
</ service >
</ services >
< behaviors >
< serviceBehaviors >
< behavior name ="MessageBehavior" >
<!-- httpGetEnabled - 使用get方式提供服务 -->
< serviceMetadata httpGetEnabled ="true" />
< serviceDebug includeExceptionDetailInFaults ="true" />
</ behavior >
</ serviceBehaviors >
</ behaviors >
</ system.serviceModel >
</ configuration >
3、客户端
Duplex.cs
using
System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.ServiceModel;
using System.Windows.Forms;
namespace Client2.Message
{
/// <summary>
/// 演示Message.Duplex的类
/// </summary>
public class Duplex
{
/// <summary>
/// Hello
/// </summary>
/// <param name="name">名字</param>
public void HelloDulex(string name)
{
var ct = new Client2.Message.CallbackType();
var ctx = new InstanceContext(ct);
var proxy = new MessageSvc.Duplex.DuplexClient(ctx);
proxy.HelloDuplex(name);
}
}
}
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.ServiceModel;
using System.Windows.Forms;
namespace Client2.Message
{
/// <summary>
/// 演示Message.Duplex的类
/// </summary>
public class Duplex
{
/// <summary>
/// Hello
/// </summary>
/// <param name="name">名字</param>
public void HelloDulex(string name)
{
var ct = new Client2.Message.CallbackType();
var ctx = new InstanceContext(ct);
var proxy = new MessageSvc.Duplex.DuplexClient(ctx);
proxy.HelloDuplex(name);
}
}
}
CallbackType.cs
using
System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows.Forms;
namespace Client2.Message
{
/// <summary>
/// 实现回调接口
/// </summary>
public class CallbackType : MessageSvc.Duplex.IDuplexCallback
{
/// <summary>
/// Hello
/// </summary>
/// <param name="name">名字</param>
public void HelloDuplexCallback(string name)
{
MessageBox.Show("Hello: " + name);
}
}
}
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows.Forms;
namespace Client2.Message
{
/// <summary>
/// 实现回调接口
/// </summary>
public class CallbackType : MessageSvc.Duplex.IDuplexCallback
{
/// <summary>
/// Hello
/// </summary>
/// <param name="name">名字</param>
public void HelloDuplexCallback(string name)
{
MessageBox.Show("Hello: " + name);
}
}
}
App.config
<?
xml version="1.0" encoding="utf-8"
?>
< configuration >
< system.serviceModel >
< client >
<!-- address - 服务地址 -->
<!-- binding - 通信方式 -->
<!-- contract - 服务契约 -->
<!-- endpoint address="http://localhost:12345/Message/Duplex/" binding="wsDualHttpBinding" contract="MessageSvc.Duplex.IDuplex" / -->
< endpoint address ="net.tcp://localhost:54321/Message/Duplex" binding ="netTcpBinding" contract ="MessageSvc.Duplex.IDuplex" />
</ client >
</ system.serviceModel >
</ configuration >
< configuration >
< system.serviceModel >
< client >
<!-- address - 服务地址 -->
<!-- binding - 通信方式 -->
<!-- contract - 服务契约 -->
<!-- endpoint address="http://localhost:12345/Message/Duplex/" binding="wsDualHttpBinding" contract="MessageSvc.Duplex.IDuplex" / -->
< endpoint address ="net.tcp://localhost:54321/Message/Duplex" binding ="netTcpBinding" contract ="MessageSvc.Duplex.IDuplex" />
</ client >
</ system.serviceModel >
</ configuration >
运行结果:
单击" btnDuplex"按钮后弹出提示框, 显示"Hello: webabcd"
OK
[源码下载]