Warning: file_get_contents(/data/phpspider/zhask/data//catemap/7/wcf/4.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 如何获取WCF服务正在侦听的端口?_C#_Wcf_Service - Fatal编程技术网

C# 如何获取WCF服务正在侦听的端口?

C# 如何获取WCF服务正在侦听的端口?,c#,wcf,service,C#,Wcf,Service,我有一个net.tcp WCF服务,我希望操作系统选择它应该监听的端口。因此,我在URI中将端口设置为0,并且netstat确认操作系统已选择5000范围内的端口 如何在服务流程中找到已在代码中拾取的实际端口 一些代码显示了我的尝试: Type serviceType = ...; Uri address = new Uri("net.tcp://0.0.0.0:0/Service/"); ServiceHost serviceHost = new ServiceHost(serviceType

我有一个net.tcp WCF服务,我希望操作系统选择它应该监听的端口。因此,我在URI中将端口设置为0,并且
netstat
确认操作系统已选择5000范围内的端口

如何在服务流程中找到已在代码中拾取的实际端口

一些代码显示了我的尝试:

Type serviceType = ...;
Uri address = new Uri("net.tcp://0.0.0.0:0/Service/");
ServiceHost serviceHost = new ServiceHost(serviceType, address);
ServiceEndpoint endPoint = serviceHost.AddServiceEndpoint(type, binding, "");
int port1 = endPoint.ListenUri.Port; // returns 0
int port2 = serviceHost.BaseAddresses.First().Port; // also returns 0

不确定这是否有帮助,但已经有一个类似的问题:

您可能希望尝试的已提交答案的相关部分:

foreach (var channelDispatcher in serviceHost.ChannelDispatchers)
{
            Console.WriteLine(channelDispatcher.Listener.Uri);
}
因此,您可能需要
channelDispatcher.Listener.Uri.Port


希望这有帮助

作为替代方案,您可以为WCF找到一个自由端口供自己使用:

private int FindPort()
{
    IPEndPoint endPoint = new IPEndPoint(IPAddress.Any, 0);

    using (Socket socket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp))
    {
         socket.Bind(endPoint);
         IPEndPoint local = (IPEndPoint)socket.LocalEndPoint;
         return local.Port;
    }
}

源代码。

一旦服务启动,您就可以获得从description.endpoints集合中实际创建的端点的完整描述(这在调用Open()之后才起作用)。从这个集合中你可以得到地址。不幸的是,您必须对端口的地址进行字符串解析

这是我的服务器在每次服务打开()后记录的内容


让一个服务在一个随机端口上监听是很不寻常的-你有什么理由这样做吗?@Cocowalla:该服务是工作进程的一部分,因此一次可以有多个,我们正在寻找不涉及.NET TCP端口共享的解决方案。可能与@D Hoerster重复:不幸的是,这只会返回我传入的URI。谢谢你给我们指出了另一个问题。@D霍斯特:看来我们赢了。我还必须设置endPoint.listenruimode=listenruimode.Unique;要使其工作(并禁用绑定上的端口共享)。您是否调用了Open?这不安全。其他人可以在释放套接字后但在打开ServiceHost之前抢夺端口。因此,这种方法可能会偶尔失败。
        serviceHost.Open();

        // Iterate through the endpoints contained in the ServiceDescription 
        System.Text.StringBuilder sb = new System.Text.StringBuilder(string.Format("Active Service Endpoints:{0}", Environment.NewLine), 128);
        foreach (ServiceEndpoint se in serviceHost.Description.Endpoints)
        {
            sb.Append(String.Format("Endpoint:{0}", Environment.NewLine));
            sb.Append(String.Format("\tAddress: {0}{1}", se.Address, Environment.NewLine));
            sb.Append(String.Format("\tBinding: {0}{1}", se.Binding, Environment.NewLine));
            sb.Append(String.Format("\tContract: {0}{1}", se.Contract.Name, Environment.NewLine));
            foreach (IEndpointBehavior behavior in se.Behaviors)
            {
                sb.Append(String.Format("Behavior: {0}{1}", behavior, Environment.NewLine));
            }
        }

        Console.WriteLine(sb.ToString());