自承载NetTcp服务超时错误

发布于 2024-10-14 19:33:04 字数 4183 浏览 1 评论 0原文

我有一个 Windows 服务,其中包含一个 WCF NetTcp 主机。从客户端,当我开始通过 tcp 调用服务时,它们一开始运行良好,但几分钟后它们都开始给出可怕的 WCF 超时错误,这实际上与超时无关:

This发送到 net.tcp://myserver:8080/ListingService 的请求操作在配置的超时 (00:01:00) 内没有收到回复。

我从这个网站上的其他帖子中看到很多有时这与最大消息大小有关,但我已经将这些设置为限制但无济于事。

这是我的 Windows 服务代码:

public partial class Service : ServiceBase
    {
        internal static ServiceHost myHost = null;

        public Service()
        {
            InitializeComponent();
        }

        protected override void OnStart(string[] args)
        {
            System.Net.ServicePointManager.DefaultConnectionLimit = 10000;
            //create host.
            var path = ConfigurationManager.AppSettings["ServiceHostAddress"].ToString();
            myHost = new ServiceHost(typeof(ListingService));
            //add endpoint.
            myHost.AddServiceEndpoint(typeof(IListingService), GetBinding(), path);
            //add behaviors.
            AddBehaviors();
            //open host.
            myHost.Open();
        }

        private void AddBehaviors()
        {
            //service metadata behavior.
            var smb = new ServiceMetadataBehavior();
            smb.MetadataExporter.PolicyVersion = PolicyVersion.Policy15;
            myHost.Description.Behaviors.Add(smb);
            //service throttling behavior.
            var behavior = new ServiceThrottlingBehavior()
            {
                MaxConcurrentCalls = 10000,
                MaxConcurrentInstances = 10000,
                MaxConcurrentSessions = 10000
            };
            myHost.Description.Behaviors.Add(behavior);
            //service debug behavior.
            var serviceDebugBehavior = myHost.Description.Behaviors.Find<ServiceDebugBehavior>();
            serviceDebugBehavior.IncludeExceptionDetailInFaults = true;
        }

        private Binding GetBinding()
        {
            var queueBinding = new NetTcpBinding(SecurityMode.None);
            queueBinding.MaxConnections = 10000;
            queueBinding.MaxBufferSize = 2048000;
            queueBinding.MaxReceivedMessageSize = 2048000;
            return queueBinding;
        }

        protected override void OnStop()
        {
            if (myHost != null)
            {
                myHost.Close();
                myHost = null; 
            }
        }
    }

这是客户端配置,以防有任何不同:

<system.serviceModel>
    <bindings>

      <netTcpBinding>
        <binding name="NetTcpBinding" transferMode="Buffered" hostNameComparisonMode="StrongWildcard"
          closeTimeout="00:01:00" openTimeout="00:01:00" receiveTimeout="00:01:00" sendTimeout="00:01:00"
          maxBufferSize="2147483647" maxBufferPoolSize="2147483647" maxReceivedMessageSize="2147483647"><!-- transactionFlow="true"-->
          <security mode="None"/>
          <reliableSession enabled="false"/>
          <readerQuotas maxArrayLength="2147483647"/>
        </binding>
      </netTcpBinding>

    </bindings>
    <client>

      <endpoint
             address="net.tcp://myserver:8080/ListingService"
             binding="netTcpBinding" bindingConfiguration="NetTcpBinding"
             contract="ListingServiceProxy.IListingService" name="NetTcpBinding" />

    </client>
  </system.serviceModel>

我确保关闭我的客户端连接,这里是代码:

public static void Using<T>(this T client, Action<T> work)
            where T : ICommunicationObject
        {
            try
            {
                work(client);
                client.Close();
            }
            catch (CommunicationException)
            {
                client.Abort();
                throw;
            }
            catch (TimeoutException)
            {
                client.Abort();
                throw;
            }
            catch
            {
                client.Abort();
                throw;
            }
        }

new ListingServiceClient().Using(client =>
                {
                    client.SaveListing(listing);
                });

I have a windows service which houses a WCF NetTcp host. From the client, when I start making calls to the service via tcp, they go through fine at first but then after a few minutes they all start to give the dreaded WCF timeout error which really has nothing to do with timeouts:

This request operation sent to net.tcp://myserver:8080/ListingService did not receive a reply within the configured timeout (00:01:00).

I've seen from other posts on this site that a lot of times this has to do with the max message sizes, but I've already set these to the limits to no avail.

Here is my windows service code:

public partial class Service : ServiceBase
    {
        internal static ServiceHost myHost = null;

        public Service()
        {
            InitializeComponent();
        }

        protected override void OnStart(string[] args)
        {
            System.Net.ServicePointManager.DefaultConnectionLimit = 10000;
            //create host.
            var path = ConfigurationManager.AppSettings["ServiceHostAddress"].ToString();
            myHost = new ServiceHost(typeof(ListingService));
            //add endpoint.
            myHost.AddServiceEndpoint(typeof(IListingService), GetBinding(), path);
            //add behaviors.
            AddBehaviors();
            //open host.
            myHost.Open();
        }

        private void AddBehaviors()
        {
            //service metadata behavior.
            var smb = new ServiceMetadataBehavior();
            smb.MetadataExporter.PolicyVersion = PolicyVersion.Policy15;
            myHost.Description.Behaviors.Add(smb);
            //service throttling behavior.
            var behavior = new ServiceThrottlingBehavior()
            {
                MaxConcurrentCalls = 10000,
                MaxConcurrentInstances = 10000,
                MaxConcurrentSessions = 10000
            };
            myHost.Description.Behaviors.Add(behavior);
            //service debug behavior.
            var serviceDebugBehavior = myHost.Description.Behaviors.Find<ServiceDebugBehavior>();
            serviceDebugBehavior.IncludeExceptionDetailInFaults = true;
        }

        private Binding GetBinding()
        {
            var queueBinding = new NetTcpBinding(SecurityMode.None);
            queueBinding.MaxConnections = 10000;
            queueBinding.MaxBufferSize = 2048000;
            queueBinding.MaxReceivedMessageSize = 2048000;
            return queueBinding;
        }

        protected override void OnStop()
        {
            if (myHost != null)
            {
                myHost.Close();
                myHost = null; 
            }
        }
    }

Here is the client config in case it makes any difference:

<system.serviceModel>
    <bindings>

      <netTcpBinding>
        <binding name="NetTcpBinding" transferMode="Buffered" hostNameComparisonMode="StrongWildcard"
          closeTimeout="00:01:00" openTimeout="00:01:00" receiveTimeout="00:01:00" sendTimeout="00:01:00"
          maxBufferSize="2147483647" maxBufferPoolSize="2147483647" maxReceivedMessageSize="2147483647"><!-- transactionFlow="true"-->
          <security mode="None"/>
          <reliableSession enabled="false"/>
          <readerQuotas maxArrayLength="2147483647"/>
        </binding>
      </netTcpBinding>

    </bindings>
    <client>

      <endpoint
             address="net.tcp://myserver:8080/ListingService"
             binding="netTcpBinding" bindingConfiguration="NetTcpBinding"
             contract="ListingServiceProxy.IListingService" name="NetTcpBinding" />

    </client>
  </system.serviceModel>

I make sure to close my client connections, here is the code:

public static void Using<T>(this T client, Action<T> work)
            where T : ICommunicationObject
        {
            try
            {
                work(client);
                client.Close();
            }
            catch (CommunicationException)
            {
                client.Abort();
                throw;
            }
            catch (TimeoutException)
            {
                client.Abort();
                throw;
            }
            catch
            {
                client.Abort();
                throw;
            }
        }

new ListingServiceClient().Using(client =>
                {
                    client.SaveListing(listing);
                });

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

爱情眠于流年 2024-10-21 19:33:04

他们最终超时了,因为数据库实际上超时了,这不是 WCF 的问题。

They ended up timing out because the database was actually timing out, it wasn't an issue with WCF.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文