0

问题

我有这个奇怪的问题。我在控制台应用程序中托管 WCF 服务器: Console.WriteLine("Press 'q' to quit.");

            var serviceHost = new ServiceHost(typeof(MessageService));
            serviceHost.Open();
            while (Console.ReadKey().KeyChar != 'q')
            {
            }
            serviceHost.Close();

它公开了两个用于发布和订阅的端点(双工绑定)当我停止或退出控制台应用程序时,我从未在客户端收到通道故障。我希望通知客户端服务器已关闭。知道这里出了什么问题吗?

我想要的只是在控制台应用程序关闭时引发以下事件之一:

    msgsvc.InnerDuplexChannel.Faulted += InnerDuplexChannelOnFaulted;
    msgsvc.InnerChannel.Faulted += InnerChannelOnFaulted;
4

3 回答 3

1

来自 MSDN:双工模型不会自动检测服务或客户端何时关闭其通道。因此,如果服务意外终止,默认情况下不会通知该服务,或者如果客户端意外终止,则不会通知该服务。客户端和服务可以实现他们自己的协议来相互通知,如果他们愿意的话。

于 2013-02-28T13:22:42.570 回答
0

AFAIK tcp 通道对(持久)连接问题非常敏感,但您可以使用回调在服务器不可用之前通知客户端。从客户端,您可以使用一些虚拟 ping/poke 方法“OnTimer”来获取实际的连接状态/保持通道活动。我想,此时恢复客户端代理(重新连接)是件好事。如果服务提供元数据端点,您也可以调用 svcutil 进行试用连接或以编程方式检索元数据:

  Uri mexAddress = new Uri("http://localhost:5000/myservice");
  var mexClient = new MetadataExchangeClient(mexAddress, MetadataExchangeClientMode.HttpGet);
  MetadataSet metadata = mexClient.GetMetadata();
  MetadataImporter importer = new WsdlImporter(metadata);
  ServiceEndpointCollection endpoints = importer.ImportAllEndpoints();

  ContractDescription description =
  ContractDescription.GetContract(typeof(IMyContract));
  bool contractSupported = endpoints.Any(endpoint =>
  endpoint.Contract.Namespace == description.Namespace &&
  endpoint.Contract.Name == description.Name);

或者

ServiceEndpointCollection endpoints = MetadataResolver.Resolve(typeof(IMyContract), mexAddress, MetadataExchangeClientMode.HttpGet)
于 2013-02-28T20:56:23.870 回答
0

如果您是客户,并且订阅了所有 3 个事件,即 IClientChannel 的 Closing、Closed 和 Faulted,那么如果您关闭服务控制台应用程序,您至少应该看到 Closing 和 Closed 事件。我不确定为什么。如果你正确关闭,你会认为你会看到错误。我正在使用 tcp.net 全双工通道,我看到这些事件很好。请记住,现在是 2017 年,所以从那时起事情可能已经发生了变化,但我在我的代码中一直依赖这些事件。对于那些说双工模型没有看到通道关闭的人,我不明白这一点。

于 2017-05-11T07:29:48.070 回答