我试图第四次写这个问题,因为我很遗憾不确定我真正想要的是什么。请原谅我是模糊的还是有点不对。
我有一个命令行.NET4.5 C#应用程序。我会在两个地理位置较远的地方同时运行它。我希望能够将一个实例转换为主机,将另一个实例转换为客户端。
在它的核心,我想要一个TextReader实现,在Read / ReadLine上等待来自远程客户端的输入。我还想要一个TextWriter,在Write / WriteLine上调用远程客户端并将文本传递给它。
TextWriter当然是相当简单的事情,因为我基本上这样做:在写入时,将client.SendText(s);
调用到另一个实例。
如何在该方案中实施TextReader.ReadLine()
?在WCF服务中,一个天真的方法是拥有一个方法:
class Service : IService{
void SendText(string s){
Console.WriteLine(s); // or whatever is the destination TextWriter
}
string ReadLine(){
return Console.ReadLine(); // or whatever is the source TextReader
}
}
但是保持WCF操作调用打开几分钟甚至几个小时是一个好主意吗?
我能看到的另一种方法是:
class Service : IService{
void RegisterClient(string url){/* url points to an IService endpoint in client*/}
void SendString(string s){...}
}
然后在两个实例中托管它,从客户端调用RegisterClient提供自己的端点url然后如果主机想要将一些数据返回给客户端 - 只需调用SendString,没问题。但是如果主机必须等待来自客户端的输入,那么如何合理地解决这个问题呢?
class WCFTextReader : TextReader{
public override string ReadLine(){
// what here? it should return whatever comes in the next SendString call from client...
}
}
我可以收到Queue<string>
条消息,然后执行while(true)
并先从Queue
或Thread.Sleep
返回并重新检查,但是每次我觉得我需要while(true)
和Thread.Sleep
我宁愿来这里,因为我觉得我错过了什么......
答案 0 :(得分:1)
默认的WCF消息模式是请求/响应;客户端发送请求,服务器响应它。
然而,存在双工消息模式,其中服务接口契约将另一个接口标识为其回调接口契约;客户端必须实现此回调接口契约,类似于服务必须实现服务接口契约的方式。
此消息模式应允许您的服务器随意向客户端发送消息,而客户端不必提示它这样做。
http://msdn.microsoft.com/en-us/library/ms731064%28v=vs.110%29.aspx
http://msdn.microsoft.com/en-us/library/ms731184%28v=vs.110%29.aspx
**公平警告:根据我的经验,您可能仍然需要处理保持连接活动的问题,以防您计划让服务器在一段时间不活动后将消息发送回客户端。< / p>
如果保持连接打开是可以接受的,那么你可以实现某种保持活动机制。
如果保持连接打开是不可接受的,那么我认为你需要考虑一个更复杂的方法,让客户定期检查服务器,以便让服务器有机会发送客户端为客户端提供的任何排队消息。