Programatically Manipulating WCF Binding, Not Having Effect - c#

I have run into the dreaded
The maximum message size quota for incoming messages (65536) has been exceeded. To increase the quota, use the MaxReceivedMessageSize property on the appropriate binding element.
error. No problem, I know you have to change the attributes on the web.config for the client and server to increase it up. I am creating my client in code however, and I am trying to manipulate these properties in kind.
Here I am creating the client, and assigning it to session. I will later call it through a class level _client field.
BasicHttpBinding binding = new BasicHttpBinding(BasicHttpSecurityMode.None);
binding.CloseTimeout = new TimeSpan(00, 05, 00);
binding.OpenTimeout = new TimeSpan(00, 05, 00);
binding.ReceiveTimeout = new TimeSpan(00, 05, 00);
binding.SendTimeout = new TimeSpan(00, 05, 00);
binding.TextEncoding = System.Text.Encoding.UTF8;
binding.MaxReceivedMessageSize = int.MaxValue;
binding.MaxBufferSize = int.MaxValue;
binding.MaxBufferPoolSize = int.MaxValue;
binding.Name = "BasicHttpBinding_Test";
binding.Security.Transport.ClientCredentialType = HttpClientCredentialType.Windows;
binding.Security.Message.ClientCredentialType = BasicHttpMessageCredentialType.UserName;
EndpointAddress endpointAddress = new EndpointAddress(wcfUrl);
HttpContext.Current.Session["Client"] = new TestClient(binding, endpointAddress);
I change the binding in code, and I could see in a watch these values are indeed taking effect. The _client in the below is the TestClient that was created before and stored in Session. However, the error persists. Is there another property I am missing?
Binding binding = _client.Endpoint.Binding;
binding.CloseTimeout = new TimeSpan(00, 05, 00);
binding.OpenTimeout = new TimeSpan(00, 05, 00);
binding.ReceiveTimeout = new TimeSpan(00, 05, 00);
binding.SendTimeout = new TimeSpan(00, 05, 00);
binding.GetType().GetProperty("ReaderQuotas").SetValue(binding, XmlDictionaryReaderQuotas.Max, null);
binding.GetType().GetProperty("TransferMode").SetValue(binding, TransferMode.Streamed, null);
binding.GetType().GetProperty("MaxBufferPoolSize").SetValue(binding, int.MaxValue, null);
binding.GetType().GetProperty("MaxBufferSize").SetValue(binding, int.MaxValue, null);
binding.GetType().GetProperty("MaxReceivedMessageSize").SetValue(binding, int.MaxValue, null);

both client and server binding would need
maxReceivedMessageSize
Setting your values to Max is a bad idea. You really want to try and limit that down to what you believe your usage is. Unless you really need 2gb file transfers and the server can handle that.

Related

WCF client failed when receive bytes array over 350 MB

When I receive bytes array over 350 MB, I am getting error as "The server did not provide a meaningful reply; this might be caused by a contract mismatch, a premature session shutdown or an internal server error."
Client side config
var binding = new NetTcpBinding(SecurityMode.None)
{
PortSharingEnabled = true,
MaxBufferSize = Int32.MaxValue,
MaxReceivedMessageSize = Int32.MaxValue,
ReaderQuotas = new XmlDictionaryReaderQuotas
{
MaxArrayLength = Int32.MaxValue,
MaxBytesPerRead = Int32.MaxValue,
MaxDepth = Int32.MaxValue,
MaxNameTableCharCount = Int32.MaxValue,
MaxStringContentLength = Int32.MaxValue,
},
MaxBufferPoolSize = 0,
TransactionFlow = false,
TransactionProtocol = TransactionProtocol.Default,
TransferMode = TransferMode.Streamed,
OpenTimeout = new TimeSpan(0, 10, 0),
CloseTimeout = new TimeSpan(0, 10, 0),
SendTimeout = new TimeSpan(0, 10, 0),
ReceiveTimeout = new TimeSpan(0, 10, 0)
};
container.Register(Component.For<IFtpsServiceFacade>()
.AsWcfClient(
new DefaultClientModel(
WcfEndpoint.BoundTo(binding)
.At(string.Format("net.tcp://{0}/FileService.Ftps",
"localhost")))
));
Server side config.
var binding = new NetTcpBinding
{
PortSharingEnabled = true,
MaxBufferSize = Int32.MaxValue,
MaxReceivedMessageSize = Int32.MaxValue,
ReaderQuotas = new XmlDictionaryReaderQuotas
{
MaxArrayLength = Int32.MaxValue,
MaxBytesPerRead = Int32.MaxValue,
MaxDepth = Int32.MaxValue,
MaxNameTableCharCount = Int32.MaxValue,
MaxStringContentLength = Int32.MaxValue,
},
MaxBufferPoolSize = 0,
TransactionFlow = false,
TransactionProtocol = TransactionProtocol.Default,
TransferMode = TransferMode.Buffered,
OpenTimeout = new TimeSpan(0, 10, 0),
CloseTimeout = new TimeSpan(0, 10, 0),
SendTimeout = new TimeSpan(0, 10, 0),
ReceiveTimeout = new TimeSpan(0, 10, 0)
};
container.Register(Component.For<IFtpsServiceFacade>()
.ImplementedBy<FtpsServiceFacade>()
.AsWcfService(
new DefaultServiceModel()
.AddEndpoints(
WcfEndpoint.BoundTo(binding)
.At(string.Format("net.tcp://{0}/FileService.Ftps",
"localhost"))
)).LifestyleSingleton() );
The establishment of the communication channel between the server-side and the client-side requires that the server-side and the client-side have the same binding settings. Therefore, the above error occurred. In order to solve this problem, we should change the settings on the server-side instead of the client-side. The max size of the supported file above 2GB, finished by the below configuration.
NetTcpBinding binding = new NetTcpBinding();
binding.Security.Mode = SecurityMode.None;
binding.MaxBufferSize = Int32.MaxValue;
binding.MaxBufferPoolSize = Int32.MaxValue;
binding.MaxReceivedMessageSize = Int32.MaxValue;
Especially to the security mode, it should be fully consistent with the setting located on the client-side.
Feel free to let me know if the problem still exists.

C# WCF Channel Timeout on subsequent calls

I have a C# app calling a Soap client using WCF. The first call to the service succeeds, but any calls thereafter fail.
The code to setup the client is:
public WebserviceHelper(string username, string password, string webserviceURL)
{
var binding = new BasicHttpBinding();
binding.MaxBufferPoolSize = 2147483647;
binding.MaxBufferSize = 2147483647;
binding.MaxReceivedMessageSize = 2147483647;
binding.OpenTimeout = new TimeSpan(0, 1, 0);
binding.ReceiveTimeout = new TimeSpan(0, 1, 0);
binding.SendTimeout = new TimeSpan(0, 1, 0);
var endpoint = new EndpointAddress(webserviceURL);
var channelFactory = new ChannelFactory<EntityAPISoap>(binding, endpoint);
SoapClient = new EntityAPISoapClient(binding, endpoint);
SoapClient.Endpoint.Behaviors.Add(new CustomEndpointBehavior(username, password));
var isAlive = SoapClient.isAlive();
Console.WriteLine(SoapClient.State); //Opened
isAlive = SoapClient.isAlive(); //timeout exception
}
The first call to isAlive returns immediately, the second call times out with this exception:
The request channel timed out while waiting for a reply after
00:01:00. Increase the timeout value passed to the call to Request or
increase the SendTimeout value on the Binding. The time allotted to
this operation may have been a portion of a longer timeout.
I've increased the timeout, but then it just takes longer to respond and anyway the server responds within a second, so 1 minute is more than enough.

Sharepoint 2010 GetListItems with Webservice - ListSoapClient with DefaultNetworkCredentials

I want to get some ListItems of a SharePoint 2010 List with a Win8 App. Everything works fine when I set the Credentials manually like:
BasicHttpBinding basicHttpBinding = new BasicHttpBinding();
basicHttpBinding.Security.Mode = BasicHttpSecurityMode.TransportCredentialOnly;
basicHttpBinding.Security.Transport.ClientCredentialType = HttpClientCredentialType.Windows;
EndpointAddress endpoint = new EndpointAddress("http://site1/site2/_vti_bin/Lists.asmx");
string listName = "{4e661b3b-d0a9-4440-b98f-3f3ef41a44a7}";
string viewName = "{f1ba8d46-ad36-40ef-b4bc-6f74ea87b5d7}";
string rowLimit = "25";
XElement ndQuery = new XElement("Query");
XElement ndViewFields = new XElement("ViewFields");
XElement ndQueryOptions = new XElement("QueryOptions");
MyService.ListsSoapClient client = new MyService.ListsSoapClient(basicHttpBinding, endpoint);
client.ClientCredentials.Windows.ClientCredential.UserName = "user";
client.ClientCredentials.Windows.ClientCredential.Password = "pw";
client.ClientCredentials.Windows.AllowedImpersonationLevel = System.Security.Principal.TokenImpersonationLevel.Impersonation;
MyService.GetListItemsResponse response = await client.GetListItemsAsync(listName, viewName, ndQuery, ndViewFields, rowLimit, ndQueryOptions, null);
If I try to set the Credentials with the logged on Windows user i get the following Unauthorized error:
The HTTP request is unauthorized with client authentication scheme
'Negotiate'. The authentication header received from the server was
'Negotiate,NTLM'.
client.ClientCredentials.Windows.ClientCredential = System.Net.CredentialCache.DefaultNetworkCredentials;
Can you help me?
try this (use default credentials instead of specific):
private ListsSoapClient CreateListsSoapClient(string siteUrl, string siteUserName, string sitePassword)
{
var basicHttpBinding = new BasicHttpBinding
{
CloseTimeout = new TimeSpan(00, 5, 00),
OpenTimeout = new TimeSpan(00, 5, 00),
ReceiveTimeout = new TimeSpan(00, 5, 00),
SendTimeout = new TimeSpan(00, 5, 00),
TextEncoding = Encoding.UTF8,
MaxReceivedMessageSize = int.MaxValue,
MaxBufferSize = int.MaxValue,
Security =
{
Mode = BasicHttpSecurityMode.TransportCredentialOnly
},
ReaderQuotas =
{
MaxArrayLength = int.MaxValue,
MaxBytesPerRead = int.MaxValue,
MaxStringContentLength = int.MaxValue
}
};
basicHttpBinding.Security.Transport.ClientCredentialType = HttpClientCredentialType.Ntlm;
var url = string.Format("{0}/_vti_bin/Lists.asmx", siteUrl);
var address = new EndpointAddress(url);
var listsSoapClient = new ListsSoapClient(basicHttpBinding, address);
listsSoapClient.ClientCredentials.Windows.AllowedImpersonationLevel = TokenImpersonationLevel.Delegation;
listsSoapClient.ChannelFactory.Credentials.Windows.ClientCredential = new NetworkCredential(siteUserName, sitePassword);
listsSoapClient.ChannelFactory.Credentials.Windows.AllowNtlm = true;
return listsSoapClient;
}

WCF nettcpbinding "send" timeout -- after all data was transmitted

I'm writing a local-machine client/server application using an application-hosted WCF service over nettcpbinding with a duplex channel (i.e., peer-to-peer communication). For legacy reasons, this is .NET 3.5.
This code sets up the server:
var netTcpBinding = new NetTcpBinding(SecurityMode.Transport);
netTcpBinding.Security.Transport.ClientCredentialType = TcpClientCredentialType.Windows;
netTcpBinding.Security.Transport.ProtectionLevel = ProtectionLevel.EncryptAndSign;
netTcpBinding.ReceiveTimeout = new TimeSpan(0, 0, 14);
netTcpBinding.SendTimeout = new TimeSpan(0, 0, 30);
netTcpBinding.OpenTimeout = new TimeSpan(0, 0, 30);
netTcpBinding.CloseTimeout = new TimeSpan(0, 0, 30);
netTcpBinding.ListenBacklog = 2;
netTcpBinding.MaxConnections = 200;
netTcpBinding.MaxBufferPoolSize = 10 * 1000 * 1000;
netTcpBinding.MaxBufferSize = 10* 1000 * 1000;
netTcpBinding.MaxReceivedMessageSize = 10* 1000 * 1000;
netTcpBinding.PortSharingEnabled = true;
netTcpBinding.ReliableSession.Enabled = true;
netTcpBinding.ReliableSession.Ordered = true;
netTcpBinding.ReliableSession.InactivityTimeout = new TimeSpan(23, 59, 59);
ISmartBrowserClientServiceCallback callback = new SmartBrowserClientServiceCallback();
InstanceContext context = new InstanceContext(callback);
smartBrowserServiceFactory = new DuplexChannelFactory<ClientService.ISmartBrowserClientService>(
context,
netTcpBinding,
new EndpointAddress(uri));
this.channel = this.smartBrowserServiceFactory.CreateChannel();
This code sets up the client:
var netTcpBinding = new NetTcpBinding(SecurityMode.Transport);
netTcpBinding.Security.Transport.ClientCredentialType = TcpClientCredentialType.Windows;
netTcpBinding.Security.Transport.ProtectionLevel = ProtectionLevel.EncryptAndSign;
netTcpBinding.ReceiveTimeout = new TimeSpan(23, 59, 59);
netTcpBinding.OpenTimeout = new TimeSpan(0, 0, 15); // timeout seconds are different to help debugging
netTcpBinding.SendTimeout = new TimeSpan(0, 0, 17);
netTcpBinding.ReceiveTimeout = new TimeSpan(0, 0, 19);
netTcpBinding.CloseTimeout = new TimeSpan(0, 0, 21);
netTcpBinding.ListenBacklog = 2;
netTcpBinding.MaxConnections = 100;
netTcpBinding.MaxBufferPoolSize = 10 * 1000 * 1000;
netTcpBinding.MaxBufferSize = 10 * 1000 * 1000;
netTcpBinding.MaxReceivedMessageSize = 10 * 1000 * 1000;
netTcpBinding.PortSharingEnabled = true;
netTcpBinding.ReliableSession.Enabled = true;
netTcpBinding.ReliableSession.Ordered = true;
netTcpBinding.ReliableSession.InactivityTimeout = new TimeSpan(23, 59, 59);
ISmartBrowserClientServiceCallback callback = new SmartBrowserClientServiceCallback(this.smartBrowserClient);
InstanceContext context = new InstanceContext(callback);
this.smartBrowserServiceFactory = new DuplexChannelFactory<ISmartBrowserClientService>(
context,
netTcpBinding,
new EndpointAddress(new Uri(string.Format(CultureInfo.InvariantCulture, "net.tcp://localhost:{0}/Cpy.SmartBrowser.SmartBrowserClientService/", defaultPort.ToString(CultureInfo.InvariantCulture)))));
this.smartBrowserServiceFactory.Faulted += (sender, e) =>
{
this.smartBrowserServiceFactory = null;
};
this.channel = this.smartBrowserServiceFactory.CreateChannel();
Now, when a client calls a service method with some data, that data is well received by the service, which acts upon it, but for some reason there's a TimeoutException on the sender after 17 seconds, the value I picked for the SendTimeout. I find this strange, because all data to send was already sent, instantly, and I see no reason for the system to wait for anything.
This client/server app will be used on a local machine with a single service and a single client, just peer-to-peer communicating. But if I can't get rid of this timeout, I'll have to work around it in a dirty way, which I want to avoid.
What obvious thing am I missing?

Silverlight out of browser mode

Does silverlight support SSL in oob mode? I have SSL turned on and it works fine in browser, but it doesnt connect oob mode. Is there something I am missing?
Thanks
EDIT:
_serviceHost = new ServiceHost(typeof(ApplicationService), new Uri(BaseAddress));
_serviceHost.Description.Behaviors.Add(new ServiceMetadataBehavior { HttpsGetEnabled = true });
var serviceBinding = new BasicHttpBinding(BasicHttpSecurityMode.Transport)
{
MessageEncoding = WSMessageEncoding.Text,
TextEncoding = Encoding.UTF8,
BypassProxyOnLocal = false,
UseDefaultWebProxy = true,
CloseTimeout = new TimeSpan(10, 0, 0),
OpenTimeout = new TimeSpan(10, 0, 0),
SendTimeout = new TimeSpan(10, 0, 0),
ReceiveTimeout = new TimeSpan(10, 0, 0),
HostNameComparisonMode = HostNameComparisonMode.StrongWildcard,
MaxBufferPoolSize = int.MaxValue,
MaxReceivedMessageSize = int.MaxValue,
AllowCookies = false,
TransferMode = TransferMode.StreamedResponse,
ReaderQuotas =
{
MaxDepth = 32,
MaxStringContentLength = int.MaxValue,
MaxArrayLength = 6553600,
MaxBytesPerRead = 4096,
MaxNameTableCharCount = 16384
}
};
var policyRetrieverBinding = new WebHttpBinding(WebHttpSecurityMode.Transport)
{
BypassProxyOnLocal = false,
UseDefaultWebProxy = true,
CloseTimeout = new TimeSpan(10, 0, 0),
OpenTimeout = new TimeSpan(10, 0, 0),
SendTimeout = new TimeSpan(10, 0, 0),
ReceiveTimeout = new TimeSpan(10, 0, 0),
HostNameComparisonMode = HostNameComparisonMode.StrongWildcard,
MaxBufferPoolSize = int.MaxValue,
MaxReceivedMessageSize = int.MaxValue,
AllowCookies = false,
TransferMode = TransferMode.StreamedResponse,
ReaderQuotas =
{
MaxDepth = 32,
MaxStringContentLength = int.MaxValue,
MaxArrayLength = 6553600,
MaxBytesPerRead = 4096,
MaxNameTableCharCount = 16384
}
};
//service endpoint
_serviceHost.AddServiceEndpoint(typeof(IApplicationService), serviceBinding, ServiceEndPoint);
//mex endpoint for metadata
_serviceHost.AddServiceEndpoint(typeof(IMetadataExchange), MetadataExchangeBindings.CreateMexHttpsBinding(), "mex");
//policy retriever endpoint
_serviceHost.AddServiceEndpoint(typeof(IPolicyRetriever), policyRetrieverBinding, string.Empty)
.Behaviors.Add(new WebHttpBehavior());
//so we get detailed exceptions
_serviceHost.Description.Behaviors.Find<ServiceDebugBehavior>()
.IncludeExceptionDetailInFaults = true;
_serviceHost.Open();
The service endpoint is configured to use :
"https://" + Environment.MachineName

Categories

Resources