Я столкнулся со странной проблемой с высокодоступной службой Windows оконечного менеджера WCF, использующей фабрику служб Azure, которая обеспечивает обратные вызовы, когда служба становится активной.
Каждый раз, когда служба становится активной, мы регистрируем конечные точки WCF, используя:
A)
serviceHost = CreateServiceHost(IWcfContractInstance)
serviceHost.AddServiceEndpoint(...)
serviceHost.Open()
Когда служба деактивируется (примечание: в этом случае процесс не останавливается)
B)
serviceHost.Close()
Они оба находятся под замком, и здесь нет проблемы с синхронизацией. Проблема в том, что A терпит неудачу, говоря, что конечная точка уже зарегистрирована.
StackTrace:
System.InvalidOperationException: The ChannelDispatcher at 'net.tcp://localhost:[PORT]/IWcfContract '"ContractName"' is unable to open its IChannelListener. ---> System.InvalidOperationException:
A registration already exists for URI 'net.tcp://localhost:[PORT]/IWcfContract'.
at System.ServiceModel.Channels.UriPrefixTable`1.RegisterUri(Uri uri; HostNameComparisonMode hostNameComparisonMode; TItem item)
at System.ServiceModel.Channels.ConnectionOrientedTransportManager`1.Register(TransportChannelListener channelListener)
at System.ServiceModel.Channels.TransportManager.Open(TransportChannelListener channelListener)
at System.ServiceModel.Channels.TransportManagerContainer.Open(SelectTransportManagersCallback selectTransportManagerCallback)
at System.ServiceModel.Channels.TransportChannelListener.OnOpen(TimeSpan timeout)
at System.ServiceModel.Channels.ConnectionOrientedTransportChannelListener.OnOpen(TimeSpan timeout)
at System.ServiceModel.Channels.TcpChannelListener`2.OnOpen(TimeSpan timeout)
at System.ServiceModel.Channels.CommunicationObject.Open(TimeSpan timeout)
at System.ServiceModel.Channels.ReliableChannelListenerBase`1.OnOpen(TimeSpan timeout)
at System.ServiceModel.Channels.CommunicationObject.Open(TimeSpan timeout)
at System.ServiceModel.Dispatcher.ChannelDispatcher.OnOpen(TimeSpan timeout)
at System.ServiceModel.Dispatcher.ChannelDispatcher.OnOpen(TimeSpan timeout)
at System.ServiceModel.Channels.CommunicationObject.Open(TimeSpan timeout)
at System.ServiceModel.ServiceHostBase.OnOpen(TimeSpan timeout)
at System.ServiceModel.Channels.CommunicationObject.Open(TimeSpan timeout)
Странно то, что B) также дает сбой и создает исключение CommunicationObjectFaptedException. Таким образом, вопрос заключается в том, что вызов Close в сбойном сеансе должен избавиться от ресурсов, поэтому, когда мы продолжим и зарегистрируем эту конечную точку снова, она должна просто работать.
Я что-то здесь упускаю?