I have a service that was previously configured to use nettcp binding. This configuration worked.
Its binding looked like this:
<binding name="TcpBinding" closeTimeout="00:01:00" openTimeout="00:01:00"
receiveTimeout="00:10:00" sendTimeout="00:01:00" transactionFlow="false"
transferMode="Streamed" transactionProtocol="OleTransactions"
hostNameComparisonMode="StrongWildcard" listenBacklog="10"
maxBufferPoolSize="524288"
maxConnections="10" maxReceivedMessageSize="100000000">
<readerQuotas maxNameTableCharCount="1000000" maxStringContentLength="8192000"
maxArrayLength="1638400" />
<security mode="None"/>
</binding>
I tried to translate this to a customBinding to enable a leaseTimeout.
<customBinding>
<binding name="TcpBindingCustom" closeTimeout="00:01:00"
openTimeout="00:01:00" receiveTimeout="00:10:00" sendTimeout="00:01:00" >
<windowsStreamSecurity protectionLevel="None" />
<transactionFlow transactionProtocol="OleTransactions"/>
<tcpTransport transferMode="Streamed" hostNameComparisonMode="StrongWildcard"
maxBufferPoolSize="524288" listenBacklog="10"
maxReceivedMessageSize="100000000" portSharingEnabled="true"
maxBufferSize="65536">
<connectionPoolSettings groupName="default" leaseTimeout="00:05:00"
开发者_如何学编程 idleTimeout="00:02:00" maxOutboundConnectionsPerEndpoint="20" />
</tcpTransport>
</binding>
<customBinding>
I did not see a way to duplicate the <security mode ="None">
This runs fine when everything is local, but I get the following exception once it is deployed.
System.ServiceModel.Security.SecurityNegotiationException:
The server has rejected the client credentials. --->
System.Security.Authentication.InvalidCredentialException:
The server has rejected the client credentials. --->
System.ComponentModel.Win32Exception:
I did not get these errors with tcpBinding.
How can I duplicate this behavior with customBinding? Could something else be causing the SecurityNegotiationException?
I think you have to use the customBinding element to configure your service. I didn't see that in the config you provided. Look at this good MSDN article on configuring bindings to see how to create a custom binding. Custom bindings are toward the end of the article.
EDIT: Sorry, got the config blocks turned around. The netTcpBinding in WCF is a secure binding which by default uses the Windows identity and transport security. Although you are trying to create a custom version of it with the security mode set to "none", you actually need to match how netTcpBinding is configured. It sure would be nice if MSDN documented all the standard binding by showing how they actually look like as custom bindings. Try this config:
<customBinding>
<binding name="TcpBindingCustom" closeTimeout="00:01:00"
openTimeout="00:01:00" receiveTimeout="00:10:00" sendTimeout="00:01:00" >
<windowsStreamSecurity protectionLevel="None" />
<transactionFlow transactionProtocol="OleTransactions"/>
<tcpTransport transferMode="Streamed" hostNameComparisonMode="StrongWildcard"
maxBufferPoolSize="524288" listenBacklog="10"
maxReceivedMessageSize="100000000" portSharingEnabled="true"
maxBufferSize="65536">
<connectionPoolSettings groupName="default" leaseTimeout="00:05:00"
idleTimeout="00:02:00" maxOutboundConnectionsPerEndpoint="20" />
</tcpTransport>
<security authenticationMode="AnonymousForSslNegotiated"/>
</binding>
<customBinding>
Turns out the answer was to remove all security information from the binding tag. So in this case remove the
<windowsStreamSecurity protectionLevel="None" />
and the
<security authenticationMode="AnonymousForSslNegotiated"/>
I followed some of Sixto Saez's advice and looked at the implementation of NetTcpBinding in Reflector.
The NetTcpBinding class overrides the CreateBindingElements method to include this logic:
SecurityBindingElement item = this.CreateMessageSecurity();
if (item != null)
{
elements.Add(item);
}
with CreateMessageSecurity implemented like this:
private SecurityBindingElement CreateMessageSecurity()
{
if ((this.security.Mode != SecurityMode.Message)
&& (this.security.Mode != SecurityMode.TransportWithMessageCredential))
{
return null;
}
return this.security.CreateMessageSecurity(this.ReliableSession.Enabled);
}
One of my co workers was able to step through this logic in the debugger and reproduce this behavior with the custom binding.
It would in fact be very helpful if someone could produce a conversion table showing how the basic bindings are created with the custom binding elements.
精彩评论