Calling secure WCF service manually - c#

I need to call a WCF manually (via HttpWebRequest). I can call my service by adding a web reference and calling it through the proxy, so I know the service is setup correctly and the certs, web config, etc. is all correct. Based on samples I've found, I think I'm doing it correctly, but still getting an internal error 500.
EDIT: WebService is using wsHttpBinding.
Console app code is:
HttpWebRequest req = (HttpWebRequest)WebRequest.Create("http://localhost:8733/Design_Time_Addresses/WcfServiceLibrary1/Service1");
string strRequest = Properties.Resources.TextFile1;
req.Method = "POST";
req.ContentType = "application/soap+xml; charset=utf-8";
req.ContentLength = strRequest.Length;
req.Credentials = new NetworkCredential("test", "test");
using (Stream stream = req.GetRequestStream())
{
stream.Write(UTF8Encoding.Default.GetBytes(strRequest), 0, strRequest.Length);
}
using (WebResponse res = req.GetResponse())
{
// nothing to do here
}
TextFile1 is the XML request... just hard coding for now:
<s:Envelope xmlns:a="http://www.w3.org/2005/08/addressing" xmlns:s="http://www.w3.org/2003/05/soap-envelope">
<s:Header>
<a:Action s:mustUnderstand="1">http://tempuri.org/IService1/GetData</a:Action>
<a:MessageID>urn:uuid:f3c2172e-eeb9-4dfd-8e1b-3a623088b78f</a:MessageID>
<a:ReplyTo>
<a:Address>http://www.w3.org/2005/08/addressing/anonymous</a:Address>
</a:ReplyTo>
</s:Header>
<s:Body>
<GetData xmlns="http://tempuri.org/">
<value>0</value>
<value2>test</value2>
</GetData>
</s:Body>
</s:Envelope>
What am I missing here? There are no further details inside the exception.
EDIT:
Web.config:
<?xml version="1.0" encoding="utf-8" ?>
<configuration>
<appSettings>
<add key="aspnet:UseTaskFriendlySynchronizationContext" value="true" />
</appSettings>
<system.web>
<compilation debug="true" />
</system.web>
<!-- When deploying the service library project, the content of the config file must be added to the host's
app.config file. System.Configuration does not support config files for libraries. -->
<system.serviceModel>
<services>
<service name="WcfServiceLibrary1.Service1">
<host>
<baseAddresses>
<add baseAddress = "http://localhost:8733/Design_Time_Addresses/WcfServiceLibrary1/Service1/" />
</baseAddresses>
</host>
<!-- Service Endpoints -->
<!-- Unless fully qualified, address is relative to base address supplied above -->
<endpoint address="" binding="wsHttpBinding" bindingConfiguration="RequestUserName" contract="WcfServiceLibrary1.IService1">
<!--
Upon deployment, the following identity element should be removed or replaced to reflect the
identity under which the deployed service runs. If removed, WCF will infer an appropriate identity
automatically.
-->
<identity>
<dns value="localhost"/>
</identity>
</endpoint>
<!-- Metadata Endpoints -->
<!-- The Metadata Exchange endpoint is used by the service to describe itself to clients. -->
<!-- This endpoint does not use a secure binding and should be secured or removed before deployment -->
<endpoint address="mex" binding="mexHttpBinding" contract="IMetadataExchange"/>
</service>
</services>
<bindings>
<wsHttpBinding>
<binding name="RequestUserName">
<security mode="Message">
<message clientCredentialType="UserName"/>
</security>
</binding>
</wsHttpBinding>
</bindings>
<behaviors>
<serviceBehaviors>
<behavior>
<!-- To avoid disclosing metadata information,
set the values below to false before deployment -->
<serviceMetadata httpGetEnabled="True" httpsGetEnabled="True"/>
<!-- To receive exception details in faults for debugging purposes,
set the value below to true. Set to false before deployment
to avoid disclosing exception information -->
<serviceDebug includeExceptionDetailInFaults="True" />
<serviceCredentials>
<userNameAuthentication userNamePasswordValidationMode="Custom" customUserNamePasswordValidatorType="WcfServiceLibrary1.DistributorValidator, WcfServiceLibrary1" />
<serviceCertificate findValue="localhost" storeLocation="LocalMachine" storeName="TrustedPeople" x509FindType="FindBySubjectName"/>
</serviceCredentials>
</behavior>
</serviceBehaviors>
</behaviors>
</system.serviceModel>
</configuration>

You need to use HttpWebBinding to access any WCF service over Http.

Related

WCF Encryption/Decrpytion using both Server and Client certificates

I have created a service where there would be a private cert on the server where i am hosting the service and the client will have public key of it.
And the client would have a different private key where they will encrypt the message which they send to the endpoint i create and i have the public key for it which i will use to decrypt the message.
What i have so far in the server config file.
So this one takes care of the main private cert where the service will be hosted. I am not sure where/how to put the public key of the cert where client has/uses the private key to encrypt the message.
Any help would be really appreciated.
<?xml version="1.0"?>
<configuration>
<appSettings>
</appSettings>
<system.web>
<httpRuntime maxRequestLength="2147483647"/>
<compilation debug="false" strict="false" explicit="true" targetFramework="4.5.2"/>
<pages controlRenderingCompatibilityVersion="4.0"/>
<customErrors mode="Off"/>
</system.web>
<system.serviceModel>
<bindings>
<basicHttpBinding>
<binding name="basicHttpEndPointBinding">
<security mode="Message">
<message clientCredentialType="Certificate"/>
</security>
</binding>
</basicHttpBinding>
</bindings>
<services>
<service behaviorConfiguration="wcfJNet.ServiceBehavior" name="wcfJNetService">
<endpoint address="" binding="basicHttpBinding"
bindingConfiguration="basicHttpEndPointBinding"
contract="IJNetService">
<identity>
<dns value="xxxxxx" />
</identity>
</endpoint>
</service>
</services>
<behaviors>
<serviceBehaviors>
<behavior name="wcfJNet.ServiceBehavior">
<serviceMetadata httpGetEnabled="true" httpsGetEnabled="true"/>
<serviceDebug includeExceptionDetailInFaults="true"/>
<serviceCredentials>
<serviceCertificate findValue="0000xx000" storeLocation="LocalMachine" storeName="My" x509FindType="FindBySerialNumber"/>
<clientCertificate>
<authentication certificateValidationMode="PeerOrChainTrust"/>
</clientCertificate>
</serviceCredentials>
</behavior>
</serviceBehaviors>
</behaviors>
<protocolMapping>
<add binding="basicHttpsBinding" scheme="https"/>
</protocolMapping>
<serviceHostingEnvironment multipleSiteBindingsEnabled="true" />
</system.serviceModel>
<system.webServer>
<modules runAllManagedModulesForAllRequests="true"/>
<!--
To browse web app root directory during debugging, set the value below to true.
Set to false before deployment to avoid disclosing web app folder information.
-->
<directoryBrowse enabled="true"/>
</system.webServer>
</configuration>
Very good, you have a deep understanding of the working mechanism of the SSL certificate. Please refer to the below link.
https://learn.microsoft.com/en-us/dotnet/framework/wcf/feature-details/message-security-with-a-certificate-client
The client-side and server-side automatically negotiate the public key of the certificates during communication to encrypt the message with the other's public key and decrypt the soap message using the private key. Thereby we don’t need to manually program this procedure. It is enough to install each other’s certificate in the local certificate store.
If we authenticate the client with message security mode, we need to use the service credential section to configure the service certificate. Just like what you have done.
<serviceCredentials>
<serviceCertificate findValue="0000xx000" storeLocation="LocalMachine" storeName="My" x509FindType="FindBySerialNumber"/>
<clientCertificate>
<authentication certificateValidationMode="PeerOrChainTrust"/>
</clientCertificate>
</serviceCredentials>
On the client-side, generally, we need to specify two certificates, one is service certificate, another is client certificate.
//message security, we need to specify both the default certificate and the client certificate.
ServiceReference1.ServiceClient client = new ServiceReference1.ServiceClient(); client.ClientCredentials.ServiceCertificate.SetDefaultCertificate(StoreLocation.LocalMachine, StoreName.Root, X509FindType.FindByThumbprint, "cbc81f77ed01a9784a12483030ccd497f01be71c");
client.ClientCredentials.ClientCertificate.SetCertificate(StoreLocation.LocalMachine, StoreName.My, X509FindType.FindByThumbprint, "9b8db0dfe615458ace0ae9e89fcb983c5d16f633");
try
{
var result = client.SayHello();
Console.WriteLine(result);
}
catch (Exception)
{
throw;
}
As for the trust relationship between the certificates, on the client-side,we need to install the server certificate in the LocalCA, and on the server-side, we need to install the client certificate in the particular location depending on the authenticating mode. By default it is ok to install it in the LocalCA.
//this is default authentication mode.
sh.Credentials.ClientCertificate.Authentication.CertificateValidationMode= System.ServiceModel.Security.X509CertificateValidationMode.ChainTrust;
Feel free to let me know if there is anything I can help with.

WCF UserName & Password validation using wshttpbinding notworking

I am new to WCF Service authentication, I was trying to achieve wcfauthentication using wshttpbinding. but i am getting below exception.
Could not find a base address that matches scheme https for the endpoint with binding WSHttpBinding. Registered base address schemes are [http].
Web.Config:
<?xml version="1.0"?>
<configuration>
<appSettings>
<add key="aspnet:UseTaskFriendlySynchronizationContext" value="true" />
</appSettings>
<system.web>
<compilation debug="true" targetFramework="4.5" />
<httpRuntime targetFramework="4.5"/>
</system.web>
<system.serviceModel>
<bindings>
<wsHttpBinding>
<binding name="wsHttp">
<security mode="TransportWithMessageCredential">
<message clientCredentialType="UserName"/>
</security>
</binding>
</wsHttpBinding>
</bindings>
<services>
<service name="WCFAuth.Service1" behaviorConfiguration="wsHttpBehavior">
<endpoint address="" binding="wsHttpBinding" bindingConfiguration="wsHttp" contract="WCFAuth.IService1">
<identity>
<dns value="localhost"/>
</identity>
</endpoint>
<host>
<baseAddresses>
<add baseAddress="http://localhost:64765/"/>
</baseAddresses>
</host>
</service>
</services>
<behaviors>
<serviceBehaviors>
<behavior name="wsHttpBehavior">
<serviceMetadata httpGetEnabled="true" httpsGetEnabled="true"/>
<serviceDebug includeExceptionDetailInFaults="false"/>
<serviceCredentials>
<userNameAuthentication userNamePasswordValidationMode="Custom" customUserNamePasswordValidatorType="WCFAuth.ServiceAuthanticator, WCFAuth"/>
</serviceCredentials>
</behavior>
</serviceBehaviors>
</behaviors>
</system.serviceModel>
<system.webServer>
<modules runAllManagedModulesForAllRequests="true"/>
<!--
To browse web app root directory during debugging, set the value below to true.
Set to false before deployment to avoid disclosing web app folder information.
-->
<directoryBrowse enabled="true"/>
</system.webServer>
</configuration>
Service Authentication class:
using System;
using System.Collections.Generic;
using System.IdentityModel.Selectors;
using System.Linq;
using System.ServiceModel;
using System.Web;
namespace WCFAuth
{
public class ServiceAuthanticator : UserNamePasswordValidator
{
public override void Validate(string userName, string password)
{
string AppUserName = "ABC";
string AppPwd = "abc";
try
{
if (userName.ToLower() != AppUserName.ToLower() && password != AppPwd)
{
throw new FaultException("Unknown Username or Incorrect Password");
}
}
catch (Exception ex)
{
throw new FaultException("Unknown Username or Incorrect Password");
}
}
}
}
Client Side config file:
<?xml version="1.0" encoding="utf-8" ?>
<configuration>
<startup>
<supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.5" />
</startup>
<system.serviceModel>
<bindings>
<basicHttpBinding>
<!--<binding name="base" />-->
<binding name="base">
<security mode="TransportCredentialOnly">
<transport clientCredentialType="Basic"/>
</security>
</binding>
</basicHttpBinding>
</bindings>
<client>
<endpoint address="http://localhost:64765/Service1.svc" binding="basicHttpBinding"
bindingConfiguration="base" contract="WCFAuth.IService1" name="base" />
</client>
</system.serviceModel>
</configuration>
Consumer:
class Program
{
static void Main(string[] args)
{
try
{
WCFAuth.Service1Client client = new WCFAuth.Service1Client();
client.ClientCredentials.UserName.UserName = "test";
client.ClientCredentials.UserName.Password = "test";
var temp = client.GetData(1);
Console.WriteLine(temp);
}
catch (Exception ex)
{
Console.WriteLine(ex.Message);
}
Console.ReadKey();
}
}
I am getting attached exception when i try to browser svc file.
Can someone correct me, where i am committing mistake, thanks in advance.
The problem here is that you are using a WSHttpBinding with Transport Security, but the base address you set is http. It is not possible to work with http here, because you are sending credentials over the wire.
Either change it to https, or create a second binding configuration for development purposes. One with Transport Security (https), and a second without (http).
Also make sure that your clients binding matches the binding from your server.
As Marc mentioned, we are supposed to provide a certificate when hosting the service. there might be something amiss during the process of hosting the service.
Here is a reference configuration, wish it is useful to you.
<system.serviceModel>
<bindings>
<wsHttpBinding>
<binding name="wsHttp">
<security mode="TransportWithMessageCredential">
<message clientCredentialType="UserName"/>
</security>
</binding>
</wsHttpBinding>
</bindings>
<services>
<service name="WCFAuth.Service1" behaviorConfiguration="wsHttpBehavior">
<endpoint address="" binding="wsHttpBinding" bindingConfiguration="wsHttp" contract="WCFAuth.IService1">
</endpoint>
</service>
</services>
<behaviors>
<serviceBehaviors>
<behavior name="wsHttpBehavior">
<serviceMetadata httpGetEnabled="true" httpsGetEnabled="true"/>
<serviceDebug includeExceptionDetailInFaults="false"/>
<serviceCredentials>
<userNameAuthentication userNamePasswordValidationMode="Custom" customUserNamePasswordValidatorType="WCFAuth.ServiceAuthanticator, WCFAuth"/>
</serviceCredentials>
</behavior>
</serviceBehaviors>
</behaviors>
</system.serviceModel>
Then we should add a https binding in IIS Site Bindings module.
The service address would be https://x.x.x.x:8865/Service1.svc
One thing must be noted that we should trust the service certificate when we call the service by adding service reference.
ServicePointManager.ServerCertificateValidationCallback += delegate
{
return true;
};
ServiceReference2.Service1Client client = new ServiceReference2.Service1Client();
client.ClientCredentials.UserName.UserName = "jack";
client.ClientCredentials.UserName.Password = "123456";
Besides, if we use SecurityMode.Message, we are supposed to provide a certificate in code snippets.
<serviceCredentials>
<serviceCertificate storeLocation="LocalMachine" storeName="My" x509FindType="FindByThumbprint" findValue="869f82bd848519ff8f35cbb6b667b34274c8dcfe"/>
<userNameAuthentication customUserNamePasswordValidatorType="WcfService1.CustUserNamePasswordVal,WcfService1" userNamePasswordValidationMode="Custom"/>
</serviceCredentials>
Feel free to let me know if there is anything I can help with.

WCF An error occurred while receiving the HTTP response

I getting this error :An unhandled exception of type 'System.ServiceModel.CommunicationException'
full discripton of error:
An unhandled exception of type
'System.ServiceModel.CommunicationException' occurred in mscorlib.dll
Additional information: An error occurred while receiving the HTTP
response to
http://localhost:8733/Design_Time_Addresses/SnUpdateService/Service1/.
This could be due to the service endpoint binding not using the HTTP
protocol. This could also be due to an HTTP request context being
aborted by the server (possibly due to the service shutting down). See
server logs for more details.
When in clien i am trying to get response with stream data
SnUpdateService.Service1Client SnService = new SnUpdateService.Service1Client();
SnUpdateService.UpdateFiles com = new SnUpdateService.UpdateFiles();
com.Path = "C:\\temp";
com.SearchType = 1;
com.Version = "20150101";
SnUpdateService.UpdateFiles comReturn = new SnUpdateService.UpdateFiles();
comReturn = SnService.GetUpdateFiles(com);//here error
if there is no stream data all work fine.
What i am doing wrong?
This my client config
<?xml version="1.0" encoding="utf-8" ?>
<configuration>
<startup>
<supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.5" />
</startup>
<system.serviceModel>
<bindings>
<basicHttpBinding>
<binding name="BasicHttpBinding_IService1" maxBufferPoolSize="200000000"
maxReceivedMessageSize="200000000" />
</basicHttpBinding>
</bindings>
<client>
<endpoint address="http://localhost:8733/Design_Time_Addresses/SnUpdateService/Service1/"
binding="basicHttpBinding" bindingConfiguration="BasicHttpBinding_IService1"
contract="SnUpdateService.IService1" name="BasicHttpBinding_IService1" />
</client>
</system.serviceModel>
</configuration>
This my server webConfig
<?xml version="1.0" encoding="utf-8" ?>
<configuration>
<appSettings>
<add key="aspnet:UseTaskFriendlySynchronizationContext" value="true" />
</appSettings>
<system.web>
<compilation debug="true" />
</system.web>
<!-- When deploying the service library project, the content of the config file must be added to the host's
app.config file. System.Configuration does not support config files for libraries. -->
<system.serviceModel>
<services>
<service name="SnUpdateService.Service1">
<host>
<baseAddresses>
<add baseAddress = "http://localhost:8733/Design_Time_Addresses/SnUpdateService/Service1/" />
</baseAddresses>
</host>
<!-- Service Endpoints -->
<!-- Unless fully qualified, address is relative to base address supplied above -->
<endpoint address="" binding="basicHttpBinding" contract="SnUpdateService.IService1">
<!--
Upon deployment, the following identity element should be removed or replaced to reflect the
identity under which the deployed service runs. If removed, WCF will infer an appropriate identity
automatically.
-->
<identity>
<dns value="localhost"/>
</identity>
</endpoint>
<!-- Metadata Endpoints -->
<!-- The Metadata Exchange endpoint is used by the service to describe itself to clients. -->
<!-- This endpoint does not use a secure binding and should be secured or removed before deployment -->
<endpoint address="mex" binding="mexHttpBinding" contract="IMetadataExchange"/>
</service>
</services>
<behaviors>
<serviceBehaviors>
<behavior>
<!-- To avoid disclosing metadata information,
set the values below to false before deployment -->
<serviceMetadata httpGetEnabled="True" httpsGetEnabled="True"/>
<!-- To receive exception details in faults for debugging purposes,
set the value below to true. Set to false before deployment
to avoid disclosing exception information -->
<serviceDebug includeExceptionDetailInFaults="False" />
</behavior>
</serviceBehaviors>
</behaviors>
</system.serviceModel>
</configuration>
I think you are missing the definition for the binding configuration BasicHttpBinding_IService1 in client configuration file.
Also, you can set includeExceptionDetailInFaults="False" to "true" to get more detailed stack trace. Which helps you debug.
I had the same problem some time back and resolved it by enabling 32-Bit applications in the app pool where my service was hosted.

WCF service and client returning invalid response type

I've read every pertinent question on the web regarding this exact error:
The content type text/html; charset=UTF-8 of the response message does not match the content type of the binding (text/xml; charset=utf-8)
However, I still can't determine what the actual cause of the error is. It happens randomly with 4 web servers behind a load balancer. When the error occurs, I manually type in one of the webserver names in the address bar where the load balancer name is. The data won't be retrieved from one of the web servers for that particular instance, but if I try on of the other servers, I'll get the data back.
We can't expect our users to manually change the url of the load balancer to one of the 4 server names to try and get a hit.
From what I read, it seems like a config error between the client and server. If that was the case, wouldn't it be happening all the time? The error is obviously happening on the client side inside the MVC controller method from my logging messages.
I'm posting my code down below and hope that somebody can answer this question. I would really appreciate it.
Server config
<system.serviceModel>
<services>
<service name="FuelTktImgRetrievalSvc.FuelTktImgRetrieval" behaviorConfiguration="ServiceBehavior">
<endpoint address="" binding="basicHttpBinding" contract="FuelTktImgRetrievalSvc.IFuelTktImgRetrieval" bindingConfiguration="BasicHttpBinding_IFuelTktImgRetrieval">
<identity>
<dns value="localhost" />
</identity>
</endpoint>
<endpoint address="mex" binding="mexHttpBinding" contract="IMetadataExchange" />
<host>
<baseAddresses>
<!--<add baseAddress="\\miavdeteoabweb\applications\FuelTktImgRetrievalSvc" />-->
</baseAddresses>
</host>
</service>
</services>
<bindings>
<basicHttpBinding>
<binding name="BasicHttpBinding_IFuelTktImgRetrieval" closeTimeout="00:10:00"
openTimeout="00:10:00" receiveTimeout="04:00:00"
sendTimeout="04:00:00" maxBufferPoolSize="2147483647" maxReceivedMessageSize="2147483647" />
</basicHttpBinding>
</bindings>
<diagnostics wmiProviderEnabled="false" performanceCounters="All">
<messageLogging logMessagesAtTransportLevel="true" logMessagesAtServiceLevel="true" logMalformedMessages="true" logEntireMessage="true" maxSizeOfMessageToLog="2147483647" maxMessagesToLog="500" />
</diagnostics>
<behaviors>
<serviceBehaviors>
<behavior name="ServiceBehavior">
<!-- To avoid disclosing metadata information, set the values below to false before deployment -->
<serviceMetadata httpGetEnabled="true" httpsGetEnabled="true" />
<!-- To receive exception details in faults for debugging purposes, set the value below to true. Set to false before deployment to avoid disclosing exception information -->
<serviceDebug includeExceptionDetailInFaults="true" />
<dataContractSerializer maxItemsInObjectGraph="2147483647" />
</behavior>
</serviceBehaviors>
</behaviors>
<protocolMapping>
<add binding="basicHttpsBinding" scheme="http" />
</protocolMapping>
<serviceHostingEnvironment aspNetCompatibilityEnabled="true" multipleSiteBindingsEnabled="true" />
</system.serviceModel>
Client config
<system.serviceModel>
<bindings>
<basicHttpBinding>
<binding name="BasicHttpBinding_IFuelTktImgRetrieval" />
</basicHttpBinding>
</bindings>
<diagnostics wmiProviderEnabled="true">
<messageLogging logMessagesAtTransportLevel="true" logMessagesAtServiceLevel="true" logMalformedMessages="true" logEntireMessage="true" maxSizeOfMessageToLog="2147483647" maxMessagesToLog="500" />
</diagnostics>
<client>
<endpoint address="http://ride/FuelTktImgRetrievalSvc/FuelTktImgRetrieval.svc"
binding="basicHttpBinding" bindingConfiguration="BasicHttpBinding_IFuelTktImgRetrieval"
contract="FuelTktImgRetrievalSvc.IFuelTktImgRetrieval" name="BasicHttpBinding_IFuelTktImgRetrieval" />
</client>
<behaviors>
<endpointBehaviors>
<behavior name="webhttp">
<webHttp />
</behavior>
<behavior name="BasicHttpBinding_IFuelTktImgRetrieval">
<dataContractSerializer maxItemsInObjectGraph="2147483647" />
</behavior>
</endpointBehaviors>
</behaviors>
</system.serviceModel>
Server method that is called
public async Task<List<HH_FuelTkt_Output>> GetFilteredFuelTicketsAsync(HH_FuelTkt_Input value)
{
using (HandheldEntities DbContext = new HandheldEntities())
{
using (var dbcxtTrans = DbContext.Database.BeginTransaction(System.Data.IsolationLevel.ReadUncommitted))
{
try
{
// code left out for brevity
List<HH_FuelTkt_Output> tkts_Combined = await tkts.ToListAsync();
dbcxtTrans.Commit();
return tkts_Combined;
}
MVC Controller code
[HttpPost]
public async Task<JsonResult> GetFilteredFuelTicketsAsync(HH_FuelTkt_Input id)
{
try
{
IEnumerable<HH_FuelTkt_Output> fto = await db.GetFilteredFuelTicketsAsync(id);
return Json(fto, JsonRequestBehavior.AllowGet);
}
AJAX call from the client to the service.
$.ajax({
url: '#Url.Action("GetFilteredFuelTicketsAsync", "Home")',
data: JSON.stringify(HH_FuelTkt_Input),
dataType: 'json',
type: "POST",
contentType: "application/json; charset=utf-8",
success: function (data) {
This is presumably an error you see on the client rather than the server. The error message states that it received text/html when it was expecting text/xml. This is usually the case when the service is being hosted in IIS and some issue with the server causes it to respond with an ASP.NET error page (which will be HTML) rather than a SOAP response (which would be XML). The intermittent nature of the error and the fact your are using a load-balancer suggests to me that one of the servers behind the load balancer has something wrong with it.
Can you reach the servers individually? Try browsing to the .svc page for each server and/or invoking the web service in a tool like soapui and you should see the HTML error page. Alternatively try trawling the Windows Event Log for ASP.NET errors on each server and you may find one of the old errors logged.

Error in Web Service when Deployed to DMZ

I have a webservice which I can get to run on my computer, but when deployed to a webserver (in a DMZ) it doesn't work.
When running the service on the web server, it shows a WSDL and singleWSDL that seemingly appear to be correct. Using the singleWSDL in SoapUI to test the service returns the following error message
The message could not be processed. This is most likely because the
action 'http://tempuri.org/IService1/TestStringContract' is incorrect
or because the message contains an invalid or expired security context
token or because there is a mismatch between bindings. The security
context token would be invalid if the service aborted the channel due
to inactivity. To prevent the service from aborting idle sessions
prematurely increase the Receive timeout on the service endpoint's
binding.
From what I gather, the most likely cause, is an issue in the App.Config file, which I have detailed herein
<?xml version="1.0" encoding="utf-8" ?>
<configuration>
<system.web>
<compilation debug="true" />
</system.web>
<system.serviceModel>
<services>
<service name="MyService.Service1" behaviorConfiguration="MyService.Service1Behavior">
<host>
<baseAddresses>
<add baseAddress = "http://localhost:{port}/MyService.Service1.svc" />
</baseAddresses>
</host>
<endpoint address="http://{external_ip}:{port}/MyService.Service1.svc" binding="wsHttpBinding" contract="MyService.IService1">
<identity>
<dns value="localhost"/>
</identity>
</endpoint>
</service>
</services>
<behaviors>
<serviceBehaviors>
<behavior name="EquitaWcfCbl.Service1Behavior">
<serviceThrottling maxConcurrentCalls="10"/>
<serviceMetadata httpGetEnabled="True" httpGetUrl="http://{external_ip}:{port}/EquitaWcfCblMyService.Service1.svc/mex"/>
<serviceDebug includeExceptionDetailInFaults="False" />
</behavior>
</serviceBehaviors>
</behaviors>
</system.serviceModel>
</configuration>
[update # 2014-02-19 1400hrs]
With further research continually pointing that the setup of the App.Config; I decided to pull out the current App.Config file and start it again, from scratch, using the WCF Service Configuration Editor, which is built into Visual Studio (tools menu) adding in the information a piece at a time and testing progress, which resulted in a working service with the following App.Config
<?xml version="1.0" encoding="utf-8"?>
<configuration>
<system.serviceModel>
<behaviors>
<serviceBehaviors>
<behavior name="ServiceBehavior1">
<serviceDebug includeExceptionDetailInFaults="true"/>
<serviceMetadata
httpGetEnabled="true"
httpGetUrl=" http://{externalip}:{port}/MyService.Service1.svc/mex"/>
</behavior>
</serviceBehaviors>
</behaviors>
<bindings>
<basicHttpBinding>
<binding>
<security mode="None"></security>
</binding>
</basicHttpBinding>
</bindings>
<services>
<service
behaviorConfiguration="ServiceBehavior1"
name="EquitaWcfCbl.TabletService">
<endpoint
address="http://{externalip}:{port}/MyService.Service1.svc/mex"
binding="basicHttpBinding"
bindingConfiguration=""
name="ServiceEndpoint1"
contract=" MyService.Service1" />
</service>
</services>
</system.serviceModel>
</configuration>
I'm not (yet) entirely convinced that this is exactly what we need, but with a working service ... I can at least progress.

Categories