【问题标题】:How to use a WCF Dual Service over the internet?如何通过 Internet 使用 WCF 双重服务?
【发布时间】:2012-06-18 12:42:23
【问题描述】:

我遵循了本教程(至少基于我的 WCF,因为我需要像这样工作): http://www.eggheadcafe.com/tutorials/wcf/b5ada8df-58c5-492f-b368-457b3a4f137c/notify-client-applications-using-wcf-callbacks.aspx

它在我的电脑上运行良好,但我需要通过互联网使用它。在尝试执行此操作时,我听说(通过互联网)使用 netTcpBiding 更好。

我将拥有一个服务器,它会知道在线客户端的数量。我想要服务器中我的 IIS 上的 WFC 服务,以及使用它并通知它的 Windows 服务。我需要回调,因为服务器有时必须能够在客户端上执行一些命令。

如果有人可以帮助我,我会非常高兴。

提前致谢,

编辑:

让我自己清楚:我只是无法让它在互联网上运行。你们能告诉我如何更改我的配置(Web.config e App.config)以使用 netTcpBinding 并通过互联网工作吗?

再次感谢,

编辑 2:

我的 WCFServiceApplication 中的 Web.config 是:

<?xml version="1.0"?>
<configuration>
  <system.web>
    <compilation debug="true" targetFramework="4.0" />
  </system.web>
  <system.serviceModel>
    <bindings>
      <wsDualHttpBinding>
        <binding name="WSDualHttpBinding_IPCWatcherWCFService" closeTimeout="00:01:00"
            openTimeout="00:01:00" receiveTimeout="00:10:00" sendTimeout="00:01:00"
            bypassProxyOnLocal="false" transactionFlow="false" hostNameComparisonMode="StrongWildcard"
            maxBufferPoolSize="524288" maxReceivedMessageSize="65536"
            messageEncoding="Text" textEncoding="utf-8" useDefaultWebProxy="true">
          <readerQuotas maxDepth="32" maxStringContentLength="8192" maxArrayLength="16384"
              maxBytesPerRead="4096" maxNameTableCharCount="16384" />
          <reliableSession ordered="true" inactivityTimeout="00:10:00" />
          <security mode="Message">
            <message clientCredentialType="Windows" negotiateServiceCredential="true" algorithmSuite="Default" />
          </security>
        </binding>
      </wsDualHttpBinding>
    </bindings>
    <services>
      <service behaviorConfiguration="TiT.PCWatcher.Server.WCFService.Services.PCWatcherWCFServiceBehavior" name="TiT.PCWatcher.Server.WCFService.Services.PCWatcherWCFService">
        <endpoint address="" binding="wsDualHttpBinding" bindingConfiguration="WSDualHttpBinding_IPCWatcherWCFService" contract="TiT.PCWatcher.Server.WCFService.Interfaces.IPCWatcherWCFService">
          <identity>
            <dns value="localhost" />
          </identity>
        </endpoint>
        <endpoint address="mex" binding="mexHttpBinding" contract="IMetadataExchange" />
      </service>
    </services>
    <behaviors>
      <serviceBehaviors>
        <behavior name="TiT.PCWatcher.Server.WCFService.Services.PCWatcherWCFServiceBehavior">
          <serviceMetadata httpGetEnabled="true"/>
          <serviceDebug includeExceptionDetailInFaults="false"/>
        </behavior>
      </serviceBehaviors>
    </behaviors>
    <serviceHostingEnvironment multipleSiteBindingsEnabled="true" />
  </system.serviceModel>
  <system.webServer>
    <modules runAllManagedModulesForAllRequests="true"/>
  </system.webServer>
</configuration>

我的 WindowsService 中的 App.config 是:

<?xml version="1.0" encoding="utf-8" ?>
<configuration>
  <system.serviceModel>
    <bindings>
      <wsDualHttpBinding>
        <binding name="WSDualHttpBinding_IPCWatcherWCFService" closeTimeout="00:01:00"
          openTimeout="00:01:00" receiveTimeout="00:10:00" sendTimeout="00:01:00"
          bypassProxyOnLocal="false" transactionFlow="false" hostNameComparisonMode="StrongWildcard"
          maxBufferPoolSize="524288" maxReceivedMessageSize="65536" messageEncoding="Text"
          textEncoding="utf-8" useDefaultWebProxy="true">
          <readerQuotas maxDepth="32" maxStringContentLength="8192" maxArrayLength="16384"
            maxBytesPerRead="4096" maxNameTableCharCount="16384" />
          <reliableSession ordered="true" inactivityTimeout="00:10:00" />
          <security mode="Message">
            <message clientCredentialType="Windows" negotiateServiceCredential="true"
              algorithmSuite="Default" />
          </security>
        </binding>
      </wsDualHttpBinding>
    </bindings>
    <client>
      <endpoint address="http://localhost:25145/Services/PCWatcherWCFService.svc"
        binding="wsDualHttpBinding" bindingConfiguration="WSDualHttpBinding_IPCWatcherWCFService"
        contract="PCWatcherWCFServiceReference.IPCWatcherWCFService"
        name="WSDualHttpBinding_IPCWatcherWCFService">
        <identity>
          <dns value="localhost" />
        </identity>
      </endpoint>
    </client>
  </system.serviceModel>
</configuration>

只是将其更改为 netTcpBinding 不起作用...

但我很高兴能够在互联网上运行它...我在 IIS 上发布了 WCFService。链接:

https://www2.tcenter.com.br/monitor/PCWatcherWCFService.svc

http://www2.tcenter.com.br:8080/monitor/PCWatcherWCFService.svc

仅仅改变配置就足以让它通过互联网工作吗?就像我说的,本地的它工作得很好。

我认为只需将客户端上的端点地址更改为它上面的 URL 之一就可以了,但它没有......

您链接的示例在 WPF 上托管服务。我不知道它是否适用于我的场景......

我想我会坚持使用 DualHttpBinding,你不认为端口转发对我的需求有好处,我可以在一个 Intranet 中拥有很多客户端,并让路由器决定他要去哪一个发送信息是不好的,对吧?或者有一种方法可以让路由器正确响应通过同一端口连接到我的网络服务器的每台机器?! (随便问问,呵呵)

非常感谢,

于 21/06/2012 编辑:

感谢您的阅读。 我无法让服务在 LAN 中与 netTcpBinding 一起使用。 我做了一个我的场景的模拟样本。这是here。称为 DualCommunicationTest。

当我开始这篇文章时,我只是想知道如何让这个 cenarion 在互联网上运行。只是。 在我在这里发布之前寻找解决方案的过程中,我读到 netTcpBinding 更好。所以我问了这件事。这只是一个附带问题。

所以...我目前对帖子的需求是:

如何在互联网上使用the sample i developed

如何使the sample i developed 与netTcpBinding 一起工作,然后能够在互联网上使用它。 (我很确定Clunky Coder 教了我第二部分,关于如何使用 IIS 和其他东西在互联网上发布 net.tcp,非常感谢,但我还不能测试它,因为我还不能做 netTcp。)

对不起,如果我不够清楚,我的英语不太好。非常抱歉,再次感谢。

【问题讨论】:

    标签: wcf callback nettcpbinding wsdualhttpbinding


    【解决方案1】:

    netTcpBinding 更适合双工通信(与回调进行通信),并且比WSDualHttpBinding 更高效,WSDualHttpBinding 是通过 HTTP 进行双工通信的首选绑定。但是你不应该真的在互联网上使用netTcpBinding,虽然你在技术上可以并且它可能工作,但是netTcpBinding使用的端口可能(并且通常是)被互联网上的防火墙阻止.当您通过 Internet 发送内容时,它会产生大量的跃点并通过大量的路由器和防火墙,并且无法保证这些路由器和防火墙会打开所有端口。但是,如果您可以在客户端和服务器端点(通常通过路由器上的端口转发完成)上打开端口(对于 netTcp,它是 TCP 808),它可能会起作用,但一般建议是不要在互联网上使用netTcpBinding。话虽如此,我已经将它用于我的服务几次,并且我的客户已经能够通过互联网毫无问题地使用该服务 - 在我转发客户端和服务器端的端口之后。

    一般而言,对于 Internet 上的双工通信,您可以使用 WSDualHttpBinding,如果您有 Silverlight 客户端(Silverlight 不支持 WSDualHttpBinding),您可以使用 PollingDuplexHttpBinding

    我还建议您阅读this

    编辑:

    要将该示例更改为使用netTcpBinding,只需将配置文件中的绑定更改为使用netTcpBinding 而不是wsDualHttpBinding。看看this article,它与您发布的链接一样,带有netTcpBinding 和更多解释。

    编辑 20/06/2012:

    让我自己清楚:我只是无法让它在互联网上运行。 你们能告诉我如何更改我的配置(Web.config e App.config) 使用 netTcpBinding 并通过 Internet 工作?

    您似乎能够让服务在 LAN 中与 netTcpBinding 一起使用,因此您之前的问题现已解决,您现在无法在 IIS 中托管该服务并在线发布它。当您的服务在 LAN 中运行时,一旦您在 IIS 中托管它并在客户端和服务器路由器上转发适当的端口,它就会在 Internet 上运行,这是一种常见的情况,并且在网上有很好的记录。为此,您必须将您的服务作为应用程序托管在您的 IIS 网站中。您需要确保您的服务有一个指向服务位置的 .svc 文件,然后复制 将 App.Config(服务配置文件)复制到新的 web.config(与您的 App.config 在同一物理目录中),并删除新创建的 web.config 中的 &lt;host&gt;&lt;baseAddresses&gt; 部分,指向应用程序的物理路径到您的服务主机上此服务的位置。一旦处理完毕,请务必编辑默认网站绑定以启用您的服务使用的特定绑定,对于netTcpBinding,请转到:网站 -> '编辑绑定...' -> '添加...' 然后选择 net.tcp 并为其分配端口。 然后在您的应用程序上转到“高级设置”并启用 net.tcp,netTcpBinding 服务通常具有http,net.tcp,因为它启用了协议。如果您遇到初期错误,请确保默认应用程序池(或您的网站正在使用的任何应用程序池)具有访问和读取服务所在服务器上的物理目录所需的权限。

    请阅读thisthis,让我详细说明只会重复他们所说的话。

    编辑 21/06/2012:

    我刚刚下载了您的服务并将其托管在 IIS 中,并且托管良好,因为它使用 HTTP 而不是 nettcp,这意味着它在 Internet 上运行良好。如果您的服务很简单,并且您不希望对其进行繁重的处理(从外观上看,您只是想获取连接到它的客户端列表),那么请坚持使用wsDualHTTPBinding,因为 HTTP 协议将在任何环境中工作,您不必像使用netTcpBinding 那样担心防火墙。这就是我在 IIS 中托管服务(并使其通过 Internet 可用)所做的一切:

    1. 转到 IIS 中的 DefaultWebsite,右键单击,添加应用程序,在 Alias 下为您的服务提供您希望在 URL 中看到的任何名称。选择默认应用程序池或 ASP.NET 4.0 应用程序池。

    2. 将物理路径指向您的 .svc 文件在您的计算机上的位置;对我来说:

    C:\Users\MyPC\Documents\DualCommunicationTest.Server\WcfServiceApp

    1. 在启用的协议下,确保您在端口 80 或任何其他端口(例如 8085)上有 HTTP,但您需要将路由器上的此端口转发到服务主机计算机。如果您的服务主机位于 LAN 中的 IP 192.168.1.4 上,则在路由器上将端口 80(或您使用的任何端口,例如 8085)转发到计算机 192.168.1.4。

    就这么简单。

    【讨论】:

    • 读起来确实不错...好吧,我不知道我是要使用 netTcp 还是 wsDual,但是,您能帮我完成它吗?我很高兴将上面链接中实现的示例付诸实施......
    • @TanielianBarreira,我刚看了这篇文章,好像写的不错,到底是什么问题?从外观上看,它实现了一个简单的聊天服务,WCF 中有很多关于回调的示例。这个想法的要点是客户端调用服务上的一些操作,服务可以反过来调用客户端上的一个方法(这是回调),所以客户端会暂时像一个服务器本身。 ChatService 中的方法是客户端在服务器上调用的,IChatServiceCallback 中的方法是服务在客户端上调用的。
    • 你能试着回答一下吗?在我的更新中,我只是问我如何更改我的配置以能够通过互联网连接。他们现在的方式(更改客户端上的服务器 url)我只是收到超时错误。
    • @TanielianBarreira 看看我的更新。如果您觉得有帮助,您是否愿意接受我的回答(通过单击旁边的勾号)?谢谢。
    • 非常感谢您的回复,我设置的 IIS 错误。 TY
    【解决方案2】:

    TCP 绑定更适合 Internet 上的回调,因为 TCP 本质上是双向的。 HTTP 是一个请求,它只是一种方式。因此 dualHttpBinding 中的对偶。 WCF 必须创建第二个返回到客户端的 HTTP 连接,以便服务可以向客户端发送请求。

    互联网并没有真正设置为服务器通过 HTTP 进行回调。路由器执行 NAT 之类的事情意味着必须转发端口才能正确路由 HTTP 请求,并且客户端必须运行 HTTP 服务器。

    因此,使用 TCP 要容易得多。无论是这样还是可能让客户端请求一个从服务器端流式传输的回复对象(实际上是一个永无止境的回复),服务器可以触发通知。但这并不简单。

    【讨论】:

    • 感谢您的回复,但是如何将上面的示例更改为使用 netTcp?
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多