简体   繁体   English

我可以使用WCF双工绑定来中继消息吗?

[英]Can I use WCF duplex binding to relay message?

I have a Client Application, a server and another client, lets call it third party. 我有一个客户端应用程序,一个服务器和另一个客户端,可以称之为第三方。 I have a callback interface as part of my contract that is implemented both by the third party and the client. 我的合同中有一个回调接口,该接口由第三方和客户端共同实施。

The third party will call a server operation(method) then the server will trigger a callback but instead of calling the callback of the third party, it will call the callback implementation of the client. 第三方将调用服务器操作(方法),然后服务器将触发回调,但不是调用第三方的回调,而是调用客户端的回调实现。

Yes, you can absolutely do that. 是的,您绝对可以做到。

The easiest way is to implement your service as a PerSession service, and capture the callback context on initialization/construction. 最简单的方法是将服务实现为PerSession服务,并在初始化/构造时捕获回调上下文。 Typically I will add the service object (which really represents a connection at that point) to an internal core object. 通常,我会将服务对象(实际上表示该时刻的连接)添加到内部核心对象。

Then, when you get in a message from a client, you can make a call to any of the service objects (not through the contract), and internally forward the data to the associated client. 然后,当您收到来自客户端的消息时,您可以调用任何服务对象(而不是通过合同),并在内部将数据转发到关联的客户端。

This is a pretty minimal implementation of the concept, without exception handling, and some pretty bad design (static class BAD!). 这是该概念的极小的实现,没有异常处理,并且有一些非常糟糕的设计(静态类BAD!)。 I haven't tested this, but the principles should hold even if I missed crossing an i or dotting a t. 我还没有对此进行测试,但是即使我错过了穿越i或打t的原则,这些原则也应该成立。 This example also forwards the calls to all clients, but selecting an individual client follows the same basic pattern. 此示例还将呼叫转发给所有客户端,但是选择单个客户端遵循相同的基本模式。

Trying to do this with a singleton service will be more difficult, and a per-call service obviously won't work :) 尝试使用单例服务来做到这一点将更加困难,并且按呼叫的服务显然不起作用:)

[ServiceContract(CallbackContract = typeof(ICallback))]
public interface IContract
{
    [OperationContract(IsOneWay = true)]
    void SendTheData(string s);
}

public interface ICallback
{
    [OperationContract(IsOneWay = true)]
    void ForwardTheData(string s);
}

[ServiceBehavior(ConcurrencyMode = ConcurrencyMode.Reentrant, InstanceContextMode = InstanceContextMode.PerSession)]
public class ServiceConnection : IContract
{
    private ICallback m_callback;

    public ServiceConnection()
    {
        m_callback = OperationContext.Current.GetCallbackChannel<ICallback>();
        ServiceCore.Add(this);
    }

    public void SendTheData(string s)
    {
        ServiceCore.DataArrived(s);
    }

    public void SendToClient(string s)
    {
        m_callback.ForwardTheData(s);
    }
}

static public class ServiceCore
{
    static private List<ServiceConnection> m_connections = new List<ServiceConnection>();


    public static void DataArrived(string s)
    {
        foreach(ServiceConnection conn in m_connections)
        {
            conn.SendTheData(s);
        }
    }

    public static void Add(ServiceConnection connection)
    {
        m_connections.Add(connection);
    }
}

From a quick read of the Microsoft Duplex service documentation I don't think that will do what you want. 从Microsoft Duplex服务文档的快速阅读中,我认为这不会满足您的要求。 There could be some other clever Kung Fu WCF way to do it but in my case I created a "PassThruService" for the server that implemented the same contract as the real service and sent any requests received onto the client. 可能还有其他一些聪明的功夫WCF方式,但是在我的情况下,我为服务器创建了一个“ PassThruService”,该服务器实现了与真实服务相同的合同,并将收到的所有请求发送到客户端。

This is a part of my code that explains the thrust of it. 这是我的代码的一部分,解释了它的目的。

private const int OPERATION_TIMEOUT = 5000;
private MyServiceClient m_client = new MyServiceClient();

public bool IsAlive() {
    try {
        logger.Debug("PassThruService IsAlive.");

        bool isAlive = false;
        ManualResetEvent isAliveMRE = new ManualResetEvent(false);

        m_client.IsAliveComplete += (s, a) => { isAlive = a.Result; isAliveMRE.Set(); };
        m_client.IsAliveAsync();

        if (isAliveMRE.WaitOne(OPERATION_TIMEOUT)) {
            return isAlive;
        }
        else {
            throw new TimeoutException();
        }
    }
    catch (Exception excp) {
        logger.Error("Exception PassThruService IsAlive. " + excp.Message);
        throw;
    }

I don't fully see what you're really asking here.... but I'll try to give some tips anyway. 我没有完全看到您在这里真正要问的问题。...但是无论如何我都会尝试给出一些提示。

Relaying messages or routing is not very well supported in WCF in .NET 3.5 - the infrastructure is there, but it's still a lot of work to set it up manually. 在.NET 3.5中的WCF中,中继消息或路由不是很受支持-那里有基础结构,但是手动设置它仍然需要大量工作。

The best intro I know into this topic for WCF in .NET 3.5 is a two-part article by Michele Leroux Bustamante on MSDN magazine: 关于.NET 3.5中WCF的这个主题,我所知道的最好的介绍是MSDN杂志上的Michele Leroux Bustamante的两部分文章:

Part 2 has a section on duplex routers - does that help you in your quest at all?? 第2部分有一个关于双工路由器的部分-完全可以帮助您完成任务吗?

WCF in .NET 4.0 promises to bring additional support for routing - there will be a RoutingService base class which can be leveraged to write routing services, and it will allow for configurable, content- or metadata-based routing - whatever it is that you need. .NET 4.0中的WCF承诺将提供对路由的附加支持-将有一个RoutingService基类,可以利用该基类来编写路由服务,并且它将允许可配置的,基于内容或基于元数据的路由-无论您需要什么。

.NET 4.0 is scheduled to be released sometime later this year (2009) - hopefully! .NET 4.0计划于今年晚些时候(2009年)发布-希望! So while this is still the future, it's looking rosy! 因此,尽管这仍然是未来,但它看起来还是美好的!

Marc

I think I found the solution.. 我想我找到了解决方案。

Here's the link. 这是链接。 http://msdn.microsoft.com/en-us/magazine/cc163537.aspx http://msdn.microsoft.com/en-us/magazine/cc163537.aspx

Try to look at figure 6. That's what I'm trying to achieve. 尝试看一下图6。这就是我要实现的目标。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 如何在Azure WCF中继中处理双工WCF - How to handle duplex wcf in azure wcf relay 使用SOAP HTTPS和Duplex进行WCF绑定 - WCF Binding with SOAP HTTPS and Duplex WCF双工回调,如何向所有客户端发送消息? - WCF duplex callbacks, how do I send a message to all clients? 使用WCF中的一个传入端口可以进行双工绑定吗? - Duplex binding possible with ONE incoming port in WCF? 如何使用Azure WCF中继和混合连接按钮? - How do I use the Azure WCF Relay and Hybrid Connections Buttons? WCF,NetTcpBinding,流传输模式可以是双工吗? - WCF, NetTcpBinding, Streamed transfer mode can be duplex? 我可以使用 WCF 在 2 个 windows 服务之间进行通信(发送消息)吗? - Can I use WCF for communicating (sending message) between 2 windows service? 我们可以使用wcf WsDualHttpBinding(DUPLEX comm)在asp.net中的两个不同网站之间进行通信吗 - Can we use wcf WsDualHttpBinding(DUPLEX comm) for communicating between two different websites in asp.net WCF - 使用NetHttpBinding(WebSockets)或备用双工绑定发送JSON - WCF - Sending JSON with NetHttpBinding(WebSockets) or alternative Duplex Binding 在双工WCF服务的客户端中使用基于任务的异步模式时出错 - Error when I use the Task-based Asynchronous Pattern in the client of duplex WCF service
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM