使用 net tcp 的 WCF 双工服务:“需要流安全性...”
Posted
技术标签:
【中文标题】使用 net tcp 的 WCF 双工服务:“需要流安全性...”【英文标题】:WCF duplex service using net tcp: "Stream Security is required..." 【发布时间】:2010-10-26 06:44:45 【问题描述】:我正在编写一项服务,允许用户注册并在事件发生时接收通知。我正在尝试使用 netTcpBinding 执行此操作,但即使在我的本地计算机上运行时也会不断出现错误。
当我尝试发送通知时,我超时,收到此错误:
http://www.w3.org/2005/08/addressing/anonymous 需要 Stream Security,但未协商安全上下文。这可能是由于远程端点在其绑定中缺少 StreamSecurityBindingElement 造成的。
为了测试,我将服务托管在控制台中,它正在为我打开,我可以看到 WSDL 并在其上运行 svcutil。但是,当我运行客户端并尝试发送通知时,就会出现上述错误。
主机 App.config:
<system.serviceModel>
<services>
<service name="CompanyName.WebServices.InterventionService.RegistrationService"
behaviorConfiguration="RegistrationServiceBehavior">
<endpoint address="http://localhost:8000/CompanyName/Registration"
binding="wsDualHttpBinding"
contract="CompanyName.WebServices.InterventionService.Interfaces.IRegistrationService"/>
<endpoint address="net.tcp://localhost:8001/CompanyName/Registration"
binding="netTcpBinding"
contract="CompanyName.WebServices.InterventionService.Interfaces.IRegistrationService"/>
</service>
<service name="CompanyName.WebServices.InterventionService.NotificationService"
behaviorConfiguration="NotificationServiceBehavior">
<endpoint address="http://localhost:8010/CompanyName/Notification"
binding="wsDualHttpBinding"
contract="CompanyName.WebServices.InterventionService.Interfaces.INotificationService"/>
<endpoint address="net.tcp://localhost:8011/CompanyName/Notification"
binding="netTcpBinding"
contract="CompanyName.WebServices.InterventionService.Interfaces.INotificationService"/>
</service>
</services>
<behaviors>
<serviceBehaviors>
<behavior name="RegistrationServiceBehavior">
<serviceMetadata httpGetEnabled="true"
httpGetUrl="http://localhost:8000/CompanyName/Registration"/>
</behavior>
<behavior name="NotificationServiceBehavior">
<serviceMetadata httpGetEnabled="true"
httpGetUrl="http://localhost:8010/CompanyName/Notification"/>
</behavior>
<behavior name="netTcpRegistrationServiceBehavior">
<serviceMetadata httpGetEnabled="true"
httpGetUrl="net.tcp://localhost:8001/CompanyName/Registration"/>
</behavior>
<behavior name="netTcpNotificationServiceBehavior">
<serviceMetadata httpGetEnabled="true"
httpGetUrl="net.tcp://localhost:8011/CompanyName/Notification"/>
</behavior>
</serviceBehaviors>
</behaviors>
这里是客户端 App.config:
<system.serviceModel>
<bindings>
<netTcpBinding>
<binding name="NetTcpBinding_IRegistrationService">
<security mode="None">
<message clientCredentialType="None"/>
<transport clientCredentialType="None"/>
</security>
</binding>
<binding name="NetTcpBinding_INotificationService">
<security mode="None">
<message clientCredentialType="None"/>
<transport clientCredentialType="None"/>
</security>
</binding>
</netTcpBinding>
<wsDualHttpBinding>
<binding name="WSDualHttpBinding_IRegistrationService">
<reliableSession ordered="true"/>
<security mode="None">
<message clientCredentialType="None" negotiateServiceCredential="false"/>
</security>
</binding>
<binding name="WSDualHttpBinding_INotificationService">
<reliableSession ordered="true"/>
<security mode="None">
<message clientCredentialType="None" negotiateServiceCredential="false"/>
</security>
</binding>
</wsDualHttpBinding>
</bindings>
<client>
<endpoint address="http://localhost:8000/GPS/Registration"
binding="wsDualHttpBinding"
bindingConfiguration="WSDualHttpBinding_IRegistrationService"
contract="IRegistrationService"
name="WSDualHttpBinding_IRegistrationService">
</endpoint>
<endpoint address="net.tcp://localhost:8001/GPS/Registration"
binding="netTcpBinding"
bindingConfiguration="NetTcpBinding_IRegistrationService"
contract="IRegistrationService"
name="NetTcpBinding_IRegistrationService">
</endpoint>
<endpoint address="http://localhost:8010/GPS/Notification"
binding="wsDualHttpBinding"
bindingConfiguration="WSDualHttpBinding_INotificationService"
contract="INotificationService"
name="WSDualHttpBinding_INotificationService">
</endpoint>
<endpoint address="net.tcp://localhost:8011/GPS/Notification"
binding="netTcpBinding"
bindingConfiguration="NetTcpBinding_INotificationService"
contract="INotificationService"
name="NetTcpBinding_INotificationService">
</endpoint>
</client>
我省略了很多注册码,因为我现在只是想让通知正常工作。
计划将此托管在不属于客户域(他们的设置)的 2003 Server 的 Windows 服务中,并且客户端计算机将位于客户的域中。
编辑:
我已将绑定添加到主机的 App.config:
<bindings>
<netTcpBinding>
<binding name="NetTcpBinding_IRegistrationService">
<security mode="None">
<message clientCredentialType="None"/>
<transport clientCredentialType="None"/>
</security>
</binding>
<binding name="NetTcpBinding_INotificationService">
<security mode="None">
<message clientCredentialType="None"/>
<transport clientCredentialType="None"/>
</security>
</binding>
</netTcpBinding>
<wsDualHttpBinding>
<binding name="WSDualHttpBinding_IRegistrationService">
<reliableSession ordered="true"/>
<security mode="None">
<message clientCredentialType="None" negotiateServiceCredential="false"/>
</security>
</binding>
<binding name="WSDualHttpBinding_INotificationService">
<reliableSession ordered="true"/>
<security mode="None">
<message clientCredentialType="None" negotiateServiceCredential="false"/>
</security>
</binding>
</wsDualHttpBinding>
</bindings>
这仍然是错误,具有相同的 Steam Security is required 错误消息。在新解决方案中尝试此应用的一小部分。
【问题讨论】:
【参考方案1】:嗯,你的问题似乎是这样的:
在服务器端,您使用不带参数的默认 netTCP 绑定 - 您无需更改任何内容。 netTCP 默认使用 Windows 凭据进行传输级安全
但是,在您的客户端上,您明确关闭了 netTCP 绑定上的任何安全性
所以两者不匹配,也不同意做什么。
您需要关闭两端(服务器和客户端)上的所有安全性,或者您只需要使用安全默认值(使用 Windows 凭据)。
马克
【讨论】:
太棒了!我认为 VS 发现这样做是正确的,但即便如此我也必须编辑配置。谢谢!【参考方案2】:我认为这是导致您进入许多不同方向的可怕错误消息之一。对于这种情况,上述答案是正确的。我的情况不同 - 我在客户端和服务端的安全设置是相同的。
就我而言,此链接指出了我的特殊缺陷:http://www.netframeworkdevs.com/windows-communication-foundation-wcf/error-invoking-service-with-a-net-tcp-binding-123918.shtml。
我的端点服务端 app.config 使用 bindingName
作为属性来命名绑定配置...而不是 bindingConfiguration
。我认为endpoint
上什至没有名为 bindingName 的属性。
所以...我的结论是,这个错误意味着“存在 WCF 配置错误”可能会缩小到服务端配置。呃。
【讨论】:
+1 确实有一个bindingName
属性,但是谢谢你——缺少bindingConfiguration
是我的问题。以上是关于使用 net tcp 的 WCF 双工服务:“需要流安全性...”的主要内容,如果未能解决你的问题,请参考以下文章