WCF netTcpBinding 问题:Contract 需要 Duplex,但 Binding 'BasicHttpBinding' 不支持它或未正确配置以支持它
WCF netTcpBinding issue: Contract requires Duplex, but Binding 'BasicHttpBinding' doesn't support it or isn't configured properly to support it
我正在尝试在 WCF 服务中创建回调。到目前为止,服务使用的是 basicHttpBinding,因此我想为 netTcpBinding 添加另一个端点。服务已托管在 IIS 中。首先它是在 IIS 6 中托管的,但后来我安装了 IIS 7。
所以,我收到以下错误:
The requested service, 'net.tcp://localhost:1801/MyServiceName.svc/NetTcpExampleAddress' could not be activated. See the server's diagnostic trace logs for more information.
看到日志时,是这样的信息:
所以主要错误是:
Contract requires Duplex, but Binding 'BasicHttpBinding' doesn't support it or isn't configured properly to support it.
这是我的配置文件:
我的Web.config服务器:
<system.serviceModel>
<bindings>
<netTcpBinding>
<binding name="demoServiceNetTcpBinding">
<security mode="None"/>
</binding>
</netTcpBinding>
<basicHttpBinding>
<binding name="demoServiceHttpBinding" receiveTimeout="00:05:00" sendTimeout="00:05:00" maxReceivedMessageSize="2147483647">
<security mode="None"/>
</binding>
</basicHttpBinding>
</bindings>
<services>
<service name="MyServerName.MyServiceName">
<host>
<baseAddresses>
<add baseAddress="net.tcp://localhost:1801/MyServiceName.svc/"/>
<add baseAddress="http://localhost:1800/MyServiceName.svc/"/>
</baseAddresses>
</host>
<endpoint
address="NetTcpExampleAddress"
binding="netTcpBinding"
bindingConfiguration="demoServiceNetTcpBinding"
contract="MyServerName.SharedContract.IMyServiceName"/>
<endpoint
address="BasicHttpExampleAddress"
binding="basicHttpBinding"
bindingConfiguration="demoServiceHttpBinding"
contract="MyServerName.SharedContract.IMyServiceName"/>
<endpoint address="mex" binding="mexTcpBinding" contract="IMetadataExchange" />
</service>
</services>
<behaviors>
<serviceBehaviors>
<behavior>
<serviceDebug includeExceptionDetailInFaults="true"/>
<serviceMetadata httpGetEnabled="true"/>
</behavior>
</serviceBehaviors>
</behaviors>
</system.serviceModel>
我的App.config客户:
<system.serviceModel>
<bindings>
<netTcpBinding>
<binding name="demoServiceNetTcpBinding">
<security mode="None"/>
</binding>
</netTcpBinding>
<basicHttpBinding>
<binding name="demoServiceHttpBinding" receiveTimeout="00:05:00" sendTimeout="00:05:00" maxReceivedMessageSize="2147483647">
<security mode="None"/>
</binding>
</basicHttpBinding>
</bindings>
<client>
<endpoint name="NetTcpExampleName"
address="net.tcp://localhost:1801/DicomQueryService.svc/NetTcpExampleAddress"
bindingConfiguration ="demoServiceNetTcpBinding"
contract="MyServerName.SharedContract.IMyServiceName"
binding="netTcpBinding" />
<endpoint name="BasicHttpExampleName"
address="http://localhost:1800/MyServiceName.svc/BasicHttpExampleAddress"
bindingConfiguration ="demoServiceHttpBinding"
contract="MyServerName.SharedContract.IMyServiceName"
binding="basicHttpBinding" />
</client>
</system.serviceModel>
我的 IIS 中的设置:
如果您需要任何其他代码,请告诉我,我会更新问题。
编辑 1:
以下是代码的更多详细信息,说明我如何从客户端(在客户端)调用服务:
public class MyCommandClass : IMyServiceCallback
{
public MyCommandClass()
{
var ctx = new InstanceContext(new MyCommandClass());
DuplexChannelFactory<MyServerName.SharedContract.IMyServiceName> channel = new DuplexChannelFactory<MyServerName.SharedContract.IMyServiceName>(ctx, "NetTcpExampleName");
MyServerName.SharedContract.IMyServiceName clientProxy = channel.CreateChannel();
clientProxy.MyFunction(); //debug point is comming here and then it throws the error
clientProxy.ProcessReport();
(clientProxy as IClientChannel).Close();
channel.Close();
}
public void Progress(int percentageCompleted)
{
Console.WriteLine(percentageCompleted.ToString() + " % completed");
}
}
其中接口(在服务器端)定义为:
[ServiceContract(CallbackContract = typeof(IMyServiceCallback))]
public interface IMyServiceName
{
[OperationContract]
void MyFunction();
[OperationContract(IsOneWay = true)]
void ProcessReport();
}
public interface IMyServiceCallback
{
[OperationContract(IsOneWay = true)]
void Progress(int percentageCompleted);
}
服务(在服务器端)定义为:
public class MyServiceName: IMyServiceName
{
public void MyFunction()
{
//do something
}
public void ProcessReport()
{
//trigger the callback method
for (int i = 1; i <= 100; i++)
{
Thread.Sleep(100);
OperationContext.Current.GetCallbackChannel<IMyServiceCallback>().Progress(i);
}
}
}
到目前为止我的方法只是一个演示。一旦与此问题相关的错误得到修复,我就会开始开发这些方法。
您的服务合同需要双工连接(您有 ServiceCallback
属性)。因此,此服务公开的所有端点都必须支持双工连接。 Net.tcp 支持它,但 basicHttp 不支持,因此您现在不能在您的服务中使用 basicHttp。
我正在尝试在 WCF 服务中创建回调。到目前为止,服务使用的是 basicHttpBinding,因此我想为 netTcpBinding 添加另一个端点。服务已托管在 IIS 中。首先它是在 IIS 6 中托管的,但后来我安装了 IIS 7。
所以,我收到以下错误:
The requested service, 'net.tcp://localhost:1801/MyServiceName.svc/NetTcpExampleAddress' could not be activated. See the server's diagnostic trace logs for more information.
看到日志时,是这样的信息:
所以主要错误是:
Contract requires Duplex, but Binding 'BasicHttpBinding' doesn't support it or isn't configured properly to support it.
这是我的配置文件:
我的Web.config服务器:
<system.serviceModel>
<bindings>
<netTcpBinding>
<binding name="demoServiceNetTcpBinding">
<security mode="None"/>
</binding>
</netTcpBinding>
<basicHttpBinding>
<binding name="demoServiceHttpBinding" receiveTimeout="00:05:00" sendTimeout="00:05:00" maxReceivedMessageSize="2147483647">
<security mode="None"/>
</binding>
</basicHttpBinding>
</bindings>
<services>
<service name="MyServerName.MyServiceName">
<host>
<baseAddresses>
<add baseAddress="net.tcp://localhost:1801/MyServiceName.svc/"/>
<add baseAddress="http://localhost:1800/MyServiceName.svc/"/>
</baseAddresses>
</host>
<endpoint
address="NetTcpExampleAddress"
binding="netTcpBinding"
bindingConfiguration="demoServiceNetTcpBinding"
contract="MyServerName.SharedContract.IMyServiceName"/>
<endpoint
address="BasicHttpExampleAddress"
binding="basicHttpBinding"
bindingConfiguration="demoServiceHttpBinding"
contract="MyServerName.SharedContract.IMyServiceName"/>
<endpoint address="mex" binding="mexTcpBinding" contract="IMetadataExchange" />
</service>
</services>
<behaviors>
<serviceBehaviors>
<behavior>
<serviceDebug includeExceptionDetailInFaults="true"/>
<serviceMetadata httpGetEnabled="true"/>
</behavior>
</serviceBehaviors>
</behaviors>
</system.serviceModel>
我的App.config客户:
<system.serviceModel>
<bindings>
<netTcpBinding>
<binding name="demoServiceNetTcpBinding">
<security mode="None"/>
</binding>
</netTcpBinding>
<basicHttpBinding>
<binding name="demoServiceHttpBinding" receiveTimeout="00:05:00" sendTimeout="00:05:00" maxReceivedMessageSize="2147483647">
<security mode="None"/>
</binding>
</basicHttpBinding>
</bindings>
<client>
<endpoint name="NetTcpExampleName"
address="net.tcp://localhost:1801/DicomQueryService.svc/NetTcpExampleAddress"
bindingConfiguration ="demoServiceNetTcpBinding"
contract="MyServerName.SharedContract.IMyServiceName"
binding="netTcpBinding" />
<endpoint name="BasicHttpExampleName"
address="http://localhost:1800/MyServiceName.svc/BasicHttpExampleAddress"
bindingConfiguration ="demoServiceHttpBinding"
contract="MyServerName.SharedContract.IMyServiceName"
binding="basicHttpBinding" />
</client>
</system.serviceModel>
我的 IIS 中的设置:
如果您需要任何其他代码,请告诉我,我会更新问题。
编辑 1:
以下是代码的更多详细信息,说明我如何从客户端(在客户端)调用服务:
public class MyCommandClass : IMyServiceCallback
{
public MyCommandClass()
{
var ctx = new InstanceContext(new MyCommandClass());
DuplexChannelFactory<MyServerName.SharedContract.IMyServiceName> channel = new DuplexChannelFactory<MyServerName.SharedContract.IMyServiceName>(ctx, "NetTcpExampleName");
MyServerName.SharedContract.IMyServiceName clientProxy = channel.CreateChannel();
clientProxy.MyFunction(); //debug point is comming here and then it throws the error
clientProxy.ProcessReport();
(clientProxy as IClientChannel).Close();
channel.Close();
}
public void Progress(int percentageCompleted)
{
Console.WriteLine(percentageCompleted.ToString() + " % completed");
}
}
其中接口(在服务器端)定义为:
[ServiceContract(CallbackContract = typeof(IMyServiceCallback))]
public interface IMyServiceName
{
[OperationContract]
void MyFunction();
[OperationContract(IsOneWay = true)]
void ProcessReport();
}
public interface IMyServiceCallback
{
[OperationContract(IsOneWay = true)]
void Progress(int percentageCompleted);
}
服务(在服务器端)定义为:
public class MyServiceName: IMyServiceName
{
public void MyFunction()
{
//do something
}
public void ProcessReport()
{
//trigger the callback method
for (int i = 1; i <= 100; i++)
{
Thread.Sleep(100);
OperationContext.Current.GetCallbackChannel<IMyServiceCallback>().Progress(i);
}
}
}
到目前为止我的方法只是一个演示。一旦与此问题相关的错误得到修复,我就会开始开发这些方法。
您的服务合同需要双工连接(您有 ServiceCallback
属性)。因此,此服务公开的所有端点都必须支持双工连接。 Net.tcp 支持它,但 basicHttp 不支持,因此您现在不能在您的服务中使用 basicHttp。